作为资深IT工程师或架构师,了解类在虚拟机中的加载过程是基本功之一。下面来简单分析一下这个过程,首先看一张整体图:
1、加载
类的加载是指将类的class文件读入到内存的过程,并为之创建一个java.lang.Class对象。
具体流程:
1.1 通过一个类的全限定名来获取定义此类的二进制字节流。
1.2 将这个字节流所代表的静态存储结构转化为方法区的运行时数据结构。
1.3 在内存中生成一个代表这个类的java.lang.Class对象,作为方法区这个类的各种数据的访问入口。
二进制数据的来源如下:
1.1 从本地系统加载class文件
1.2 从JAR包中加载class文件
1.3 通过网络加载class文件
1.4 把一个java源文件动态编译后再加载
2、连接
连接阶段主要负责把类的二进制数据合并到JRE中,分为如下三个阶段:
2.1 验证:用于检验加载的类是否有正确的内部结构,并和其他类协调一致,并且不会危害虚拟机自身的安全。
①文件格式验证:主要是验证字节流是否符合Class文件格式的规范,并且能被当前版本的虚拟机处理。
②元数据验证:对字节码描述的信息进行语义分析,保证其描述的信息符合java语言规范的要求。
③字节码验证:通过数据流和控制流分析,确定程序语义是合法的、符合逻辑的。对类的方法体进行校验分析,保证被校验类的方法在运行时不会做出危害虚拟机安全的事件。
④对类自身以外的信息进行匹配性校验,发生在解析阶段。
2.2 准备:负责为类的变量分配内存并设置类变量初始值。
2.3 解析:将类的二进制数据中的符号引用替换成直接引用。
3、初始化
主要是对类变量进行初始化,对类变量指定初始值有两种方式:一是声明类变量时指定,二是使用静态初始化块为类变量指定。
类加载时机:
1、创建类的实例,例如使用new操作符来创建实例
2、调用某个类的类方法
3、访问某个类或接口的类变量,或为该类变量赋值。
4、使用反射方式调用。