在以下代码示例中:
class Parent {
int x =5;
public Integer aMethod(){
System.out.print("Parent.aMthod ");
return x;
}
}
class Child extends Parent {
int x =6;
public Integer aMethod(){
System.out.print("Child.aMthod ");
return x;
}
}
class ZiggyTest2{
public static void main(String[] args){
Parent p = new Child();
Child c = new Child();
System.out.println(p.x + " " + c.x);
System.out.println(p.aMethod() + " \n");
System.out.println(c.aMethod() + " \n");
}
}
输出:
5 6
Child.aMthod 6
Child.aMthod 6
当p.x打印6时,为什么p.aMethod()
不能打印6?
谢谢
哎呀一个小错字:问题应该是“为什么p.aMethod()在p.x打印5时不打印5” - 谢谢@thinksteep
答案 0 :(得分:12)
访问像p.x
这样的类成员字段(实例变量)时,没有进行多态解析。换句话说,您将从编译时已知的类中获得结果,而不是运行时已知的类。
对于方法调用,这是不同的。它们在运行时被分派到引用指向的实际类的对象,即使引用本身具有超类型。 (在VM中,这通过invokevirtual
操作码发生,请参阅例如http://java.sun.com/docs/books/jvms/second_edition/html/Instructions2.doc6.html#invokevirtual)。
答案 1 :(得分:1)
操作始终在对象上。在这两种情况下,p.aMethod()
和c.aMethod()
,对象都是孩子,这就是为什么它在两种情况下都打印了6。直接访问变量时,它会读取与左侧相关的变量。
答案 2 :(得分:0)
因为声明变量不会继承。您在类中有两个x副本,一个在父命名空间中,一个在子命名空间中。