本文主要探讨在一条继承链(比如说A派生出子类B,B又派生出子类C······)上各种变量的赋值语句,初始化块和构造方法的执行顺序。先说结论:
按顺序分成两个阶段:
一、类加载后进行的初始化(只进行一次,以后实例化对象不需要重新进行类的初始化)
按照继承链从父类到子类的顺序,依次执行每一个类中静态成员变量的赋值语句和静态初始化块
二、实例化对象
按照继承链从父类到子类的顺序,依次执行每一个类中,成员变量的赋值语句和初始化块,然后才执行这个类的构造方法(注意:同一个类中,构造方法的优先级比成员变量的赋值语句和初始化块低)
参见代码:
package initialization;
public class InitializeClassObject {
public static void main(String[] args) {
System.out.println("====初始化第一个B类对象====");
new B();
System.out.println("\n====初始化第二个B类对象====");
new B();
}
static class MyLog{ //赋值语句执行时打印提示信息
public MyLog(String mes){
System.out.println(mes);
}
}
static class A{
public A() {
System.out.println("构造方法A()定义在最前面");
}
{
System.out.println("A {} 1");
}
static {
System.out.println("A static {} 1");
}
MyLog varA = new MyLog("给成员变量varA赋值");
public static MyLog staA = new MyLog("给静态变量staA赋值");
static {
System.out.println("A static {} 2");
}
{
System.out.println("A {} 2");
}
}
static class B extends A{
static {
System.out.println("B static {}");
}
public B() {
System.out.println("构造方法B()");
}
}
}
运行结果:
====初始化第一个B类对象====
A static {} 1
给静态变量staA赋值
A static {} 2
B static {}
A {} 1
给成员变量varA赋值
A {} 2
构造方法A()定义在最前面
构造方法B()
====初始化第二个B类对象====
A {} 1
给成员变量varA赋值
A {} 2
构造方法A()定义在最前面
构造方法B()