我有一个关于方法重写协方差的询问.. 假设我们有两个类,如下所示:
class Parent {
Object getSomething(){
return 10;
}
}
class Child extends Parent {
Integer getSomething() {
return 10;
}
}
class TestCovariance {
public static void main(String[] args) {
Child c = new Child();
Parent p = new Child();
Integer i1 = c.getSomething(); //this is ok
Integer i2 = p.getSomething(); //this one gives a runtime exception
}
}
正如您在给出运行时异常的那行注释中看到的,异常详细信息:
Exception in thread "main" java.lang.RuntimeException: Uncompilable source code - incompatible types: java.lang.Object cannot be converted to java.lang.Integer
为什么c
对象的方法返回一个Integer
,而p
对象的方法返回一个Object
??
最佳答案
首先,我想重申协变返回类型是将重写方法的返回类型更改为被重写方法的子类型的能力返回类型在您的情况下似乎是正确的。
对 Integer i1 = c.getSomething();
的调用编译成功,因为接收者类型为 Child
并且编译器知道 的返回类型c.getSomething()
是 Integer
。
然而,另一方面,由于您使用 Parent
作为 p
的接收者类型,因此只有 Parent< 的方法
类通过此引用可见,即使实际对象 p
引用的是一个 Child
并且显然是 p.getSomething ()
假定在编译时返回 Object
,而您尝试将其分配给 Integer
,因此会出现编译错误。
话虽如此,调用Integer i2 = p.getSomething();
可能在运行时成功,但正如前面提到的,这是一个编译时错误,因为编译器会检查并确保您只调用接收器类型存在的方法。
正如 davidxxx 所提到的:
the RuntimeException is thrown but it is not thrown by the program itself but the IDE as it "discovers" that the started program has a uncompilable class.
关于Java方法重写协方差查询,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47762148/