🌟 ZGC 核心知识点 🌟

118 阅读3分钟

1. 核心设计目标 🎯

  • 超低延迟(Low Latency) :ZGC(Z Garbage Collector)主打 亚毫秒级停顿(通常 < 10ms),适合大堆内存(TB级)场景。
  • 可扩展性:堆内存越大,ZGC 的停顿时间几乎不增长。
  • 并发性:大部分垃圾回收操作(标记、转移、重定位)与应用线程并发执行。

2. 关键技术特性 🔧

  • Colored Pointers(颜色指针)  🎨
    通过指针元数据(4个标志位)标记对象状态(Marked、Remapped、Finalizable),无需额外内存存储标记信息。
  • Load Barriers(读屏障)  🚧
    在对象访问时触发屏障,确保应用线程看到一致的内存视图,解决并发转移时的对象引用问题。
  • Region 分区 🧩
    内存划分为 2MB/32MB/... 动态大小 Region(类似 G1),但更灵活,无分代概念(JDK 21 前)。
  • NUMA 感知 �
    优化非统一内存访问(NUMA)架构,优先在本地内存分配对象。

3. 工作阶段 🔄

  1. 初始标记(Pause Mark Start) :短暂 STW,标记根对象。
  2. 并发标记:与应用线程并发标记可达对象。
  3. 再标记(Pause Mark End) :短暂 STW,处理漏标。
  4. 并发转移准备:选择待回收的 Region。
  5. 初始转移(Pause Relocate Start) :短暂 STW,转移根对象。
  6. 并发转移:并发迁移对象到新 Region。
  7. 重定位表清理:清理旧地址引用。

🆚 ZGC vs G1 对比 🆚

特性ZGCG1
目标低延迟(亚毫秒级)平衡吞吐与延迟(百毫秒级)
最大堆内存TB 级百 GB 级
分代模型无分代(JDK 21 前)分代(Young/Old)
内存布局动态 Region(2MB/32MB)固定 Region(1MB~32MB)
标记/转移算法并发标记 + 并发转移并行标记 + 增量转移
停顿时间控制严格亚毫秒级通过 MaxGCPauseMillis 目标控制
Full GC 触发极少(依赖并发处理)可能触发(如晋升失败)
内存碎片无(并发压缩)可能有(需 Full GC 处理)
适用场景大堆 + 严格低延迟(如金融交易)中等堆 + 吞吐敏感场景

🛠️ 调优项与参数 🛠️

ZGC 调优 ⚙️

  1. 基础参数

    bash

    复制

    -XX:+UseZGC                  # 启用 ZGC
    -Xmx -Xms                    # 堆大小(建议设为相同值)
    -XX:ConcGCThreads=<N>        # 并发 GC 线程数(默认=总CPU的1/8)
    -XX:ParallelGCThreads=<N>    # 并行阶段线程数(默认=总CPU的60%)
    
  2. 延迟敏感场景 ⏳:

    bash

    复制

    -XX:ZAllocationSpikeTolerance=2  # 分配速率波动容忍度(默认2)
    -XX:ZCollectionInterval=300      # 强制触发 GC 周期(秒,默认不限制)
    
  3. 大堆优化 🚀:

    bash

    复制

    -XX:ZUncommitDelay=<seconds>     # 空闲内存归还延迟(默认300s)
    -XX:+ZProactive                  # 主动触发 GC(默认开启)
    

G1 调优 ⚙️

  1. 基础参数

    bash

    复制

    -XX:+UseG1GC                  # 启用 G1
    -XX:MaxGCPauseMillis=200      # 目标停顿时间(默认200ms)
    -XX:InitiatingHeapOccupancyPercent=45  # 触发并发标记的堆占用比
    
  2. 避免 Full GC 🚫:

    bash

    复制

    -XX:G1ReservePercent=15       # 预留内存防晋升失败
    -XX:+ParallelRefProcEnabled   # 并行处理引用对象
    

💡 调优建议 💡

  • ZGC:优先确保堆足够大(避免频繁 GC),监控 ZGC Cycles 和 GC Pauses,关注 Allocation Stall 事件。
  • G1:通过 -XX:MaxGCPauseMillis 平衡吞吐和延迟,避免 Old 区过快填满(调整 IHOP)。

🌈 总结 🌈

  • ZGC 适合 超大堆 + 严格低延迟 场景,无分代设计简化调优,但需高版本 JDK(JDK 15+ 生产推荐)。
  • G1 更成熟,适合 中等堆 + 吞吐优先,分代模型对短期对象友好,但 Full GC 风险需警惕。