关于java静态内部类的思考

前言

最近在看多线程,讲到单例模式安全问题的时候。提到了单例的第四种模式——InnerClass模式。里面提到这种是用的最多的方式。很好奇里面的写法,然后就对静态内部类加载产生了疑问。故写了以下的代码实验一下。

代码1

我们利用静态代码块随着类的加载而执行这一特征,对静态内部类进行了测试。

public class StaticClassTest {

 static {
  System.out.println("this is static outter calss");
 }
​
 public static class Innclass {
  static {
   System.out.println("this is static inner class");
  }
 }
​
 public static void main(String[] args) {
  new StaticClassTest();//修改在这里
  System.out.println("------------我是华丽的分割线-----------");
  new StaticClassTest.Innclass();
 }
​
}
​```

这段代码的运行结果是

this is static outter calss

------------我是华丽的分割线-----------
this is static inner class
​```

这里面看到先是外部类加载,然后在调用内部类创建对象的时候,才会去加载静态内部类。这点和静态成员随着类一起加载有出入。而后,我对代码进行一些修改。

代码2

public class OutterClassTest {

​
 public static void main(String[] args) {
  new Outter();//修改在这里

  System.out.println("-------我是华丽的分割线--------");
  new Outter.Inner();
 }
​
}
​
class Outter {
 static {
  System.out.println("this is outter class loading ");
 }
 

 public static class Inner {
  static {
   System.out.println("this is inner calss loading ");
  }
 }
}

这段代码我将静态类的外部类和测试类分开。执行主方法后,得到如下结果:

this is outter class loading 
-------我是华丽的分割线--------
this is inner calss loading 

这和上面一段代码没什么区别。但是,当我们将调用外部类的方法创建对象这句话分别注释掉的时候。其结果就发生了变化:
代码1

this is static outter calss
------------我是华丽的分割线-----------
this is static inner class
​```

代码2

-------我是华丽的分割线--------
this is inner calss loading

##总结
很明显在这里面,代码1由于是main函数所在的类,必须加载。所以,静态代码块先执行。没什么问题。但主要问题在代码2上,为什么直接调用静态内部类创建对象的时候,外部类都没有加载。
这说明,静态内部类作为一种特殊的类成员有如下两个特征:
1. 加载时间随着调用而加载。而不是和外部类一起加载。

2. 静态内部类作为一个类,是可以单独使用,而不需要加载任何外部类代码的。

以上是我对静态内部类特性的一些总结,如有错误,欢迎指正。谢谢

你可能感兴趣的:(关于java静态内部类的思考)