1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
   | public class Main { 
      public static void main(String[] args) {         new Main();      }
      static int num = 4; 
      {         num += 3;         System.out.println("b");      }
      int a = 5; 
      {          System.out.println("c");      }
      Main() {          System.out.println("d");      }
      static {          System.out.println("a");     }
      static void run()      {         System.out.println("e");     } }
  | 
 
执行以上代码可以总结加载顺序:静态代码块(静态变量) -> 匿名代码块(成员变量) -> 构造方法 -> 静态方法(不调用不加载
- 静态代码块只加载一次
 
- 静态方法只有调用才会加载
 
- 静态代码块和静态变量按照代码编写前后顺序执行
 
- 匿名代码块和成员变量按照代码编写前后顺序执行
 
1 2 3 4 5
   | public class Print {     public Print(String s) {         System.out.println(s + " ");     } }
  | 
 
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
   | public class Parent {     public static Print obj1 = new Print("1");
      public Print obj2 = new Print("2");
      public static Print obj3 = new Print("3");
      static {         new Print("4");     }
      public static Print obj4 = new Print("5");
      public Print obj5 = new Print("6");
      public Parent() {         new Print("7");     } }
  | 
 
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
   | public class Child extends Parent {     static {         new Print("a");     }
      public static Print obj1 = new Print("b");
      public Print obj2 = new Print("c");
      public Child() {         new Print("d");     }
      public static Print obj3 = new Print("e");
      public Print obj4 = new Print("f");
      public static void main(String[] args) {         Parent obj1 = new Child();
          Parent obj2 = new Child();     } }
  | 
 
执行main方法打印顺序:1 3 4 5 a b e 2 6 7 c f d 2 6 7 c f d
- 先执行父类的静态代码块和静态变量初始化,并且静态代码块和静态变量的执行顺序只跟代码中出现的顺序有关;
 
- 执行子类的静态代码块和静态变量初始化;
 
- 执行父类的实例变量初始化;
 
- 执行父类的构造函数;
 
- 执行子类的实例变量初始化;
 
- 执行子类的构造函数;
 
如果类已经被加载,则静态代码块和静态变量就不用重复执行,再创建类对象时,只执行与实例相关变量初始化和构造方法