Difference between a class and object in Kotlin

JavaAndroidKotlin

Java Problem Overview


I'm new to Kotlin and have recently converted a simple file from java to Kotlin. I am wondering why the Android converter changed my java class to a Kotlin object.

Java:

public class MyClass {
    static public int GenerateChecksumCrc16(byte bytes[]) {

        int crc = 0xFFFF;
        int temp;
        int crc_byte;

        for (byte aByte : bytes) {

            crc_byte = aByte;

            for (int bit_index = 0; bit_index < 8; bit_index++) {

                temp = ((crc >> 15)) ^ ((crc_byte >> 7));

                crc <<= 1;
                crc &= 0xFFFF;

                if (temp > 0) {
                    crc ^= 0x1021;
                    crc &= 0xFFFF;
                }

                crc_byte <<= 1;
                crc_byte &= 0xFF;

            }
        }

        return crc;
    }
}

Converted Kotlin:

object MyClass {
    fun GenerateChecksumCrc16(bytes: ByteArray): Int {

        var crc = 0xFFFF
        var temp: Int
        var crc_byte: Int

        for (aByte in bytes) {

            crc_byte = aByte.toInt()

            for (bit_index in 0..7) {

                temp = crc shr 15 xor (crc_byte shr 7)

                crc = crc shl 1
                crc = crc and 0xFFFF

                if (temp > 0) {
                    crc = crc xor 0x1021
                    crc = crc and 0xFFFF
                }

                crc_byte = crc_byte shl 1
                crc_byte = crc_byte and 0xFF

            }
        }

        return crc
    }
}

Why wasn't it:

class MyClass {
    ... etc ...
}

Any help would be greatly appreciated thanks.

Java Solutions


Solution 1 - Java

Kotlin's documentation on this is pretty good, so feel free to read that.

The chosen answer for this question has some poor phraseology in its explanation, and could easily mislead people. For instance, an object is not "a static class per se", but rather it is a static instance of a class that there is only one of, otherwise known as a singleton.

Perhaps the best way to show the difference is to look at the decompiled Kotlin code in Java form.

Kotlin object and class:

object ExampleObject {
  fun example() {
  }
}

class ExampleClass {
  fun example() {
  }
}

In order to use the ExampleClass, you need to create an instance of it: ExampleClass().example(), but with an object, Kotlin creates a single instance of it for you, and you don't ever call it's constructor, instead you just access it's static instance by using the name: ExampleObject.example().

Equivalent Java code Kotlin would generate:

Kotlin compiles to Java byte code, but if we reverse compile the above compiled Kotlin code to Java code this is what we get:

public final class ExampleObject {
   public static final ExampleObject INSTANCE = new ExampleObject();

   private ExampleObject() { }

   public final void example() {
   }
}

public final class ExampleClass {
   public final void example() {
   }
}

You would use the object in Kotlin the following way:

ExampleObject.example()

Which would compile down to the equivalent Java byte code for:

ExampleObject.INSTANCE.example()

Why does Kotlin introduce objects?

The primary use case of object in Kotlin is because Kotlin tries to do away with static, and primitives, leaving us with a purely object oriented language. Kotlin still uses static and primitives underneath the hood, but it discourages devs to use those concepts any more. Instead, now Kotlin replaces static with singleton object instances. Where you would previously use static field in Java, in Kotlin you will now create an object, and put that field in the object.

Interoperability with Java:

Because Kotlin is 100% interoperable with Java, sometimes you will want to expose certain APIs or fields in a way that is nicer for Java to read. To do this, you can use the @JvmStatic annotation. By annotating a field or a function in an object with @JvmStatic, it will compile down to static fields which Java can use easier.

Companion Objects:

One last thing that's worth mentioning is companion objects. In Java, you typically have classes that have some static content, but also some non-static / instance content. Kotlin allows you to do something similar with companion objects, which are objects tied to a class, meaning a class can access it's companion object's private functions and properties:

class ExampleClass {
  companion object {
    // Things that would be static in Java would go here in Kotlin
    private const val str = "asdf"
  }

  fun example() {
    // I can access private variables in my companion object
    println(str)
  }
}

Solution 2 - Java

A Kotlin object is like a class that can't be instantiated so it must be called by name. (a static class per se)

The android converter saw that your class contained only a static method, so it converted it to a Kotlin object.

Read more about it here: http://petersommerhoff.com/dev/kotlin/kotlin-for-java-devs/#objects

Solution 3 - Java

An object is a singleton. You do not need to create an instance to use it.

A class needs to be instantiated to be used

In the same way that in Java you may say Math.sqrt(2) and you dont need to create a Math instance to use sqrt, in Kotlin you can create an object to hold these methods, and they are effectively static.

There is some info here:

https://kotlinlang.org/docs/reference/object-declarations.html

IntelliJ has obviously been smart enough to detect you need an object since you only have static java methods.

Solution 4 - Java

Different between : object || class || companion object || data class

1.object

  • An object declaration, is initialised lazily, when accessed for the first time.
  • Object is act like singleton class
  • Only one reference for whole app
  • Access members, methods without create an instance

2.class

  • Multiple reference you can create
  • Need to create instance for access members, methods

3.companion object

  • A companion object is initialized when the corresponding class is loaded
  • In object MyClass{} by default whole variable have single reference but in companion object you have choice to create static method or to create static variable
  • You can create singleton class

4.data class

  • Classes that are used to hold data/state
  • Kotlin’s data classes, you don’t need to write/generate all the lengthy boilerplate code yourself
  • The compiler automatically generates a default getter and setter for all the mutable properties
  • The compiler automatically derives the implementation of standard methods like equals(), hashCode() and toString()

Examples

//---------------1- object ----------------------
object MyClass1 {
        fun checkData {
            // ...
        }
}

MyClass1.checkData()  // call method


//----------------2- class ---------------------
class MyClass2 {
        fun checkData {
            // ...
        }
}

var myClass = MyClass2()
myClass.checkData()  // call method



//----------------3- companion object ---------------------
class MyClass3 {
        companion object {
            fun myStaticMethod() {
                // ...
            }
        }

       fun myInstanceMethod() {
            // ...
        }
}
MyClass3.myStaticMethod() // call companion object member
var myClass = MyClass3()
myClass.myInstanceMethod()  // call simple method using reference

//----------------4- data class ---------------------
data class MyClass4(val name: String, val rId: Int)

Solution 5 - Java

Also you can define functions without object declaration. Just in .kt file For example:

fun GenerateChecksumCrc16(bytes: ByteArray): Int {
    ...
}

And this function was related to package where is .kt file is declared. You can read more about it here https://kotlinlang.org/docs/reference/packages.html

Solution 6 - Java

Building on @speirce7's answer:

The following code shows the basic difference between a Class and an Object when it comes to Kotlin:

class ExampleClass(){
    fun example(){
            println("I am in the class.")
    }
}

object ExampleObject{
    fun example(){
            println("I am in the object.")
    }
}

fun main(args: Array<String>){
    val exampleClass = ExampleClass() // A class needs to be instantiated.
    exampleClass.example()            // Running the instance of the object.
    ExampleObject.example()           // An object can be thought of as a Singleton and doesn't need any instantiation.
}

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionCrunchy234View Question on Stackoverflow
Solution 1 - Javaspierce7View Answer on Stackoverflow
Solution 2 - JavaHeadlineView Answer on Stackoverflow
Solution 3 - JavaBruce LoweView Answer on Stackoverflow
Solution 4 - JavaSanjayrajsinhView Answer on Stackoverflow
Solution 5 - JavaSilvestrView Answer on Stackoverflow
Solution 6 - JavaRajView Answer on Stackoverflow