静态和非静态成员数据初始化和构造函数顺序

时间:2017-02-01 11:36:45

标签: java static

我是Java的初学者,当在类的定义中有静态成员时,他坚持使用简单的数据初始化和构造函数调用。

代码:

class Bowl {
    Bowl(int marker) {
        System.out.println("Bowl(" + marker + ")");
    }
    void f1(int marker) {
        System.out.println("f1(" + marker + ")");
    }
}
class Table {
    static Bowl bowl1 = new Bowl(1);
    Table() {
        System.out.println("Table()");
        bowl2.f1(1);
    }
    void f2(int marker) {
        System.out.println("f2(" + marker + ")");
    }
    static Bowl bowl2 = new Bowl(2);
}
class Cupboard {
    Bowl bowl3 = new Bowl(3);
    static Bowl bowl4 = new Bowl(4);
    Cupboard() {
        System.out.println("Cupboard()");
        bowl4.f1(2);
    }
    void f3(int marker) {
        System.out.println("f3(" + marker + ")");
    }
    static Bowl bowl5 = new Bowl(5);
}
class StaticInitialization {
    public static void main(String[] args) {
        System.out.println("Creating new Cupboard() in main");
        new Cupboard();
        System.out.println("Creating new Cupboard() in main");
        new Cupboard();
        table.f2(1);
        cupboard.f3(1);
    }
    static Table table = new Table();
    static Cupboard cupboard = new Cupboard();
}

输出:

Bowl(1)
Bowl(2)
Table()
f1(1)
Bowl(4)
Bowl(5)
Bowl(3)
Cupboard()
f1(2)
Creating new Cupboard() in main
Bowl(3)
Cupboard()
f1(2)
Creating new Cupboard() in main
Bowl(3)
Cupboard()
f1(2)
f2(1)
f3(1)

我无法理解代码的流程,并且书中没有太多解释,除了静态成员在之前和必要时尚未初始化时初始化。 任何线索?

1 个答案:

答案 0 :(得分:3)

当您的计划开始时,

1) StaticInitialization 类被加载到内存中,其静态字段首先按照描述的顺序进行初始化

2)初始化静态字段,这就是为什么类被加载到内存中并且所有静态字段都被初始化的原因。

3)初始化静态字段 bowl1 ,这就是为什么 Bowl 类被加载到内存中但没有静态字段的原因,因此构造函数被调用并且打印碗(1)

4)静态字段 bowl2 已初始化,但 Bowl 类已加载,因此只需调用其构造函数并打印 Bowl(2)

5)调用构造函数,打印 Table()并调用方法 f1(1)

6) StaticInitialization 类中的静态字段橱柜被初始化,这就是为什么 Cupboard 类被加载到内存和所有它的静态字段已初始化。

7)静态字段 bowl4 已初始化,但 Bowl 类已加载,因此调用 Bowl 构造函数并打印 Bowl (4)

8)与 bowl5 静态字段相同。

9)然后,在初始化Cupboard的所有静态字段之后,初始化类成员,即 bowl3 字段。所以,调用 Bowl 构造函数并打印 Bowl(3)

10) Cupboard 构造函数被调用,打印 Cupboard()并调用 f1(2)方法

11)主要方法开始工作。打印创建... 并创建新的橱柜对象,以便初始化橱柜的班级成员。也就是说, bowl3 字段在这个新对象中被初始化并且它的构造函数被调用,因此打印 Bowl(3)

12)调用这个新的 Cupboard 对象的构造函数,打印 Cupboard()并调用 f1(2) 的方法> bowl3 对象

13)重复步骤11和12。 (主要打印创建... 并创建新的橱柜对象)

14) f2(1) f3(1)方法在不同的对象上被逐个调用

  

请记住,静态字段在类中初始化一次   加载到内存中,默认情况下会初始化类成员   该对象已创建。