伴生对象(companion object)与静态成员的模拟
1. 伴生对象的基本概念
在 Kotlin 中,伴生对象(companion object) 是一个与类关联的特殊对象,用于模拟 Java 中的静态成员(静态方法和静态属性)。每个类只能有一个伴生对象,其名称可以省略(默认为 Companion),也可以自定义。
语法示例
class MyClass {
companion object {
const val CONSTANT_VALUE = 100 // 静态常量
fun staticMethod() { // 静态方法
println("This is a static method.")
}
}
}
2. 伴生对象的特点
- 单例性:伴生对象是类的静态成员,全局唯一。
- 直接通过类名访问:无需实例化类即可调用伴生对象的成员。
- 可继承接口:伴生对象可以实现接口,扩展功能。
调用方式
MyClass.CONSTANT_VALUE // 访问静态常量
MyClass.staticMethod() // 调用静态方法
3. 伴生对象 vs Java 静态成员
| 特性 | Kotlin 伴生对象 | Java 静态成员 |
|---|---|---|
| 定义方式 | 通过 companion object 块 | 使用 static 关键字 |
| 成员访问 | 通过类名直接访问 | 通过类名直接访问 |
| 支持接口实现 | 是 | 否 |
| 运行时类型 | 是真实对象(可赋值给变量) | 无对象实例 |
4. 实际应用场景
4.1 工厂模式
class User private constructor(val name: String) {
companion object {
fun create(name: String): User {
return User(name)
}
}
}
// 使用
val user = User.create("Alice")
4.2 常量定义
class Config {
companion object {
const val API_URL = "https://api.example.com"
}
}
4.3 实现接口
interface Logger {
fun log(message: String)
}
class MyService {
companion object : Logger {
override fun log(message: String) {
println("[LOG] $message")
}
}
}
// 调用
MyService.log("Service initialized")
5. 注意事项
- 性能影响:伴生对象是真实对象,首次访问时会初始化,但开销极小。
- JVM 注解:如需在 Java 中像调用静态方法一样使用,可用
@JvmStatic注解:companion object { @JvmStatic fun utilityMethod() { ... } } - 命名伴生对象:调用时可通过
companion object Named { // ... }MyClass.Named.method()访问。
6. 总结
Kotlin 的伴生对象提供了比 Java 静态成员更灵活的功能,同时保持了相似的调用方式。它是实现工具方法、常量定义和工厂模式的理想选择,同时支持面向对象的高级特性(如接口实现)。
