JVM:java virtua Machine
jdk中包含了 JVM 和 "屏蔽操作系统差异的组件"
- jvm 各个操作系统之上是一致的
- "屏蔽操作系统差异的组件" : 在各个PC上各不相同(如不同系统需要下载不同版本的JDK)
类的生命周期
生命周期:类的加载 --> 连接 --> 初始化 --> 使用 --> 卸载
-
类的加载
查找并加载类的二进制数据(class 文件)。
将硬盘上的 class 文件加载到 JVM 的内存当中。
-
连接:确定类与类之间的关系。
例如现在有 Student 对象和 Address 对象,学生对象包含了 address 属性
student.setAddress(address);
连接阶段有三个子阶段:
-
验证
拿到一个 .class 文件,验证 .class 文件的正确性。防止人为手动修改 class 文件内容。
-
准备
- 为 static 静态变量分配内存,并赋初始化默认值。
static int num = 10; //在准备阶段,会将 num 赋值为0,之后(初始化阶段)再将0修改为 10;
-
在准备阶段,JVM中只有类,没有对象。
初始话顺序:static --> 非static --> 构造方法
public class Student{ //在准备阶段将 age = 0 static int age; String name; }
-
解析
将类中的符号引用,转为直接引用。
比如 Student 类的全限定类名为
cn.wengzi.pojo.Student
。 前期阶段,还不知道某个类具体的内存地址,只能使用
cn.wengzi.pojo.Student
来代替 Student 类,这种方式称为符号引用。 在解析阶段,JVM就可以将
cn.wengzi.pojo.Student
映射为实际的内存地址,之后就会用内存地址来代替 Student 类,这种使用内存地址来使用类的方式称为符号引用。
-
-
初始化阶段
为静态变量赋正确的值
static int num = 10; //在连接的准备阶段中,会将 num 赋值为0. //在初始阶段再将0修改为 10;
-
使用
在使用类时,其实用的是类的对象 : Student student = new Student();
- 对象的初始化
- 对象的垃圾回收
- 对象的销毁
-
卸载
- 该类所有的实例都已经被回收,也就是java堆中不存在该类的任何实例。
- 加载该类的ClassLoader已经被回收。
- 该类对应的java.lang.Class对象没有任何地方被引用,无法在任何地方通过反射访问该类的方法。
如果以上三个条件全部满足,jvm就会在方法区垃圾回收的时候对类进行卸载,类的卸载过程其实就是在方法区中清空类信息,java类的整个生命周期就结束了。
JVM 结束生命周期的时机:
- 正常结束。
- 异常结束/错误。
- System.exit(); 强行终止类的生命周期
- 操作系统异常