https://docs.oracle.com/javase/tutorial/java/javaOO/initial.html
A class can have any number of static initialization blocks, and they can appear anywhere in the class body. The runtime system guarantees that static initialization blocks are called in the order that they appear in the source code.There is an alternative to static blocks — you can write a private static method.
静态块:
- 不限个数
- 不限位置
- 按照出现顺序执行
- 二选一的另一种形式是初始化方法
- 实例初始化块同静态块
调整后:
class Whatever { static { System.out.println("A:"); } static int i = getI(); static { System.out.println("B:" + i); } static int getI() { System.out.println("C:" + i); return 1; } public static void main(String[] args) { } }
结果:
A: C:0 B:1
小结:
最先默认值
其次块
再次构造函数
Block.java ↓
package t; public class Block extends BlockFather { /* * 静态块 */ static { System.out.println(" [静态块]"); } /* * 构造块 */ { System.out.println(" [构造块]"); } /* * 构造函数 */ public Block() { System.out.println(" [构造函数]"); } /* * 静态变量 */ public static String staticField1; // 重写父类静态属性 public static int fStaticField2; /* * 静态方法 */ public static void staticMethod() { System.out.println(" [静态方法]"); } /* * 普通变量 */ public String feild; /* * 普通方法 */ public void method() { System.out.println(" [普通方法]"); } /* * main方法 */ public static void main(String[] args) { System.out.println(" [main方法]"); } }
BlockFather.java ↓
package t; public class BlockFather { /* * 静态块 */ static { System.out.println("f[静态块]"); } /* * 构造块 */ { System.out.println("f[构造块]"); } /* * 构造函数 */ public BlockFather() { System.out.println("f[构造函数]"); } /* * fStaticField */ public static int fStaticField1; public static int fStaticField2; }
TestBlock.java ↓
package t; public class TestBlock { public static void main(String[] args){ // 1. new // new Block(); // f[静态块] // [静态块] // f[构造块] // f[构造函数] // [构造块] // [构造函数] // 2. new new // new Block(); // new Block(); // f[静态块] // [静态块] // f[构造块] // f[构造函数] // [构造块] // [构造函数] // f[构造块] // f[构造函数] // [构造块] // [构造函数] // 3.1 使用(读取或修改)静态属性(子类) // String s = Block.staticField1; // f[静态块] // [静态块] // 3.2 使用(读取或修改)静态属性(父类&未重写) // int i = Block.fStaticField1; // f[静态块] // 3.3 使用(读取或修改)静态属性(父类&重写) // int i = Block.fStaticField2; // f[静态块] // [静态块] // 4. 调用静态方法 // Block.staticMethod(); // f[静态块] // [静态块] // [静态方法] // 5. 反射使用静态属性(完全同3) // try { // Block.class.getField("staticField1").get(null); // } catch (IllegalArgumentException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } catch (IllegalAccessException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } catch (NoSuchFieldException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } catch (SecurityException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } // 6. 反射使用静态方法(同4) // try { // Block.class.getMethod("staticMethod", null).invoke(null, null); // } catch (IllegalAccessException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } catch (IllegalArgumentException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } catch (InvocationTargetException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } catch (NoSuchMethodException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } catch (SecurityException e) { // // TODO Auto-generated catch block // e.printStackTrace(); // } // 7. 直接运行一个main函数入口的类
// f[静态块]
// [静态块]
// [main方法]
}
}
ps:
构造块和构造方法只有new 时执行