类扩展了另一个问题?

时间:2016-02-04 18:15:54

标签: java

我正在学习Java,我在这里感到困惑:这段代码究竟是如何工作的?

class A
{
    int n = 9;

    void show()
    {
        System.out.println(n);
    }
}

class B extends A 
{
    void show()
    {
        System.out.println(n+" "+super.n+" "+a.n);
    }

    int n = 4;
    static A a = new A();

    public static void main(String[] args)
    {
        B b = new B();
        a.show();//9, expected
        a = b;
        /*Line A*/ a.show();//4 9 9
        /*Line B*/ b.show();//4 9 9
    }
}

在A行中,将调用B中的函数,这是预期的。但为什么要打印4 9 9?

3 个答案:

答案 0 :(得分:2)

您将b放入a,但b始终保留B Class - 背景中的对象。

你可以像这样打印出来:

/*Line B*/ b.show();//4 9 9
System.out.println(a.getClass());

引用来自类型A,但堆上的对象是相同的b对象。

答案 1 :(得分:2)

排队

else

静态变量a = b; 设置为a 的实例。这是可能的,因为B继承自B

因此,系列调用来自班级A的方法show(),而不是B

有关详细信息,请搜索material on Polymorphism

答案 2 :(得分:1)

在A行中,我们实际上是在.show()类型的引用上调用方法class A。这里class Bclass A的子类。在Java中,父类引用可以指向子类对象。

当JVM看到这个调用时,它实际上会检查引用实际指向的对象。在我们的例子中,它指向类型为class B的子类对象。此处,show方法也在class B中声明。这意味着,它成功地覆盖了父方法。当JVM看到它时,它实际上调用子类方法而不是父类。整个过程称为polymorphism