Java 子类构造函数继承成员

Java subclass constructor inherited member

我有一个问题,为什么这段代码在执行时会打印出值 0。我不完全理解 SubClass 构造函数中发生了什么,以及为什么当我擦除被覆盖的方法 implicitValue,它打印出 10. SubClass 构造函数是否使用 SuperClass 构造函数? 谢谢你。

class SuperClass {
    protected int superClassValue;

    public SuperClass() {
        superClassValue = implicitValue();
    }

    public int implicitValue() {
        return 10;
    }

    public int getValue() {
        return superClassValue;
    }
}

class SubClass extends SuperClass {
    private int subClassValue;

    public SubClass() {
        subClassValue = 20;

    }

    public int implicitValue() {
        return subClassValue;

    }
}

class Example {
    public static void main(String argv[]) {
        SubClass ss = new SubClass();
        System.out.println("The value is " + ss.getValue());

    }
}

听起来你的 Override 方法或 subclass 有问题。因为它听起来像是在实现一个变量时,该值没有被实例化,所以它默认为 0,然后当您删除它时,超级 class 接管导致您获得值 10.

是的,如果未明确给出此类调用,子类构造函数将隐式调用超类构造函数。但它打印 0 因为 implicitValue 方法在 SubClass.

中被覆盖了
  1. 调用超类构造函数。在这里,创建了对象的 SuperClass 部分。所有变量都被初始化。因为没有给出明确的值,所以编译器给出了 superClassValue 默认值 0。然后超类构造函数调用 implicitValue(),它调用子类的方法。此方法 returns superClassValue,它被初始化为 0。此值明确分配回 superClassValue.
  2. 子类将其subClassValue初始化为10
  3. 调用getValue()方法,returns superClassValue,即0The value is 0 被打印出来。

如果您要删除 SubClass 中的 implicitValue 方法,那么它将继承 SuperClass 的方法版本,即 returns 10.

如果您将SubClass中的implicitValue方法修改为return5,那么它会将superClassValue初始化为5 , 它会打印 The value is 5.

TL;DR

问题是 SubClass 中的 implicitValue 被 superclass 隐式超类构造函数(super())通过 implicitValue() 方法使用,在 [=23 之前=] 将在 SubClass 构造函数中执行,因此它 return 的 subClassValue 默认值 int 字段是 0.


Does the SubClass constructor make use of the SuperClass constructor?

是的,启动时的 subclass 构造函数总是调用 superclass 构造函数,所以代码

public SubClass() {
    subClassValue = 20;
}

相同
public SubClass() {
    super();//superclass constructor
    subClassValue = 20;
}

但让我们看看您的代码。您正在打印 superclass

中存在的 getVlaue() 方法的结果
public int getValue() {
    return superClassValue;
}

如您所见,return 是 superClassValue 的值。在调用 getVlaue() 之前,您正在创建 ss 实例,因此您正在调用代码

super();//superclass constructor
subClassValue = 20;

这意味着你正在调用 superclass 的构造函数,它看起来像

public SuperClass() {
    superClassValue = implicitValue();
}

所以 this.superClassValue 使用 implicitValue() 方法的 returned 值初始化,但是由于 dynamic binding (后期绑定)JVM 将尝试搜索此方法的实现方法从 this 的实际 class 开始,即 SubClass,并且由于此 class 有其自己的覆盖版本,它将被调用

public int implicitValue() {
    return subClassValue;
}

但是 subClassValue 还没有设置任何东西

super();// <-- we are still here
subClassValue = 20;// this line was not executed yet

所以subClassValue仍然有它的默认值0,这意味着

superClassValue = implicitValue(); //will be initialized with 0;

所以

public int getValue() {
    return superClassValue;
}

将 return 0.

  1. 在您的情况下:默认情况下将调用 SuperClass 构造函数。

  2. new SubClass() 的逻辑。

它会先调用SuperClass的构造函数。当调用 SuperClass 的构造函数时 - 来自 implicitValue() 的值 return 将分配给变量 superClassValue - 被调用的方法 implicitValue() 是子类的方法(不是 implicitValue() 的如你所想的 SupperClass - OOP 的多态特性)。

调用SubClass的implicitValue()时,subClassValue域还没有初始化,所以subClassValue域仍然是0。这就是您在输出中看到零的原因。

  1. 当您从子类中删除重写隐式值时。被调用的 implicitValue() 是 SupperClass 的 implicitValue() --> 这就是您在输出中看到 10 的原因。