[英]What does it happen when a superclass reference which is assigned to an object of subclass invokes an overriding method?
这是代码:
class Override {
public static void main(String[] args) {
A a = new A(1, 2);
A a1 = new B(1, 2, 3);
B b = new B(4, 5, 6);
a.show();
a1.show();
b.show();
}
}
class A {
int a;
int b;
A(int a, int b) {
this.a = a;
this.b = b;
}
void show() {
System.out.println(a + " " + b);
}
}
class B extends A {
int c;
B(int a, int b, int c) {
super(a, b);
this.c = c;
}
void show() {
System.out.println(c);
}
}
Restult:
1 2
3
6
可以将超类的引用变量分配给从该超类派生的任何子类的对象。 引用变量的类型确定可以访问的成员。
基于上述事实,a1无法访问c(B的成员),因为a1不知道B中存在任何成员。我的问题是a1调用show()时,为什么B中的show()是被调用而不是A?
谢谢大家的回答。
我认为这很有趣:
动态方法分派是一种在运行时解决对覆盖方法的调用的机制。 当通过超类引用调用重写的方法时,java根据调用发生时所引用的对象的类型来确定要执行该方法的版本。
因为B
已覆盖的方法show()
的show()
在B
被调用。 考虑一个abstract
方法,如果B
无法替换该抽象方法,它将永远无法实现(同样使用接口)。
abstract void show();
最后,如果该方法不应该被重写,则将其设为private
。 默认的访问级别是继承的。
因为您的class B
覆盖了show()
方法。 仅当继承者没有覆盖超类方法时,才使用超类方法。
来自B的函数将被调用。 这种机制称为“虚拟功能”。 如果子类覆盖基类中的函数,则程序将在运行时搜索正确的函数,并为正确的类型(B而不是A)调用该函数。 在Java中,所有功能都是虚拟的。
但是您的问题是正确的,尽管,在C ++和C#中,这些函数默认情况下不是虚函数,如果未将它们显式声明为虚函数,则将调用A中的函数(等效于C ++ / C#代码);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.