- 类是在运行期间动态加载的。
类的生命周期
包括以下 7 个阶段:
- 加载(Loading)
- 验证(Verification)
- 准备(Preparation)
- 解析(Resolution)
- 初始化(Initialization)
- 使用(Using)
卸载(Unloading)
其中解析过程在某些情况下可以在初始化阶段之后再开始,这是为了支持 Java 的动态绑定。
类加载过程
1.加载
加载是类加载的一个阶段,注意不要混淆。
- 加载过程完成以下三件事:
1.通过一个类的全限定名来获取定义此类的二进制字节流。
2.将这个字节流所代表的静态存储结构转化为方法区的运行时存储结构。
3.在内存中生成一个代表这个类的 Class 对象,作为方法区这个类的各种数据的访问入口。
2. 验证
确保 Class 文件的字节流中包含的信息符合当前虚拟机的要求,并且不会危害虚拟机自身的安全。
主要有以下 4 个阶段:
(一)文件格式验证
验证字节流是否符合 Class 文件格式的规范,并且能被当前版本的虚拟机处理。
(二)元数据验证
对字节码描述的信息进行语义分析,以保证其描述的信息符合 Java 语言规范的要求。
(三)字节码验证
通过数据流和控制流分析,确保程序语义是合法、符合逻辑的。
(四)符号引用验证
发生在虚拟机将符号引用转换为直接引用的时候,对类自身以外(常量池中的各种符号引用)的信息进行匹配性校验。
3. 准备
- 类变量是被 static 修饰的变量,准备阶段为类变量分配内存并设置初始值,使用的是方法区的内存。
- 实例变量不会在这阶段分配内存,它将会在对象实例化时随着对象一起分配在 Java 堆中。
- 初始值一般为 0 值,例如下面的类变量 value 被初始化为 0 而不是 123。
public static int value = 123;
- 如果类变量是常量,那么会按照表达式来进行初始化,而不是赋值为 0。
public static final int value = 123;
4. 解析
- 将常量池的符号引用替换为直接引用的过程。
5. 初始化
- 初始化阶段才真正开始执行类中的定义的 Java 程序代码。初始化阶段即虚拟机执行类构造器 () 方法的过程。
- 在准备阶段,类变量已经赋过一次系统要求的初始值,而在初始化阶段,根据程序员通过程序制定的主观计划去初始化类变量和其它资源。