繁体   English   中英

Java子类构造函数继承的成员

[英]Java subclass constructor inherited member

我有一个问题,为什么这段代码在执行时为什么会打印出0值。我不完全了解SubClass构造函数中发生的情况,为什么在擦除覆盖的方法hiddenValue时会打印出该值呢? out 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());

    }
}

TL; DR

问题是, implicitValueSubClass所使用的超类隐式超类构造( super()通过) implicitValue()方法,前subClassValue = 20; 将在SubClass构造函数中执行,因此它返回subClassValue默认值,其中int字段为0


SubClass构造函数是否使用SuperClass构造函数?

是的,子类构造函数在开始时始终会调用超类构造函数,因此代码

public SubClass() {
    subClassValue = 20;
}

与...相同

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

但是,让我们看看您的代码。 您正在打印超类中存在的getVlaue()方法的结果

public int getValue() {
    return superClassValue;
}

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

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

这意味着您正在调用超类的构造函数,如下所示

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

所以this.superClassValue被初始化的返回值implicitValue()方法,但由于动态绑定 (后期绑定)JVM将尝试寻找实现这种方法从实际的类的开始的thisSubClass ,由于该类有其自己的覆盖版本,它将被调用

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;
}

将返回0

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

  1. 超类构造函数被调用。 在这里,创建了对象的SuperClass部分。 所有变量均已初始化。 因为没有给出显式值,所以编译器将superClassValue的默认值设置为0 然后,超类构造函数将调用implicitValue() ,后者将调用子类的方法。 该方法返回已初始化为0 superClassValue 该值被明确分配回superClassValue
  2. 子类将其subClassValue初始化为10
  3. 调用getValue()方法,并返回superClassValue ,该值为0 The value is 0

如果要删除implicitValue的方法SubClass ,那么它会继承SuperClass的方法,该方法返回的版本10

如果要修改implicitValue的方法SubClass返回5 ,那么它会初始化superClassValue5 ,这将打印The value is 5

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

  2. 在Java进程中:new SubClass()。 它将首先调用SuperClass的构造函数。 调用SuperClass的构造方法时-将从hiddenValue()返回的值分配给superClassValue-调用的隐含值()方法是SubClass的方法(如您所想的那样调用SupperClass的NOT hiddenValue()-OOP的多态性功能) 。 调用SubClass的implicitValue()时,subClassValue尚未初始化(subClassValue = 20;尚未运行),因此subClassValue仍为零。 这就是在输出中看到零的原因。

  3. 当您删除SubClass中的override hiddenValue时。 被调用的implicitValue()是SupperClass的implicitValue->这就是为什么您在输出中看到10的原因。

听起来您的Override方法或子类有问题。 因为这听起来像是在实现变量时未实例化该值,所以它默认为0,然后在删除它时,超类将接管,从而得到值10。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM