Bohr-L Bohr-L
首页
技术
常见面试题
收藏
  • 分类
  • 标签
  • 归档
GitHub (opens new window)

刘博

I'm a slow walker, But I never walk backwards.
首页
技术
常见面试题
收藏
  • 分类
  • 标签
  • 归档
GitHub (opens new window)
  • 数据处理与存储类

  • Spring 生态类

  • 缓存问题类

  • 多线程类

  • JVM 类

    • JVM 中一次完整的 GC 流程(从 ygc 到 fgc)是怎样的
    • 如何判断对象可以被回收
    • 你知道哪些垃圾收集算法
      • 虚拟机为什么使用元空间替换了永久代
      • 简述 CMS 垃圾收集器的工作流程,它有什么优缺点?
      • 简述一下 JVM 的内存模型
      • 说说堆和栈的区别
      • 简述 Java 的对象结构
      • JVM 中的即时编译器(JIT)如何工作?
      • 什么是内存屏障?JVM 如何使用内存屏障保证指令执行顺序?
      • 如何排查和解决 JVM 内存泄漏问题?有哪些常用的工具和方法?
      • JVM 如何处理异常?try-catch-finally 结构在字节码层面是如何实现的?
    • MySQL 类

    • Java 8 + 特性类

    • 其他技术类

    • 常见面试题
    • JVM 类
    刘博
    2025-12-28
    目录

    你知道哪些垃圾收集算法

    垃圾收集算法是 JVM 回收堆内存中死亡对象的核心策略,不同算法适用于不同的内存区域(新生代、老年代),核心目标是 “高效回收内存、减少 STW 时间”,常见算法如下:

    # 1. 标记 - 清除算法(Mark-Sweep)

    • 核心流程:分为 “标记” 和 “清除” 两步:
      1. 标记:通过可达性分析,标记所有存活对象;
      2. 清除:遍历内存区域,清除未被标记的死亡对象,释放内存。
    • 适用场景:老年代(对象存活时间长,死亡对象少,标记和清除效率高);
    • 优点:实现简单,无需移动对象;
    • 缺点:
      • 产生内存碎片:清除后内存中会出现大量不连续的空闲块,当需要分配大对象时,可能因找不到足够大的连续空闲块而触发 FGC;
      • 效率低:需遍历两次内存(标记一次、清除一次),当内存区域大、对象多时,效率低。
    • 典型收集器:CMS 收集器(老年代)。

    # 2. 复制算法(Copying)

    • 核心流程:将内存区域分为两个大小相等的空间(如新生代的 From Survivor 和 To Survivor):
      1. 标记:标记存活对象;
      2. 复制:将存活对象复制到另一个空闲空间(如 From Survivor 的存活对象复制到 To Survivor);
      3. 清空:清空原空间的所有对象(死亡对象和存活对象已复制)。
    • 适用场景:新生代(对象朝生夕死,存活对象少,复制成本低);
    • 优点:
      • 无内存碎片:复制后空闲空间是连续的,便于大对象分配;
      • 效率高:只需复制存活对象,且清空原空间时无需遍历,直接覆盖;
    • 缺点:
      • 内存利用率低:需将内存分为两个相等空间,总有一个空间空闲(如新生代的 Survivor 区,利用率仅 50%);
      • 不适合存活对象多的区域:若存活对象多(如老年代),复制成本高,效率低。
    • 典型收集器:Serial 收集器(新生代)、ParNew 收集器(新生代)。

    # 3. 标记 - 整理算法(Mark-Compact)

    • 核心流程:在 “标记 - 清除” 算法基础上增加 “整理” 步骤,解决内存碎片问题:
      1. 标记:标记所有存活对象;
      2. 整理:将存活对象向内存一端移动,使存活对象紧凑排列;
      3. 清除:清空内存另一端的死亡对象,释放连续内存。
    • 适用场景:老年代(存活对象多,需避免内存碎片);
    • 优点:
      • 无内存碎片:存活对象紧凑排列,空闲空间连续;
      • 内存利用率高:无需划分两个相等空间,内存全部可用;
    • 缺点:
      • STW 时间长:整理步骤需要移动对象,且需更新对象的引用地址(如 A 引用 B,B 移动后 A 的引用需指向新地址),操作复杂,耗时久;
      • 效率低于复制算法:比复制算法多了 “整理” 步骤。
    • 典型收集器:Serial Old 收集器(老年代)、Parallel Old 收集器(老年代)。

    # 4. 分代收集算法(Generational Collection)

    • 核心思想:基于 “大部分对象朝生夕死” 和 “存活对象逐渐晋升老年代” 的规律,将堆内存分为新生代和老年代,不同代采用不同 GC 算法:
      • 新生代:用复制算法(存活对象少,复制成本低);
      • 老年代:用标记 - 清除算法或标记 - 整理算法(存活对象多,避免内存碎片);
    • 优点:结合不同算法的优势,提升整体 GC 效率;
    • 缺点:依赖分代模型,若对象存活周期不符合 “朝生夕死”(如大量长存活对象),效率会下降;
    • 典型收集器:所有主流收集器(如 CMS、G1、ZGC)均基于分代收集思想(G1、ZGC 支持部分代回收)。

    # 5. 分区收集算法(Region-Based Collection)

    • 核心思想:将堆内存分为多个大小相等的 “Region”(区域,如 G1 的 Region 大小为 1-32MB),每个 Region 可独立进行 GC,无需回收整个堆:
      1. 每个 Region 可标记为新生代(Eden/Survivor)或老年代,动态调整;
      2. GC 时,优先回收垃圾比例高的 Region(“Garbage First”,如 G1 收集器),减少 STW 时间;
    • 适用场景:大堆内存(如堆内存 10GB 以上),避免全堆 GC 导致的长时间 STW;
    • 优点:
      • 支持部分代回收:无需回收整个堆,STW 时间可控;
      • 灵活适配对象分布:Region 的代属性可动态调整,适合复杂对象存活场景;
    • 缺点:
      • 实现复杂:需管理多个 Region 的状态、引用关系(如跨 Region 引用需用 Remembered Set 记录);
      • 内存开销大:需维护 Remembered Set 等额外数据结构。
    • 典型收集器:G1 收集器、ZGC 收集器、Shenandoah 收集器。

    # 6. 增量收集算法(Incremental Collection)

    • 核心思想:将 GC 过程拆分为多个小步骤,与用户线程交替执行,减少单次 STW 时间(如将 “标记” 步骤拆分为 10 次,每次执行 10%,然后切换到用户线程);
    • 适用场景:早期 JVM(如 JDK 1.2 之前),用于低配置设备(如手机),避免长时间 STW 影响用户体验;
    • 优点:单次 STW 时间短,用户线程响应性好;
    • 缺点:
      • 总 GC 时间长:GC 步骤拆分后,上下文切换成本高,整体 GC 耗时增加;
      • 可能导致 “浮动垃圾”:GC 步骤间隙,用户线程可能产生新的死亡对象,需下次 GC 回收;
    • 现状:已被并发收集算法替代(如 CMS、G1),现代 JVM 很少使用。

    # 7. 并发收集算法(Concurrent Collection)

    • 核心思想:GC 的大部分步骤(如标记、清除)与用户线程并发执行,仅在关键步骤(如初始标记、重新标记)暂停用户线程(STW),大幅减少 STW 时间;
    • 适用场景:高并发应用(如电商、金融),对 STW 时间敏感;
    • 优点:STW 时间短(毫秒级),用户线程影响小;
    • 缺点:
      • 实现复杂:需处理 GC 线程与用户线程的并发冲突(如对象引用变动),需维护额外数据结构(如 CMS 的 Card Table、G1 的 Remembered Set);
      • 可能产生 “浮动垃圾”:并发执行时,用户线程产生的新死亡对象需下次 GC 回收;
      • 内存占用高:额外数据结构(如 Card Table)占用内存;
    • 典型收集器:CMS 收集器、G1 收集器、ZGC 收集器。

    上次更新: 12/30/2025
    如何判断对象可以被回收
    虚拟机为什么使用元空间替换了永久代

    ← 如何判断对象可以被回收 虚拟机为什么使用元空间替换了永久代→

    最近更新
    01
    CPU 使用率较高排查和解决
    12-29
    02
    JVM OOM 问题如何排查和解决
    12-29
    03
    接口防刷怎么实现?
    12-29
    更多文章>
    Theme by Vdoing | Copyright © 2025-2026 Bohr-L's note
    • 跟随系统
    • 浅色模式
    • 深色模式
    • 阅读模式