類繼承鏈上的初始化(屬性和靜態程式碼塊的執行順序)
阿新 • • 發佈:2021-02-19
類的初始化順序
類的初始化:在類連結的準備階段時,類屬性會被賦予預設值;類連結階段之後,類屬性賦值和靜態程式碼塊才會被執行(類初始化)。
現在探究 類繼承鏈上的類屬性賦值和靜態程式碼塊的執行順序 ?
預期瞭解
- 初始化順序,靜態程式碼塊和靜態屬性(按自上而下的排列順序);
- 如果父類沒有被初始化,就會先初始化父類,初始化完父類,才會輪到自己;
注:
- 由 final 修飾的靜態屬性,只有使用 new 關鍵字賦值, 才會觸發類的初始化(只是屬性特例,方法沒影響)
// new 關鍵字 觸發 類的初始化
static final Object obj = new Object ();
// 不觸發 類的初始化
static final int count = 1;
- 靜態內部類的初始化 不會 觸發外部類的初始化
測試
注:測試類 必須另外 建立,因為 JVM 會首先載入和初始化 主類(有 main 方法的類)
public class Children extends Parent{
// 靜態程式碼塊
static {
System.out.println("初始化子類的靜態程式碼塊");
}
// 普通靜態屬性
public static Option2 option = new Option2 ();
// final 靜態屬性
// 使用 new 關鍵字
public static final Object newFinalObj = new Object();
// 不是用 new 關鍵字
public static final int finalCount = 1;
// 普通靜態方法
public static String test1(){
System.out.println("呼叫子類的 普通靜態方法");
return "";
}
// final 靜態方法
public static final String finalMethod(){
System.out.println("呼叫子類的 final的靜態方法");
return "";
}
static class StaticInClass{
public static Option1 option = new Option1();
// final 靜態屬性
// 使用 new 關鍵字
public static final Object newFinalObj = new Object();
// 不是用 new 關鍵字
public static final int finalCount = 1;
// 靜態程式碼塊
static {
System.out.println("初始化子類的靜態內部類的靜態程式碼塊");
}
// 普通靜態方法
public static String test1(){
System.out.println("呼叫子類的靜態內部類的 普通靜態方法");
return "";
}
// final 靜態方法
public static final String finalMethod(){
System.out.println("呼叫子類的靜態內部類的 final的靜態方法");
return "";
}
}
}
class Option1{
static {
System.out.println("初始化子類的靜態內部類的靜態屬性");
}
}
class Option2{
static {
System.out.println("初始化子類的靜態屬性");
}
}
public class Parent {
// 靜態程式碼塊
static {
System.out.println("初始化父類的靜態程式碼塊");
}
// 普通靜態屬性
public static Option0 option = new Option0();
// final 靜態屬性
// 使用 new 關鍵字
public static final Object newFinalObj = new Object();
// 不是用 new 關鍵字
public static final int finalCount = 1;
// 普通靜態方法
public static String test1(){
System.out.println("呼叫父類的 普通靜態方法");
return "";
}
// final 靜態方法
public static final String finalMethod0(){
System.out.println("呼叫父類的 final的靜態方法");
return "";
}
}
class Option0{
static {
System.out.println("初始化父類的靜態屬性");
}
}
public class Test {
public static void main(String[] args) {
// 測試本類
// System.out.println(Children.option);
// System.out.println(Children.newFinalObj);
// System.out.println(Children.finalCount);
// System.out.println(Children.finalMethod());
// System.out.println(Children.test1());
// 測試靜態內部類
// System.out.println(Children.StaticInClass.option);
// System.out.println(Children.StaticInClass.finalCount);
// System.out.println(Children.StaticInClass.newFinalObj);
// System.out.println(Children.StaticInClass.finalMethod());
// System.out.println(Children.StaticInClass.test1());
// 測試 繼承鏈的
// System.out.println(Children.newFinalObj);
}
}
結論
和預期瞭解吻合。。。