最近项目经理要我整理一下java基础,找个重点讲一下,刚好最近在研究关于静态static的东西,所以拿出来先分享一下。
首先讲一下java中有关静态代码块、静态变量、构造代码块、构造方法的定义。
静态代码块:直接在类中定义的并且加了static关键字的代码块{},静态代码块是在类加载时自动执行的一段语句。形如:
public class Test
{
static {
//.......
}
}
静态变量:被static修饰的变量。形如:
static int num = 1;
构造代码块:直接在类中定义的没有加static关键字的代码块{}。
public class Test
{
{
//.......
}
}
构造方法:
public class Test
{
Test()
{
//无参构造方法
}
Test(int i)
{
//有参构造方法
}
}
然后开始我们的实验。
1、对于一个类里的静态变量和静态代码块,执行的顺序是谁在前先执行谁。
测试代码:
Test4.java
public class Test4
{
public static int no = 1;
public static int num1 = 6;
static {
if(num1 == 6)
System.out.println("第" + (no++) + "次加载静态变量");
System.out.println("第" + (no++) + "次加载静态代码块");
}
public static int num2 = 10;
static {
if(num2 == 10)
System.out.println("第" + (no++) + "次加载静态变量");
System.out.println("第" + (no++) + "次加载静态代码块");
}
public static void main(String args[])
{
new Test4();
}
}
测试结果:
第1次加载静态变量
第2次加载静态代码块
第3次加载静态变量
第4次加载静态代码块
public class Test5
{
public static int no = 1;
{
System.out.println("第" + (no++) + "次加载构造代码块");
}
static {
System.out.println("第" + (no++) + "次加载静态代码块");
}
Test5()
{
System.out.println("第" + (no++) + "次加载构造方法");
}
public static void main(String args[])
{
new Test5();
}
}
第1次加载静态代码块
第2次加载构造代码块
第3次加载构造方法
public class TestParent
{
{
System.out.println("这是父类的构造代码块");
}
static {
System.out.println("这是父类的静态代码块");
}
TestParent()
{
System.out.println("这是父类的构造方法");
}
}
TestChild.java
public class TestChild extends TestParent
{
{
System.out.println("这是子类的构造代码块");
}
static {
System.out.println("这是子类的静态代码块");
}
TestChild()
{
System.out.println("这是子类的构造方法");
}
}
Test6.java
public class Test6
{
public static void main(String args[])
{
new TestChild();
}
}
这是父类的静态代码块
这是子类的静态代码块
这是父类的构造代码块
这是父类的构造方法
这是子类的构造代码块
这是子类的构造方法
public class Test7
{
public static int no = 1;
static {
if(no == 1)
System.out.println("第" + (no++) + "次加载静态变量");
System.out.println("第" + (no++) + "次加载静态代码块");
}
{
System.out.println("第" + (no++) + "次加载构造代码块");
}
Test7()
{
System.out.println("第" + (no++) + "次加载构造方法");
}
public static void main(String args[])
{
new Test7();
new Test7();
}
}
第1次加载静态变量
第2次加载静态代码块
第3次加载构造代码块
第4次加载构造方法
第5次加载构造代码块
第6次加载构造方法
public class Test8
{
public static int no = 1;
public static Test8 t8 = new Test8();
static {
if(no == 1)
System.out.println("第" + (no++) + "次加载静态变量");
System.out.println("第" + (no++) + "次加载静态代码块");
}
{
System.out.println("第" + (no++) + "次加载构造代码块");
}
Test8()
{
System.out.println("第" + (no++) + "次加载构造方法");
}
public static void main(String args[])
{
new Test8();
}
}
第1次加载构造代码块
第2次加载构造方法
第3次加载静态代码块
第4次加载构造代码块
第5次加载构造方法
public class Test8
{
public static Test8 t8 = new Test8();
public static int no = 1;
static {
if(no == 1)
System.out.println("第" + (no++) + "次加载静态变量");
System.out.println("第" + (no++) + "次加载静态代码块");
}
{
System.out.println("第" + (no++) + "次加载构造代码块" );
}
Test8()
{
System.out.println("第" + (no++) + "次加载构造方法");
}
public static void main(String args[])
{
new Test8();
}
}
测试结果:
第0次加载构造代码块
第1次加载构造方法
第1次加载静态变量
第2次加载静态代码块
第3次加载构造代码块
第4次加载构造方法
public class TestParent
{
{
System.out.println("这是父类的构造代码块");
}
static {
System.out.println("这是父类的静态代码块");
}
TestParent()
{
System.out.println("这是父类的构造方法");
}
}
TestChild1.java
public class TestChild1 extends TestParent
{
public static TestChild1 tc1 = new TestChild1();
{
System.out.println("这是子类的构造代码块");
}
static {
System.out.println("这是子类的静态代码块");
}
TestChild1()
{
System.out.println("这是子类的构造方法");
}
public static void main(String args[])
{
}
}
这是父类的静态代码块
这是父类的构造代码块
这是父类的构造方法
这是子类的构造代码块
这是子类的构造方法
这是子类的静态代码块
public class Test9 {
public static Test10 t10;
public static Test10 t11 = new Test10();
public static int no = 1;
static {
if(no == 1)
System.out.println("第" + (no++) + "次加载静态变量");
System.out.println("第" + (no++) + "次加载静态代码块");
}
{
System.out.println("第" + (no++) + "次加载构造代码块");
}
Test9()
{
System.out.println("第" + (no++) + "次加载构造方法");
}
public static void main(String args[])
{
}
}
public class Test10
{
public static int no = 1;
static {
if(no == 1)
System.out.println("第" + (no++) + "次加载静态变量");
System.out.println("第" + (no++) + "次加载静态代码块");
}
{
System.out.println("第" + (no++) + "次加载构造代码块");
}
Test10()
{
System.out.println("第" + (no++) + "次加载构造方法");
}
}
第1次加载静态变量
第2次加载静态代码块
第3次加载构造代码块
第4次加载构造方法
第1次加载静态变量
第2次加载静态代码块
这里可以看出,如果实例化的静态类不是当前类,那么该静态类的执行顺序还是正常的,也就是说不会绕开静态代码块和静态变量。
注意,这里如果没有实例化而只是声明了静态类,那么该静态类不会执行任何语句。