为什么CMS不作为JDK默认垃圾回收器?CMS的常见问题

1. CMS概念

CMS 是老年代垃圾回收算法,通过标记-清除的方式,=意在通过并发的方式适度减少吞吐量,减少用户线程停顿时间。

2. CMS常见问题

既然CMS可以并发回收垃圾,效率这么高,为什么不作为JDK的默认垃圾回收器?因为CMS存在两个问题。当出现问题时,其回收垃圾效率大打折扣。

1.Memory Fragmentation(内存碎片问题)

因为CMS是用的回收算法是标记清除算法,那就意味着会产生内存碎片。
当内存碎片过多,导致启动单线程serial Old垃圾回收器,单线程意味着效率低。

缓解办法:

CMS收集器提供了-XX:UseCMSCompactAtFullCollection开关参数,用于在CMS收集器不得不进行Full GC时开启内存碎片的合并整理过程。 有参数可以配置有多少次Full GC会堆内存碎片进行整理(-XX:CMSFullGCsBeforeCompaction)

2.Floating Garbage(浮动垃圾)

1.什么是浮动垃圾?

在CMS的并发标记和并发清理阶段,用户线程是还在继续运行的,程序在运行自然就还会伴随有新的垃圾对象不断产生,而这部分的垃圾对象是出现在标记过程结束以后,CMS无法在当次收集中处理掉它们,只好留在下次垃圾收集时再清理掉。这样的垃圾就叫做浮动垃圾。

2.CMS怎么处理浮动垃圾?

由于垃圾收集和用户线程是并发执行的,因此CMS收集器不能像其他收集器那样几乎填满了再进行收集,需要预留一些空间用来保存用户新创建的对象。
在JDK1.5之前老年带使用了68%空间后就会激活CMS收集。
到了JDK6 CMS收集器的启动阀值就已经默认提升到92%。

3.如果预留空间不够怎么办?

CMS垃圾回收报错(Concurrent Model Failure) 并发失败。
启动后备预案:冻结用户线程的执行,临时启用Serial Old收集器来重新进行老年代的垃圾收集。(这样的话时间就会变得很长)

我们应该怎么避免启用Serial Old收集器来重新进行老年代的垃圾收集?

实际应用中可以适当调整参数-XX:CMSInitiatingOccu-pancyFraction 的值来提高CMS的触发百分比,降低内存回收频率获得更好的性能。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值