Sling Academy
Home/Kotlin/Static-Like Behavior with Companion Objects in Kotlin

Static-Like Behavior with Companion Objects in Kotlin

Last updated: November 30, 2024

Understanding Static-Like Behavior with Companion Objects in Kotlin

Kotlin is a modern programming language that runs on the Java Virtual Machine (JVM) and is fully interoperable with Java. One of its notable features is its object-oriented nature, which makes programming intuitive for those well-versed in classes and objects. However, something that Kotlin intentionally avoids is true static members or methods in classes, unlike Java. Instead, Kotlin offers a unique construct known as companion objects to achieve similar functionality.

What Are Companion Objects?

Companion objects are defined within a class and provide a way to call methods and access properties similarly to static members in Java, without requiring an instance of a class.


class MyClass {
    companion object {
        fun sayHello() {
            println("Hello from the companion object!")
        }
    }
}

fun main() {
    // Call the companion object's method without creating an instance
    MyClass.sayHello()
}

In the example above, the sayHello() function within the companion object can be called directly through the class name MyClass.sayHello() without the need for an instance of MyClass.

Setting Static-Like Properties

Companion objects can also contain properties that behave similarly to static properties in Java.


class Counter {
    companion object {
        var count = 0
        fun increment() {
            count++
        }
    }
}

fun main() {
    // Access and modify the companion object property directly
    println(Counter.count) // Prints: 0
    Counter.increment()
    println(Counter.count) // Prints: 1
}

Here we see that count can be accessed and modified directly using the class name. This mimics the behavior of static fields in Java.

Naming Companion Objects

While the name of the companion object is implicit by default, designers can assign a custom name to enhance clarity and code readability.


class Calculator {
    companion object Operations {
        fun add(a: Int, b: Int): Int {
            return a + b
        }
    }
}

fun main() {
    // Access using the specified companion object name
    val sum = Calculator.Operations.add(5, 10)
    println(sum) // Prints: 15
}

In this modified example, we've named the companion object Operations and referenced it directly.

Conclusion

In Kotlin, companion objects fill the role of static members from Java while following the language's object-oriented principles. By leveraging companion objects, developers can craft clean, logically organized code without sacrificing direct class-level functionality found in other languages. Always remember, while they are similar to statics, companion objects in Kotlin provide an instance-related, yet class-environment scope, thus helping maintain encapsulation and clarity in codebase organization.

Next Article: How to Use Nested and Inner Classes in Kotlin

Previous Article: Using Backing Fields (`field`) in Kotlin

Series: Kotlin Object-Oriented Programming

Kotlin

You May Also Like

  • How to Use Modulo for Cyclic Arithmetic in Kotlin
  • Kotlin: Infinite Loop Detected in Code
  • Fixing Kotlin Error: Index Out of Bounds in List Access
  • Setting Up JDBC in a Kotlin Application
  • Creating a File Explorer App with Kotlin
  • How to Work with APIs in Kotlin
  • What is the `when` Expression in Kotlin?
  • Writing a Script to Rename Multiple Files Programmatically in Kotlin
  • Using Safe Calls (`?.`) to Avoid NullPointerExceptions in Kotlin
  • Chaining Safe Calls for Complex Operations in Kotlin
  • Using the Elvis Operator for Default Values in Kotlin
  • Combining Safe Calls and the Elvis Operator in Kotlin
  • When to Avoid the Null Assertion Operator (`!!`) in Kotlin
  • How to Check for Null Values with `if` Statements in Kotlin
  • Using `let` with Nullable Variables for Scoped Operations in Kotlin
  • Kotlin: How to Handle Nulls in Function Parameters
  • Returning Nullable Values from Functions in Kotlin
  • Safely Accessing Properties of Nullable Objects in Kotlin
  • How to Use `is` for Nullable Type Checking in Kotlin