1. 静态代码块在类第一次加载时就会执行,并且只执行一次
2. 普通代码块在每创建一个实例时执行
3. 普通代码块在构造器的super()执行后就会执行(其中super()是构造器中默认的第一句,写与不写该super()都一样)
看以下实例:
public class Init {
Init(int x) {
System.out.println("一个参数构造器");
}
Init() {
System.out.println("无参构造器");
}
static {
System.out.println("第一个静态代码块");
}
{
System.out.println("第一个普通代码块");
}
{
System.out.println("第二个普通代码块");
}
static {
System.out.println("第二个静态代码块");
}
public static void main(String [] args) {
new Init();
new Init(8);
}
}
执行结果为:
第一个静态代码块
第二个静态代码块
第一个普通代码块
第二个普通代码块
无参构造器
第一个普通代码块
第二个普通代码块
一个参数构造器
在继承关系树中,如果C继承B,B继承A
1. 首先A中静态代码块,然后B中静态代码块,然后C中静态代码块(即在类加载时,因为C依赖B,B依赖A,所以最先加载A,然后B,然后C)
2. 接下来A中普通代码块,A中构造器,B中普通代码块,B中构造器,C中普通代码块,C中构造器。(即执行每个构造器中的super()之后,再执行普通代码块,然后构造器super()之后的代码)
class A {
{ System.out.print("A普通代码块--->"); }
public A() {
System.out.print("A构造器--->");
}
static {
System.out.print("A静态代码块--->");
}
}
class B extends A {
static { System.out.print("B静态代码块--->"); }
public B() {
System.out.print("B构造器--->");
}
{ System.out.print("B普通代码块--->"); }
}
public class C extends B {
static {
System.out.print("C静态代码块--->");
}
public C() {
System.out.print("C构造器--->");
}
{ System.out.print("C普通代码块--->"); }
public static void main(String[] args) {
System.out.print("开始--->");
new C();
System.out.println("结束");
}
}
运行结果如下:
A静态代码块--->B静态代码块--->C静态代码块--->开始--->A普通代码块--->A构造器--->B普通代码块--->B构造器--->C普通代码块--->C构造器--->结束