一.不考虑继承的情况,一个类中的初始化顺序是:
1.静态变量,包括静态代码块
2.普通变量,包括普通代码块
3.执行构造函数
举个例子:
class Sample {
public Sample() {
System.out.println("调用Sample的默认构造函数");
}
public Sample(String s) {
System.out.println(s + ":调用Sample的含参构造函数");
}
}
public class Test {
public Test() {
System.out.println("调用Test的默认构造函数");
}
{
System.out.println("Test的非静态代码块");
}
static {
System.out.println("Test的静态代码块");
}
private Sample sample2 = new Sample();
private static Sample sample1 = new Sample("静态成员sample1初始化:");
public static void main(String args[]) {
System.out.println("main函数");
new Test();
System.out.println("已经构造完Test的匿名对象");
}
}
输出结果:
Test的静态代码块
静态成员sample1初始化::调用Sample的含参构造函数
main函数
Test的非静态代码块
调用Sample的默认构造函数
调用Test的默认构造函数
已经构造完Test的匿名对象
补充:对于静态成员和普通成员,其初始化顺序只与在类中定义的顺序有关,与其他因素无关
例子如下:
class Sample {
public Sample() {
System.out.println("调用Sample的默认构造函数");
}
public Sample(String s) {
System.out.println(s + ":调用Sample的含参构造函数");
}
}
public class Test {
public Test() {
System.out.println("调用Test的默认构造函数");
}
{
System.out.println("Test的非静态代码块1");
}
static {
System.out.println("Test的静态代码块1");
}
private Sample sample1 = new Sample("sample1初始化:");
private static Sample staticSample1 = new Sample("静态成员staticSample1初始化:");
private static Sample StaticSample2 = new Sample("静态成员staticSample2初始化:");
static {
System.out.println("Test的静态代码块2");
}
private Sample sample2 = new Sample("sample2初始化:");
{
System.out.println("Test的非静态代码块2");
}
public static void main(String args[]) {
new Test();
}
}
输出结果:
Test的静态代码块1
静态成员staticSample1初始化::调用Sample的含参构造函数
静态成员staticSample2初始化::调用Sample的含参构造函数
Test的静态代码块2
Test的非静态代码块1
sample1初始化::调用Sample的含参构造函数
sample2初始化::调用Sample的含参构造函数
Test的非静态代码块2
调用Test的默认构造函数
二.考虑继承的情况,一个类中的初始化顺序是:
1.继承体系中所有的静态变量初始化(先父类,后子类)
2.父类初始化(普通成员先初始化,构造函数的调用)
3.子类初始化(普通成员先初始化,构造函数的调用)
举个例子:
class Sample {
public Sample(String s) {
System.out.println(s);
}
}
class Father {
public Father() {
System.out.println("调用Father默认构造函数");
}
static {
System.out.println("父类-静态代码块1");
}
private Sample sample1 = new Sample("父类-成员sample1初始化");
static private Sample fatheStaticSample1 = new Sample(
"父类-静态成员fatheStaticSample1初始化");
static {
System.out.println("父类-静态代码块2");
}
private Sample sample2 = new Sample("父类-成员sample2初始化");
static private Sample fatheStaticSample2 = new Sample(
"父类-静态成员fatheStaticSample2初始化");
}
class Child extends Father {
public Child() {
System.out.println("调用Child默认构造函数");
}
static private Sample childStaticSample1 = new Sample(
"子类-静态成员childStaticSample1初始化");
private Sample sample1 = new Sample("子类-成员sample1初始化");
static {
System.out.println("子类-静态代码块1");
}
private Sample sample2 = new Sample("子类-成员sample2初始化");
static private Sample childStaticSample2 = new Sample(
"子类-静态成员childStaticSample2初始化");
static {
System.out.println("子类-静态代码块2");
}
}
public class Test {
public Test() {
System.out.println("调用Test的默认构造函数");
}
public static void main(String args[]) {
System.out.println("main函数");
new Child();
System.out.println("已经构造完Child对象");
}
}
运行结果:
main函数
父类-静态代码块1
父类-静态成员fatheStaticSample1初始化
父类-静态代码块2
父类-静态成员fatheStaticSample2初始化
--------------------父类静态成员初始化
子类-静态成员childStaticSample1初始化
子类-静态代码块1
子类-静态成员childStaticSample2初始化
子类-静态代码块2
--------------------子类静态成员初始化
父类-成员sample1初始化
父类-成员sample2初始化
调用Father默认构造函数
--------------------父类普通成员初始化和调用构造函数
子类-成员sample1初始化
子类-成员sample2初始化
调用Child默认构造函数
---------------------子类普通成员初始化和调用构造函数
最后附上图一张,帮助理解!
参考链接:
http://www.cnblogs.com/miniwiki/archive/2011/03/25/1995615.html(这个写的很好,本博文大多参考于此)
http://wangleide414.iteye.com/blog/515732
http://blog.sina.com.cn/s/blog_4cc16fc50100bjjp.html