gc日志不直接输出“对象回收率”,但可通过内存字段计算每次gc的回收比例:①区域内回收率=(gc前使用量−gc后使用量)÷gc前使用量×100%,如年轻代90%;②绝对内存回收率=回收字节数÷堆总容量×100%,如25.4%。

JVM GC 日志中不直接输出“对象回收率”这个数值,但可以通过日志中的关键内存数据手动计算出**每次GC的内存回收比例**,它在实践中常被当作对象回收效率的近似指标。
看懂日志里的核心内存字段
以典型的 G1 或 Parallel GC 日志片段为例:
[GC (Allocation Failure) [PSYoungGen: 123456K->12345K(131072K)] 234567K->134567K(393216K), 0.0456789 secs]
重点关注三组“使用量→回收后使用量(总容量)”结构:
-
PSYoungGen(年轻代):123456K → 12345K(131072K)
说明:GC前已用 123456K,GC后剩 12345K,即回收了 123456 − 12345 = 111111K - 整个堆(234567K→134567K):回收了 234567 − 134567 = 100000K
- 括号内是对应区域的总容量(如 131072K),用于算占比分母
回收率的两种常用计算方式
① 区域内回收率(推荐,反映该代清理效果)
公式:(GC前使用量 − GC后使用量) ÷ GC前使用量 × 100%
例如年轻代:
(123456 − 12345) ÷ 123456 ≈ 90.0% —— 表示本次 Minor GC 清除了约 90% 的年轻代存活对象
② 绝对内存回收率(辅助参考)
公式:回收字节数 ÷ 堆总容量 × 100%
上例中:100000K ÷ 393216K ≈ 25.4% —— 表示本次GC释放了全堆约 1/4 的空间
注意几个关键点
- 回收率高 ≠ 系统健康:如果老年代回收率长期接近 0%,可能说明对象晋升过多或存在内存泄漏
- 年轻代回收率持续低于 70%,需关注对象是否过早晋升、Survivor 区是否太小或对象生命周期异常延长
- Full GC 回收率若低于 5%,大概率存在大对象堆积或类加载器泄漏,应结合 jmap 或 MAT 分析堆快照
- 日志中没有“回收对象个数”,只有内存大小;JVM 不统计对象数量级回收率,所以所有计算都基于字节维度











