资讯详情

JVM 垃圾回收机制

📅 2026/11/2 1:55:08 | 华诺云谱 👁 阅读
JVM 垃圾回收机制
一、什么是 JVM 垃圾回收首先我们思考一个问题在 Java 中我们创建对象时通常不需要手动释放内存。例如public class Main { public static void main(String[] args) { User user new User(); user new User(); user null; } }这里发生了什么new User()创建第一个 User 对象。user new User()创建第二个 User 对象第一个对象不再被变量 user 引用。user null第二个对象也不再被 user 引用。那么问题来了这两个 User 对象占用的内存什么时候释放这就是 JVM 垃圾回收机制要解决的问题。简单来说JVM 垃圾回收GC就是自动识别不再使用的对象并回收它们占用的内存空间。它有两个核心任务找出哪些对象已经没有用了。回收这些对象占用的内存。二、JVM 如何判断一个对象是不是垃圾这是 GC 最核心的问题。JVM 主要涉及两种判断思路1. 引用计数法原理非常简单给每个对象维护一个引用计数器。每当有一个引用指向该对象计数器就加 1。每当有一个引用失效计数器就减 1。当计数器为 0 时就认为对象可以被回收。例如User user1 new User(); User user2 user1;此时user1 和 user2 两个变量都指向同一个 Use r对象两个变量都指向同一个对象因此引用计数为 2。但是引用计数法有一个严重问题无法解决循环引用问题。例如class A { B b; } class B { A a; } public class Main { public static void main(String[] args) { A a new A(); B b new B(); a.b b; b.a a; a null; b null; } }此时A 对象引用着 B 对象。B 对象引用着 A 对象。外部已经没有任何变量引用它们。但是两个对象的引用计数都不为 0。所以引用计数法无法判断它们是否已经成为垃圾。2. 可达性分析算法这是 HotSpot JVM 判断对象是否存活的核心方法。它的基本思想是从一组被称为 GC Roots 的根对象出发向下搜索所有能够到达的对象。能够被访问到的对象说明仍然可能被使用。无法被访问到的对象就可以被判定为不可达对象。看下面这个示意图常见的 GC Roots 有哪些1、虚拟机栈中引用的对象例如局部变量引用的对象。2、方法区中类静态属性引用的对象。3、方法区中常量引用的对象。4、本地方法栈中 JNI 引用的对象。5、JVM 内部的一些引用对象例如活动线程、系统类加载器等。注意对象不可达不代表一定会立即被回收还需要考虑对象的终结处理等特殊情况。三、JVM 垃圾回收主要发生在哪里理解 GC必须先了解JVM 堆内存结构。Java 对象主要分配在堆内存中而堆通常按照对象生命周期特点进行分代管理。传统分代模型主要分为区域作用新生代 Young Generation存放新创建的对象老年代 Old Generation存放长期存活的对象新生代又可以分成Eden 区大多数新对象首先分配在这里。Survivor 0S0存放经过 GC 后存活的对象。Survivor 1S1与 S0 交替使用。为什么要这样设计因为 JVM 发现大多数 Java 对象都是朝生夕死的。例如public void test() { for (int i 0; i 10000; i) { User user new User(); } }循环创建的很多对象在使用结束后就没有引用了。因此把新生代和老年代分开可以针对不同生命周期的对象采用不同的回收策略。四、JVM 垃圾回收有哪些算法1. 标记-清除算法Mark-Sweep分为两个步骤标记找到所有需要保留的对象。清除回收没有被标记的对象。优点实现简单。不需要移动存活对象。缺点会产生大量内存碎片。分配大对象时可能找不到连续的内存空间。2. 标记-复制算法Mark-Copy核心思想将内存划分为两块每次只使用其中一块。当发生 GC 时找出存活对象。将存活对象复制到另一块内存。清空原来的内存区域。优点不会产生内存碎片。回收过程相对简单。缺点需要额外的内存空间。存活对象较多时复制成本较高。因此这种算法很适合新生代因为新生代对象通常存活率比较低。3. 标记-整理算法Mark-Compact核心思想标记所有存活对象。将存活对象向内存一端移动。清理边界之外的内存。优点不会产生内存碎片。不需要额外保留一整块复制空间。缺点需要移动对象。整理过程有一定性能开销。这种算法常用于老年代的垃圾回收实现中。三种算法对比算法优点缺点标记-清除简单内存碎片标记-复制无碎片效率较高需要额外空间标记-整理无碎片移动对象开销五、JVM 垃圾回收器有哪些面讲的是 GC 算法现在讲真正执行垃圾回收工作的组件垃圾回收器。常见的有垃圾回收器特点Serial单线程简单Parallel Scavenge注重吞吐量ParNew新生代并行回收器CMS注重低停顿采用并发标记清除G1面向服务端应用兼顾吞吐量和停顿时间ZGC面向低延迟支持并发回收其中有三个尤其值得学习1. CMSCMS 的主要特点是尽可能减少垃圾回收时应用线程的停顿时间。主要阶段初始标记并发标记重新标记并发清除2. G1G1 将堆划分为多个大小相同的 Region不再简单地按照连续空间划分新生代和老年代。它可以优先回收垃圾最多、回收收益较高的 Region。3. ZGCZGC 是一款低延迟垃圾回收器主要通过并发处理和着色指针等技术减少停顿时间。六、用一个实际案例理解 GC假设我们运行下面的代码public class Main { public static void main(String[] args) { User user1 new User(); User user2 new User(); User user3 new User(); user1 null; user2 null; System.gc(); } }假设三个对象都成功分配在堆中。执行过程注意System.gc()只是向 JVM 提出执行 GC 的建议并不保证立即执行垃圾回收。
📝

华诺云谱内容团队

资深建站顾问 · 行业研究员

10年+企业数字化服务经验,专注智能建站、SEO优化与品牌营销,持续输出建站技巧、行业洞察与营销干货,已帮助5000+企业实现数字化增长。

你可能需要的服务

订阅华诺云谱资讯周报

每周一封,精选建站技巧、SEO与营销干货,直达邮箱。已有 8,000+ 企业主订阅,助你少走弯路。

↑