目录
- 1.引用计数法
-
- 2.可达性分析算法
- 2.1 原理
- 2.2 GC Roots
- 2.3 标记-清除阶段
- 3.引用类型
1.引用计数法
1.1 原理
- 1.为每个对象创建一个引用计数,当有对象引用该对象时,计数器加1。
- 2.当引用失效时,计数器减1。
- 3.当计数器的值为0时,表示该对象没有被任何对象引用,因此可以被回收。
1.2 缺点
- 1.引用计数法存在循环引用的问题。
- 2.如果两个对象相互引用,它们的引用计数将不会为0,导致无法回收,进而造成内存泄漏。
- 3.JVM中的主流垃圾回收器通常不单独使用这种方法。
2.可达性分析算法
2.1 原理
- 1.可达性分析算法是JVM判断对象是否可回收的核心算法。
- 2.它从一组称为GC Roots的根对象开始,通过递归方式遍历引用图,判断哪些对象是可达的,哪些是不可达的。
- 3.如果一个对象从GC Roots无法到达,则该对象被视为不可达,可以被垃圾回收。
2.2 GC Roots
- 1.GC Roots是可达性分析算法的起点,包括以下几种对象:
- 2.栈帧中的局部变量:当前正在执行的方法中的所有局部变量和参数。
- 3.方法区中的静态变量:所有类的静态属性(类变量)和常量引用的对象。
- 4.本地方法栈中的JNI(Java Native Interface)引用:通过JNI调用的本地代码中持有的对象引用。
- 5.活动线程:正在运行的线程本身也被视为GC Roots。
2.3 标记-清除阶段
- 1.可达性分析算法通常分为标记和清除两个阶段:
- 2.标记阶段:从GC Roots开始遍历所有可达的对象,并进行标记。JVM会使用一个标志位来标记对象是否可达。
- 3.清除阶段:在标记完成后,JVM遍历堆中的所有对象,将未被标记的对象视为垃圾,清除这些对象所占用的内存。
3.引用类型
- 1.在进行可达性分析时,JVM还考虑了不同的引用类型,这些引用类型决定了对象的可达性及其回收时机。
- 2.强引用:强引用是Java中的默认引用类型。只要一个对象有强引用存在,垃圾回收器就不会回收它。
- 3.软引用:使用SoftReference类表示。只有在内存不足时,JVM才会回收被软引用持有的对象。软引用通常用于实现内存敏感的缓存。
- 4.弱引用:使用WeakReference类表示。只要垃圾回收器发现一个对象只被弱引用持有,就会回收该对象。弱引用主要用于实现规范化映射,如WeakHashMap。
- 5.虚引用:使用PhantomReference类表示。虚引用是最弱的一种引用,无法通过虚引用访问对象。虚引用的存在主要用于跟踪对象被垃圾回收的状态,可以在对象被回收后执行一些清理操作。