AN0*_*N00 3 java binding casting subclass superclass
我已经实现了以下代码,以便了解静态和动态绑定之间的区别:
class A {
int met(A a) {
return 0;
}
int met(B b) {
return 1;
}
int met(C c) {
return 2;
}
}
class B extends A {
int met(A a) {
return 3;
}
int met(B b) {
return 4;
}
int met(C c) {
return 5;
}
}
class C extends B {
int f() {
return ((A)this).met((A)this);
}
}
public class Test {
public static void main(String[] args) {
C x = new C();
System.out.println(x.f());
}
}
Run Code Online (Sandbox Code Playgroud)
我得到的结果是3,但我不明白为什么,因为第一次演员是为了A.
那么,让我们来看看电话:
((A)this).met((A)this);
Run Code Online (Sandbox Code Playgroud)
这相当于:
A target = this;
A argument = this;
target.met(argument);
Run Code Online (Sandbox Code Playgroud)
因此,对于最后一行,编译器根据所涉及的编译时类型查找签名 - 它将查找A(和超类)一个被调用的方法,该方法met具有与之兼容的参数A(编译时类型的参数).重载决议发现答案是:
int met(A a)
Run Code Online (Sandbox Code Playgroud)
这是在编译时确定的签名.但是,该方法的实现是在执行时根据方法调用的执行时间目标确定的.这种类型在C这里 - 因为this是对实例的引用C.(该f方法在.的实例上调用C.)
现在C不覆盖int met(A a),但B(它的超类)确实 - 所以这是使用的实现.B 同样覆盖met(B b)并且met(C c)因为编译器已经确定它met(A a)是被调用的方法也没关系.