在下面的精简示例中,您能否解释为什么 Kotlin 编译器在覆盖 a 时提示我们进一步限制其类型(编译器消息:Var-property type is 'B',这不是覆盖类型公共(public)抽象变量 a: A
)
interface A
interface B : A {
fun someFunc():Boolean
}
class C : B {
override fun someFunc(): Boolean {
return true
}
}
abstract class D {
abstract var a: A
}
class E : D() {
override var a : B = C()
fun otherFunc() {
println(a.someFunc())
}
}
此外,编译器不会提示以下片段:
open class G
class H : G()
abstract class F {
abstract val g: G
}
class I : F() {
override var g : H = H()
}
所以我想接口(interface)继承会发生一些事情,而类不会发生这种情况。
最佳答案
您的第一个代码片段无法编译,否则可能会出现这样的怪异现象:
val d: D = E()
d.a = object : A {} // Some other sub-type of A, but definitely not a sub-type of B
这实际上是 lack of method parameter covariance in Java 的变体(没有双关语意) - 特别是考虑到 Kotlin var
属性实际上只是 getter 和 setter 方法的语法糖。
相反,您的第二个代码段会编译,因为在这种情况下,协方差不是问题 - 基类 (F
) 中没有要覆盖的 setter,所以我上面描述的“怪异”是不可能的。
关于inheritance - Kotlin 属性不能被子接口(interface)覆盖,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47643545/