首页 > 解决方案 > 继承中如何初始化父子字段?

问题描述

我面临着一种困惑。

这是我的小代码片段

public class Father {

    public String x;

    public Father() {
        this.init();
        System.out.println(this);
        System.out.println(this.x);
    }

    protected void init() {
        x = "Father";
    }

    @Override
    public String toString() {
        return "I'm Father";
    }

    void ParentclassMethod(){

        System.out.println("Parent Class");
    }

}


public class Son extends Father {
    public String x;


    @Override
    protected void init() {
        System.out.println("Init Called");

        x = "Son";
    }

    @Override
    public String toString() {
        return "I'm Son";
    }

    @Override
    void ParentclassMethod(){
        super.ParentclassMethod();
        System.out.println("Child Class");
    }

}

public class MainCLass{

    public static void main(String[] args){

        Son ob = new Son();

}

所以当我创建一个继承自父类的子类实例时,JVM会自动调用父类的构造函数。当父亲的构造函数被调用时,它会创建 Son 类型实例,否则父亲的字段不会被初始化。到目前为止好..!

如您所见,字段x是从父亲的类派生到儿子的类中的。我的代码x使用init()方法初始化。

那为什么它显示为空。

它非常混乱。谁能解释一下?

标签: javainheritance

解决方案


Java中的变量不是多态的。x由于您在 inside重新声明Son,因此该变量实际上与 in 中的变量不同 。所以在 of 的方法中,你正在初始化's ,而不是' s 。xFatherinitSonSonxFatherx

另一方面,您的语句System.out.println(this.x);Father类内,因此它只知道Father's x。由于重写该init方法,您不再初始化此变量,因此xinFather保留null(默认),因此它将打印null.

您可以通过public String x;Son班级中删除来解决问题。这将使Father'sx唯一的x,消除问题。

但是,通常,您希望使用此变量private而不是public. 你也不应该final在构造函数中调用非方法。它只能引入错误。在这种情况下,初始化它的正确方法是使用带有 in 参数的构造函数Father

public class Father {
    private String x;

    protected Father(String x) {
        this.x = x;
        System.out.println(this);
        System.out.println(this.x);
    }

    public Father() {
        this("Father");
    }

    // Rest of father's code, without the init method
}

public class Son extends Father {
    public Son() {
        super("Son");
    }

    // Rest of son's code, without the init method
}

推荐阅读