关于Java构造函数和类成员初始化的一个问题

关于Java构造函数和类成员初始化的一个问题,java,constructor,Java,Constructor,我试图理解为什么以下Java代码的输出是这样的: class A { public A() { System.out.print("A()"); } public static void main(String[] args) { } } class B { public B() { System.out.print("B()"); } public static

我试图理解为什么以下Java代码的输出是这样的:

class A {
    public A() {
        System.out.print("A()");
    }
    public static void main(String[] args) {

    }
}
class B {
    public B() {
        System.out.print("B()");
    }

    public static void main(String[] args) {}
}
class C extends A {
    B b = new B();
}

public class E05SimpleInheritance {
    public static void main(String args[]) {
        new C();
    }
}
输出:

"A()B()"
我可以想象,当调用E05SimpleInheritance公共类的主方法时,应该会发生以下事情

在调用类C的默认构造函数之前,将加载非公共类C并初始化其字段 由于其成员“b”是类b的对象,因此类b被加载到内存中 由于我们构造了一个类B的对象,它的构造函数被称为 调用C的默认构造函数,它会自动调用打印A的超类A的构造函数
所以最终的输出应该是BA,这显然是错误的,所以我并不真正理解在这种情况下代码是如何流动的。你能告诉我为什么打印AB而不是BA吗?你的错误在第一步:

在调用类C的默认构造函数之前,将加载非公共类C并初始化其字段

事情不是这样的。实际上,非静态字段是在构造函数的开头初始化的,而不是在构造函数之前。甚至在此之前,基类构造函数也被隐式或显式调用

换句话说,javac为C生成代码,相当于以下内容:

class C extends A {
    B b;

    C() {
        super();
        b = new B();
    }
}

您的错误在步骤1中:

在调用类C的默认构造函数之前,将加载非公共类C并初始化其字段

事情不是这样的。实际上,非静态字段是在构造函数的开头初始化的,而不是在构造函数之前。甚至在此之前,基类构造函数也被隐式或显式调用

换句话说,javac为C生成代码,相当于以下内容:

class C extends A {
    B b;

    C() {
        super();
        b = new B();
    }
}

这回答了你的问题吗?这回答了你的问题吗?