Follow me on GitHub

可达性分析

垃圾回收有 3 个基本问题:

  1. 哪些对象需要回收?
  2. 何时回收?
  3. 如何回收?

垃圾回收是回收 非存活 对象,可达性分析可以判断一个对象 是否存活,用来解决第 1 个问题。

算法基本思路只有两步:

  1. 确定一组由 GC root 引用组成的集合 X;
  2. 以 X 集合中的引用为起点开始搜索,搜索走过的 引用路径 称为 引用链

若对象 A 与任意 GC root 都没有引用链相连,则该对象已经不再存活。

什么是 GC root 呢,RednaxelaFX 在知乎解释为:

所谓“GC roots”,或者说 tracing GC 的“根集合”,就是一组 必须活跃的引用

因为在某时某刻,GC root 引用集合 必须活跃,所以直接 or 间接被 GC root 引用的 上的对象也 必须活跃,这些对象不能被垃圾回收。

不同虚拟机实现可作为 GC root 的引用各不相同,大致分为:

  • 执行上下文
    • 所有线程的当前栈帧中指向 中对象的引用;
    • 正在被调用的方法 所引用的堆上对象;
    • 即虚拟机栈、本地方法栈中当前栈帧的 局部变量表(含方法入参、局部变量、临时值);
  • 全局性引用/静态数据结构
    • 方法区中 类静态字段
    • 方法区中 常量
  • JNI 相关
    • JNI Local:JNI 方法的局部变量与参数;
    • JNI Global:全局 JNI 引用;

要正确完成垃圾回收,可达性分析中的 GC root 集合必须是 完整 的,以上只是可作为 GC root 引用的举例,实际虚拟机实现中 GC root 范围更加广泛。