您的位置:首页 > 编程语言 > Java开发

JAVA对象的成员初始化顺序的初步理解

2016-10-13 19:19 381 查看
问题:



JAVA创建一个对象的时候,静态成员和非静态是按什么顺序进行初始化的?

下面通过一个例子,如果你能准确地写出它的输出顺序,那么你对成员初始化顺序就有了一定的理解了.
然后在后面给出,为什么是这样的输出顺序?

class Bowl{
public Bowl(int mark) {
System.out.println("Bowl("+ mark +")");
}
void f1(int mark){
System.out.println("f1("+ mark +")");
}
}

class Table{
static Bowl bowl1=new Bowl(1);
public Table() {
System.out.println("Table");
bowl2.f1(1);
}
void f2(int mark){
System.out.println("f2("+ mark +")");
}
static Bowl bowl2=new Bowl(2);
}

class Cupboard{
Bowl bowl3=new Bowl(3);
static Bowl bowl4=new Bowl(4);
public Cupboard() {
System.out.println("Cupboard");
bowl4.f1(2);
}
void f3(int mark){
System.out.println("f3("+ mark +")");
}
static Bowl bowl5=new Bowl(5);
}
public class StaticInitialization {
public static void main(String[] args) {
System.out.println("Creating new Cupboard() in main");
new Cupboard();
System.out.println("Creating new Cupboard() in main");
new Cupboard();
table.f2(1);
cupboard.f3(1);
}
<pre name="code" class="java">static Table table =new Table();
static Cupboard cupboard=new Cupboard();


}


建议自己先试着写一遍结果,然后对照真实输出结果

Bowl(1)
Bowl(2)
Table
f1(1)
Bowl(4)
Bowl(5)
Bowl(3)
Cupboard
f1(2)
Creating new Cupboard() in main
Bowl(3)
Cupboard
f1(2)
Creating new Cupboard() in main
Bowl(3)
Cupboard
f1(2)
f2(1)
f3(1)


JAVA的初始化被分成几个部分(Murre murre 是类中的一个成员)

1静态成员指定初始化  和 静态块中初始化

静态成员指定初始化

static Murre murre=new Murre();

 

静态块中初始化

static{

murre = new Murre

}

这两者的优先级是相等的,意思按照书写顺序往下运行;

因此

static{
son=2;
<span>	</span>}

static int son=1;


int son=1;
{
son=2;
}


这两者的结果是有区别的(我之前有些误会)

2非静态成员指定初始化 和非静态块初始化

非静态成员指定初始化

Murre murre=new Murre();

非静态块初始化

Murre murre;

{

murre=new Murre();

}

优先级是相等的,按照书写顺序,同上静态

3构造函数中的初始化

Murre murre1;

static Murre murre2;

public Shit(Murre mu,Murre mu2)  //Shit类的构造函数

{

muure1=mu;

murre2=mu2;

}

创建一个类的初始化顺序就是按照我写的3种初始化顺序初始化的,

JAVA如此设计的根本原因是:

确保,每一个变量在被使用之前,都能被好好地初始化.

回到刚才的程序中,让我们分析一波:

首先要调用Class StaticInitialization 的static main()函数,所以加载StaticInitialization中的static 成员

 也就是

static Table table =new Table(); <span style="white-space:pre">	</span><span style="font-family: Arial, Helvetica, sans-serif;">//静态指定初始化</span>

static Cupboard cupboard=new Cupboard();
这两个,先看第一个

由于涉及到了new Table();

所以又要加载Table类,在Table类中要执行的初始化有:

static Bowl bowl1=new Bowl(1);<span style="white-space:pre">		</span><span style="font-family: Arial, Helvetica, sans-serif;">//静态指定初始化  </span><span style="white-space:pre">
</span>public Table() {
System.out.println("Table");<span style="white-space:pre">	</span>//构造器初始化
bowl2.f1(1);
}
static Bowl bowl2=new Bowl(2);<span style="white-space:pre">		</span><span style="font-family: Arial, Helvetica, sans-serif;">//静态指定初始化</span>
其中构造器初始化要慢于所有的静态初始化,即使有一个静态初始在它的后面

这里又涉及到新建Bowl对象

所以又要初始化Bowl对象,所以又要初始化Bowl的初始化

public Bowl(int mark) {
System.out.println("Bowl("+ mark +")");
}


到这里,应该可以明白为什么输出顺序是这样子了,剩下的自行推导..
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  初始化 JAVA