這道面試題,知識點是,java在加載類的時候,有一個準備階段,準備階段會給類的靜態成員變量賦java默認的初始值。
再走到類的初始化階段,纔會給類的靜態成員變量賦程序員給的值。
package nine4one;
/**
* java虛擬機將在以下四種情況結束生命週期
* 1.執行了System.exit();方法,0是正常退出
* 2.程序執行正常結束
* 3.程序在執行過程中遇到了異常或者錯誤而異常終止
* 4.由於操作系統出現錯誤而導致java虛擬機進程終止
* -------------------------
* 類的加載、連接與初始化
* 1.加載:查找並加載類的二進制數據
* 2.連接:
* -驗證:確保被加載的類的正確性;
* -準備:爲類的靜態變量分配內存,並將其初始化爲默認值
* -解析:把類中的符號引用轉換爲直接引用
* 3.初始化:爲類的靜態變量賦予正確的初始值
*
* --------------------------
* java程序對類的使用方式可分爲兩種:
* 1.主動使用
* -創建類的實例
* -訪問某個類或接口的靜態變量, 或者對該靜態變量賦值
* -調用類的靜態方法
* -反射,如:Class.forName("");
* -初始化一個類的子類
* -java虛擬機啓動時被標明爲啓動類的類
* 2.被動使用
* 所有的java虛擬機實現必須在每個類或接口被java程序“首次主動使用”時,才初始化它們。
*
* ----------------------------
* 類的加載指的是將類的.class文件中的二進制數據讀入到內存中,將其放在運行時數據區的方法區內,然後在
* 堆區創建一個java.lang.Class對象,用來封裝類在方法區內的數據結構。
*
* ---------------------------
* 加載class文件的方式
* -從本地系統中直接加載v
* -通過網絡下載.class文件
* -從zip,jar等歸檔文件中加載.class文件
* -從專有數據庫中提取.class文件
* -將java源文件動態編譯爲.class文件
*
* ----------------------------
* 類的加載的最終產品是位於堆區中的Class對象
* Class對象封裝了類在方法區內的數據結構,並且向java程序員提供了訪問方法區內的數據結構的接口
*
* ----------------------------
* 有兩種類型的類加載器
* -java虛擬機自帶的加載器
* 根類加載器(Bootstrap),c++實現
* 擴展類加載器(Extension),java實現
* 系統類加載器(System)又稱應用加載器,java實現
* -用戶自定義類加載器
* java.lang.ClassLoader的子類
* 用戶可以定製類的加載方式
* 類加載器並不需要等到某個類被“首次主動使用”時再加載它
* ----------------------------------------
* jvm規範允許類加載器在預料某個類將要被使用時就預先加載它,如果
* 在預先加載的過程中遇到了.class文件缺失或存在錯誤,類加載器必須在
* 程序首次主動使用該類時才報告錯誤,(LinkageError錯誤)
*
* 如果這個類一直沒有被程序主動使用,那麼類加載器就不會報告錯誤
*
* 類的驗證:
* -類文件的結構檢查
* -語義檢查
* -字節碼驗證
* -二進制兼容性的驗證
* 類被加載後,就進入連接階段。連接就是將已經讀入到內存的類的二進制數據
* 合併到虛擬機的運行時環境中去。
* -----------------------------------------
* 類的準備:
* 在準備階段,java虛擬機爲類的靜態變量分配內存,並設置默認的初始值。
* 類的解析:
* 在解析階段,java虛擬機會把類的二進制數據中的符號引用替換爲直接引用。
* 類的初始化:
* 在初始化階段,java虛擬機執行類的初始化語句,爲類的靜態變量賦予初始值,
*。在程序中,靜態變量的初始化有兩種途徑:1,在靜態變量的聲明處初始化;2,在
*靜態代碼塊中初始化。
*
*
*
* @author 180719-2
*
*/
public class Singleton {
//private static Singleton singleton = new Singleton();
public static int count1;
public static int count2 = 0;
private static Singleton singleton = new Singleton();
public Singleton(){
count1++;
count2++;
}
public static Singleton getInstance(){
return singleton;
}
}
package nine4one;
public class Test{
public static void main(String[] args) throws Exception{
Singleton singleton = Singleton.getInstance();
System.out.println("count1 = " + singleton.count1);
System.out.println("count2 = " + singleton.count2);
// Class clazz = Class.forName("java.lang.String");
// System.out.println(clazz.getClassLoader());
//
// Class clazz2 = Class.forName("eightsix2.CglibProxyFactory");
// System.out.println(clazz2.getClassLoader());
}
}