1. 程式人生 > >jvm 關於初始化時 , 的呼叫。

jvm 關於初始化時 , 的呼叫。

在編譯生成class檔案時,會自動產生兩個方法,一個是類的初始化方法<clinit>, 另一個是例項的初始化方法<init>

<clinit>:在jvm第一次載入class檔案時呼叫,包括靜態變數初始化語句和靜態塊的執行

<init>:在例項創建出來的時候呼叫,包括呼叫new操作符;呼叫Class或java.lang.reflect.Constructor物件的newInstance()方法;呼叫任何現有物件的clone()方法;通過java.io.ObjectInputStream類的getObject()方法反序列化。

  1. public
     class T2{  
  2. static{  
  3.    System.out.println("-----.static---");  
  4.    }  
  5.    static T2 t2 = new T2();  
  6.    C t =new C();  
  7.    static String str = "ff";   
  8.    public T2(){System.out.println("-----...");}  
  9.   public static void main(String[] ages){  
  10.    String a = "hi";  
  11.     String s = "'"+a+"'";  
  12.     String ni= T2.str;  
  13.    }  
  14. }  
  15. class C{  
  16.  static{System.out.println("----cccccc  static-...");}  
  17. }  

   這個是test類。下面是位元組碼

Java程式碼  收藏程式碼
  1. {  
  2. static T2 t2;  
  3. C t;  
  4. static java.lang.String str;  
  5. public T2();<init>將相應的變數壓入<init>方法中  
  6.   Code:  
  7.    Stack=3, Locals=1, Args_size=1  
  8.    0:   aload_0  
  9.    1:   invokespecial   #1
    //Method java/lang/Object."<init>":()V  
  10.    4:   aload_0  
  11.    5:   new     #2//class C  
  12.    8:   dup  
  13.    9:   invokespecial   #3//Method C."<init>":()V  
  14.    12:  putfield        #4//Field t:LC;  
  15.    15:  getstatic       #5//Field java/lang/System.out:Ljava/io/PrintStream;  
  16.    18:  ldc     #6//String -----...  
  17.    20:  invokevirtual   #7//Method java/io/PrintStream.println:(Ljava/lang/Str  
  18. ing;)V  
  19.    23:  return  
  20.   LineNumberTable:  
  21.    line 110  
  22.    line 84  
  23.    line 1115  
  24. public static void main(java.lang.String[]);  
  25.   Code:  
  26.    Stack=2, Locals=4, Args_size=1  
  27.    0:   ldc     #8//String hi  
  28.    2:   astore_1  
  29.    3:   new     #9//class java/lang/StringBuilder  
  30.    6:   dup  
  31.    7:   invokespecial   #10//Method java/lang/StringBuilder."<init>":()V  
  32.    10:  ldc     #11//String '  
  33.    12:  invokevirtual   #12//Method java/lang/StringBuilder.append:(Ljava/lang  
  34. /String;)Ljava/lang/StringBuilder;  
  35.    15:  aload_1  
  36.    16:  invokevirtual   #12//Method java/lang/StringBuilder.append:(Ljava/lang  
  37. /String;)Ljava/lang/StringBuilder;  
  38.    19:  ldc     #11//String '  
  39.    21:  invokevirtual   #12//Method java/lang/StringBuilder.append:(Ljava/lang  
  40. /String;)Ljava/lang/StringBuilder;  
  41.    24:  invokevirtual   #13//Method java/lang/StringBuilder.toString:()Ljava/l  
  42. ang/String;  
  43.    27:  astore_2  
  44.    28:  getstatic       #14//Field str:Ljava/lang/String;  
  45.    31:  astore_3  
  46.    32:  return  
  47.   LineNumberTable:  
  48.    line 130  
  49.    line 143  
  50.    line 1528  
  51.    line 1632  
  52. static {};  
  53.   Code:  
  54.    Stack=2, Locals=0, Args_size=0  
  55.    0:   getstatic       #5//Field java/lang/System.out:Ljava/io/PrintStream;  
  56.    3:   ldc     #15//String -----.static---  
  57.    5:   invokevirtual   #7//Method java/io/PrintStream.println:(Ljava/lang/Str  
  58. ing;)V  
  59.    8:   new     #16//class T2  
  60.    11:  dup  
  61.    12:  invokespecial   #17//Method "<init>":()V//調了T2<init>方法  
  62.    15:  putstatic       #18//Field t2:LT2;  
  63.    18:  ldc     #19//String ff  
  64.    20:  putstatic       #14//Field str:Ljava/lang/String;  
  65.    23:  return  
  66.   LineNumberTable:  
  67.    line 50  
  68.    line 78  
  69.    line 918  
  70. }  
  71. 沒註釋static T2 t2 = new T2();//調了T2<init>方法  
  72. 結果:-----.static---  
  73. ----cccccc  static-...  
  74. -----...  
  75. {  
  76. C t;  
  77. static java.lang.String str;  
  78. public T2();<init>將相應的變數壓入<init>方法中  
  79.   Code:  
  80.    Stack=3, Locals=1, Args_size=1  
  81.    0:   aload_0  
  82.    1:   invokespecial   #1//Method java/lang/Object."<init>":()V  
  83.    4:   aload_0  
  84.    5:   new     #2//class C  
  85.    8:   dup  
  86.    9:   invokespecial   #3//Method C."<init>":()V  
  87.    12:  putfield        #4//Field t:LC;  
  88.    15:  getstatic       #5//Field java/lang/System.out:Ljava/io/PrintStream;  
  89.    18:  ldc     #6//String -----...  
  90.    20:  invokevirtual   #7//Method java/io/PrintStream.println:(Ljava/lang/Str  
  91. ing;)V  
  92.    23:  return  
  93.   LineNumberTable:  
  94.    line 110  
  95.    line 84  
  96.    line 1115  
  97. public static void main(java.lang.String[]);  
  98.   Code:  
  99.    Stack=2, Locals=4, Args_size=1  
  100.    0:   ldc     #8//String hi  
  101.    2:   astore_1  
  102.    3:   new     #9//class java/lang/StringBuilder  
  103.    6:   dup  
  104.    7:   invokespecial   #10//Method java/lang/StringBuilder."<init>":()V  
  105.    10:  ldc     #11//String '  
  106.    12:  invokevirtual   #12//Method java/lang/StringBuilder.append:(Ljava/lang  
  107. /String;)Ljava/lang/StringBuilder;  
  108.    15:  aload_1  
  109.    16:  invokevirtual   #12//Method java/lang/StringBuilder.append:(Ljava/lang  
  110. /String;)Ljava/lang/StringBuilder;  
  111.    19:  ldc     #11//String '  
  112.    21:  invokevirtual   #12//Method java/lang/StringBuilder.append:(Ljava/lang  
  113. /String;)Ljava/lang/StringBuilder;  
  114.    24:  invokevirtual   #13//Method java/lang/StringBuilder.toString:()Ljava/l  
  115. ang/String;  
  116.    27:  astore_2  
  117.    28:  getstatic       #14//Field str:Ljava/lang/String;  
  118.    31:  astore_3  
  119.    32:  return  
  120.   LineNumberTable:  
  121.    line 130  
  122.    line 143  
  123.    line 1528  
  124.    line 1632  
  125. static {};  
  126.   Code:  
  127.    Stack=2, Locals=0, Args_size=0  
  128.    0:   getstatic       #5//Field java/lang/System.out:Ljava/io/PrintStream;  
  129.    3:   ldc     #15//String -----.static---  
  130.    5:   invokevirtual   #7//Method java/io/PrintStream.println:(Ljava/lang/Str  
  131. ing;)V  
  132.    8:   ldc     #16//String ff  
  133.    10:  putstatic       #14//Field str:Ljava/lang/String;  
  134.    13:  return  
  135.   LineNumberTable:  
  136.    line 50  
  137.    line 98  
  138. }  
  139. 註釋static T2 t2 = new T2(); 沒有t2的<init>方法  
  140. 結果:-----.static---  

總結:當一個類初始化的時候,先呼叫<cinit>方法 ,如果在<cinit>方法中遇到<init>方法。則先呼叫完<init>方法。然後在繼續執行<cinit>