The :: symbol in Kotlin addresses specific syntax needs. We’ve seen that functions are first-class citizens, but getting a function reference is different from Python or JavaScript. In Kotlin, we use ::. This might be because Kotlin allows invoking functions without parentheses in some cases, making it tricky to determine if a reference or invocation is intended.
Function References. To use an existing function elsewhere, get its reference using ::.
|
|
The Kotlin compiler generates a singleton class implementing the relevant “Function Type Interface” (here, kotlin.jvm.functions.Function2), which calls the sayHi
function through its invoke
method.
You can invoke the function reference directly. In this case, no “Function object” is needed, so no class is created; the generated bytecode is the same as a direct function call:
|
|
Method References. We can obtain references to methods. When retrieved from a class, it’s an Unbound Method Reference (requiring the receiver as the first parameter during invocation). When retrieved from an instance, it’s a Bound Method Reference.
Here’s an example of Unbound Method References:
|
|
The compiler generates a Singleton class implementing the Function2 interface. Its invoke
method accepts two parameters, using the first as the receiver to call format
.
Direct invocation of method references is also possible, avoiding new class creation and behaving like a regular call:
|
|
Now, an example of Bound Method References:
|
|
A new class is created with a property referencing the receiver. The invoke
method takes a string and uses the receiver to invoke format
.
Constructor references are obtained using ::ClassName
(e.g., myFn = ::ClassName
). This creates a new singleton class. Since Kotlin doesn’t use “new” for instantiation, this reference acts as a factory, similar to Python.
|
|
We can also obtain bound and unbound references to properties. This explanation is similar to Callable References" documentation., with different examples and insights into the compiler’s actions.
Another use of :: is getting an object (KClass instance) with class information. We can obtain this directly from the class (Person::class
) or an instance (myPerson::class
). Note that a KClass is not a Python metaclass; it only holds class information, unlike a metaclass which is involved in class creation (a concept absent in Kotlin).