package logic;public class Ali { //顺序执行 ------------>静态修饰无论如何只会被装载一次. public static int k=0; //二、k=0; public static Ali t1 = new Ali("t1"); //三、new Ali("t1") public static Ali t2 = new Ali("t2"); //七、new Ali("t2"); public static int i = print("i"); //十一、静态变量与静态构造块优先执行,但是得按照先后次序(在代码中的) public static int n = 99; //十二、n=99; static //十三、静态构造块无论如何也只能被执行一次.与静态变量之间按照先后次序决定。 { print("静态块"); } public static int print(String str) //九下、(合并九上) //十二、静态方法不执行 { /*静态方法如果不被调用不会主动执行.*/ System.out.println((++k)+":"+str+" i="+i+" n="+n); ++n; return ++i; } //------------------------------------\\ //-------------以上为static-------------\\ //------------------------------------\\ public int j = print("j"); //四、非静态元素定义与非静态方法块按上下顺序执行 //八、非静态变量执行是new多少次就执行多少次的 //十五、再次执行,这是来自main里面的呼唤
public static Test t2=new Test("t2"); 应该先初始化。具体顺序应该是这样的:静态变量—静态块—成员变量—构造方法—静态方法
程序的确是在初始化静态变量public static Test t1=new Test("t1"); ,
只不过这个静态变量t1引用了一个Test实例,那只能是构造好这个实例(构造实例时就会初始化实例变量,构造块,构造函数),然后赋值给静态变量t1后,才算初始化完t1;
静态变量t2也是一样的。另外,说一下:
对于类中的各代码的执行顺序:静态变量在类编译时全部初始化,非静态变量仅在实例化时才初始化
严格的说,静态变量是在类被加载到java虚拟机时,被初始化的,和编译没有关系。
1.编译Test类:
测试方法把
// public static Test t1=new Test("t1");
// public static Test t2=new Test("t2");
// Test t=new Test("init");
都注释了,运行结果会是:
1:i i=0 n=0
2:静态块 i=1 n=99
没有输出j相关的,那是因为j是成员变量,非静态成员变量。也就是说在不实例化Test的条件下,加载顺序是静态变量,静态块。
2.当有实例化的Test静态变量存在的时候。
public class Test {
public static int k=0;
public static Test t1=new Test("t1");
// public static Test t2=new Test("t2");
public static int i=print("i");
public static int n=99;
private int a=0;
private int j = print("j");
{
print("构造块");
}
static{
print("静态块");
}
public Test(String str){
System.out.println((++k)+":"+str+" i="+i+" n="+n);
++i;++n;
}
public static int print(String str){
System.out.println((++k)+":"+str+" i="+i+" n="+n);
++n;
return++i;
}
public static void main(String args[])
{
// Test t=new Test("init");
}
}
运行结果:
1:j i=0 n=0
2:构造块 i=1 n=1
3:t1 i=2 n=2
4:i i=3 n=3
5:静态块 i=4 n=99
这说明,在实例化Test类的时候,先初始化的并不是静态变量,而是成员变量,最后加载的静态变量,跟静态快。
但我们在把public static int i=print("i"); 移到public static Test t1=new Test("t1"); 之前运行结果:
1:i i=0 n=0
2:j i=1 n=1
3:构造块 i=2 n=2
4:t1 i=3 n=3
5:静态块 i=4 n=99
说明静态变量的初始化顺序跟位置有关系。
public static int k=0; ①main开始,先执行左边初始化Test t k=0
public static Test t1=new Test("t1"); //②实例化new Test,跳到a=0,执行print("j"),输出1:j i=0 n=0 ③执行print("构造块"),输出2:构造块 i=1 n=1 ④执行public Test(t1) ,输出3:t1 i=2 n=2这句执行完毕。// public static Test t2=new Test("t2");//⑤同理可得输出4:j i=3 n=3 5:构造块 i=4 n=4 6:t2 i=5 n=5
public static int i=print("i"); //⑥继续初始化Test t 执行这句输出7:i i=6 n=6
public static int n=99; //⑦执行这句,n=99
private int a=0;
private int j = print("j");
{
print("构造块");
}
static{
print("静态块"); //⑧执行这句,输出8:静态块 i=7 n=99 Test t初始化完毕 }
public Test(String str){
System.out.println((++k)+":"+str+" i="+i+" n="+n);
++i;++n;
}
public static int print(String str){
System.out.println((++k)+":"+str+" i="+i+" n="+n);
++n;
return++i;
}
public static void main(String args[])
{
// Test t=new Test("init"); //⑨实例化new Test("init"),调到执行a=0;print("j")输出9:j i=8 n=100 ⑩执行{构造块}输出 10:构造块 i=9 n=101
接着执行构造函数Test("init")输出11:init i=10 n=102 执行完毕。 }
}
http://bbs.csdn.net/topics/390607692
Java对象初始化详解:http://blog.csdn.net/ysjian_pingcx/article/details/19605335
package logic;public class Ali {
//顺序执行 ------------>静态修饰无论如何只会被装载一次.
public static int k=0; //二、k=0;
public static Ali t1 = new Ali("t1"); //三、new Ali("t1")
public static Ali t2 = new Ali("t2"); //七、new Ali("t2");
public static int i = print("i"); //十一、静态变量与静态构造块优先执行,但是得按照先后次序(在代码中的)
public static int n = 99; //十二、n=99;
static //十三、静态构造块无论如何也只能被执行一次.与静态变量之间按照先后次序决定。
{
print("静态块");
}
public static int print(String str) //九下、(合并九上) //十二、静态方法不执行
{
/*静态方法如果不被调用不会主动执行.*/
System.out.println((++k)+":"+str+" i="+i+" n="+n);
++n;
return ++i;
}
//------------------------------------\\
//-------------以上为static-------------\\
//------------------------------------\\
public int j = print("j"); //四、非静态元素定义与非静态方法块按上下顺序执行 //八、非静态变量执行是new多少次就执行多少次的 //十五、再次执行,这是来自main里面的呼唤
{ //五、非静态构造块优先构造器执行,但与非静态变量按上下先后顺序 //九、非静态构造块优先构造器执行,但与非静态变量按上下先后顺序 //十六、这是来自main里面的呼唤
print("构造块");
}
public Ali(String str) //六、构造器 //十、构造器 //十七、这儿执行完毕之后就不会再执行了.
{
System.out.println( (++k) + ":"+str+" i="+i+" n="+n);
++i;
++n;
}
//------------------------------------\\
//-------------以上非static-------------\\
//------------------------------------\\
public static void main(String[] args) {//一、大约步骤--装载static修饰的
new Ali("init ... "); //十四、执行 new Ali("init ... ");
}
}
那样是不会造成死循环的,要读懂java的加载顺序。上学期学长们实习回来就说了这个问题。我这儿做了点批注,有错请轻拍
java的加载顺序应该是这样的:
main第一句之前载入类,只载入static修饰的语句。变量或者是方法块优先顺序按照代码排列上下决定。静态方法载入不执行。
之后若是遇到调用构造器的,从上到下依次执行非静态变量定义、方法块。相对而言 , 构造器优先级最低。
java的加载顺序应该是这样的:
main第一句之前载入类,只载入static修饰的语句。变量或者是方法块优先顺序按照代码排列上下决定。静态方法载入不执行。
之后若是遇到调用构造器的,从上到下依次执行非静态变量定义、方法块。相对而言 , 构造器优先级最低。
学习了!
* 构造函数执行,main函数执行
*
* 其实记住三点就行了~~~~搞的我都郁闷死了,给大家总结下:
* 1.先顺序加载static变量
* 2.无论何时只要执行构造函数,那么在执行构造函数方法体之前必须完成非静态变量,方法的加载(不限次数)
* 3.static执行完成后,classloader会执行main方法体,然后就正常执行呗~~~
可以看看我的博客~~写的比较详细~
http://blog.csdn.net/supera_li/article/details/39431663