static成員加載時機

廢話不多說 看看這段代碼。告訴我結果:

[java] view plain copy
  1. import java.io.*;  
  2. class Test    
  3. {  
  4.       
  5.     public static Test t = new Test();  
  6.       
  7.     public  Test(){  
  8.         a++;  
  9.         b++;  
  10.     }  
  11.       
  12.     public static int a;  
  13.     public static int b = 0;  
  14.       
  15.     public static void main (String[] args) throws java.lang.Exception  
  16.     {  
  17.           
  18.         System.out.println(t.a + " " + t.b);  
  19.     }  
  20. }  


如果你毫無疑問的答很簡單 static 是類所有的,每個實例改變都會變他的值,答案是 1,1   那麼。。恭喜你上套了。


你可以親自試一下結果。 是1,0  這是爲什麼呢。  原來一個類加載的時候會經歷以下步驟:


加載:查找並加載類的二進制數據

連接 
     -驗證:確保被加載的類的正確性    //爲什麼會檢驗? 因爲.class有可能是手動改的
     -準備:爲類的靜態變量分配內存,並將其初始值轉化爲默認值 
     -解析:把類中的符號引用轉換爲直接引用
初始化:爲類的靜態變量賦予正確的初始值

回過頭再來看最上面的一段程序。發現實例是在static成員上面寫的,也就是在賦值之前。
那麼在準備階段, 會爲靜態變量分配內存,初始值爲默認值,這時候 a 和b 都是 0,0   然後創建實例  a++;b++; 此時 a 和b的值都是1;

重點來了。接下來到了初始化過程, 會爲靜態變量賦予正確的初始值, 由於a沒有賦值,所以還爲1沒有變化,但是b被賦予正確的初始值0。
所以這下真相大白了。 b的真實變化過程是 0-->1-->0。

附上一些筆記:

類的主動使用
     1.創建類的實例
     2.訪問靜態變量
     3.調用靜態方法
     4.反射
     5.初始化一個類的子類
     6.虛擬機啓動時候被標明啓動類的類


將二進制讀入到內存中  放在運行時的方法去內   堆內創建一個Class對象,用來封裝類在方法區內的數據結構


加載class的方式
1.從本地系統直接加載
2.網絡加載
3.zip  jar包加載
4.從專有數據庫提取.class
5,將java 源文件動態編譯爲.class


發佈了60 篇原創文章 · 獲贊 6 · 訪問量 13萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章