jvm 为什么Kotlin中的变量可以被覆盖,而在Java中,它们不能?

xv8emn3q  于 4个月前  发布在  Kotlin
关注(0)|答案(2)|浏览(64)

在java中,变量不能被覆盖,只能被隐藏。而在Kotlin中,我们可以覆盖变量。
虽然它们都运行在JVM上,但为什么会有这种区别呢?是因为Kotlin中的变量并没有被覆盖,而是只有默认的getter被覆盖了吗?我的理解正确吗?

Kotlin代码:

open class Animal {
    open var name: String = "Animal"
}

class Dog : Animal() {
    override var name: String = "Dog"
}

fun main() {
    val animal: Animal = Dog()
    println(animal.name) // Output: Dog
}

字符串

Java代码:

class Animal {
    String name = "Animal";
}

class Dog extends Animal {
    String name = "Dog";
}

public class Main {
    public static void main(String[] args) {
        Animal animal = new Dog();
        System.out.println(animal.name); // Output: Animal
    }
}

j91ykkif

j91ykkif1#

原因是Java中的String name = "Animal";和Kotlin中的open var name: String = "Animal"不一样,这就是为什么前者的结构叫做 field,后者叫做 property
默认情况下,Kotlin中的非私有 var 属性实际上是一个私有字段,在Java级别上具有非私有getter和setter(您可以在单击 Tools ->Kotlin-> ShowKotlinBytecode 然后单击 Decompile 后看到它,如下面的屏幕截图所示)。
x1c 0d1x的数据
因此,您实际上覆盖了它的getter和setter,而不是字段本身。如果您创建了一个 JavaCat,则只能覆盖相应的方法。

ctzwtxfj

ctzwtxfj2#

首先,Kotlin代码和Java代码在运行时的行为是相同的,所以唯一的区别是编码风格。
Kotlin强制你声明你正在重写属性(如注解中所述,实际上是getter),而Java没有。这是唯一的区别;Kotlin更严格,使你重写的东西很明显(例如,使事情开放并使用override关键字),而在Java中,这有点免费,狂野的西部方法。
在Java中有OverRide注解,但它不是强制性的。

相关问题