垃圾收集算法

文章详细介绍了Java虚拟机中的垃圾收集算法,包括分代收集理论,它基于弱、强分代假说将堆分为新生代和老年代。标记-清楚、标记-复制和标记-整理等不同算法各有优缺点,分别适用于不同场景。新生代的Appel式回收和老年代的标记-整理算法被广泛使用。此外,文章还提到了收集器如ParallelScavenge和CMS的关注点以及如何处理内存碎片。
摘要由CSDN通过智能技术生成

GC算法分为引用计数式垃圾收集追踪式垃圾收集(Java虚拟机涉及)。

1.分代收集理论

一套符合大多数程序运行实际情况的经验法则。

建立在三个假说之上:

  1. 弱分代假说:绝大多数对象都是朝生夕灭的。
  2. 强分代假说:熬过越多次GC的对象就越难以消亡。
  3. 跨分代假说:跨代引用相当于同代引用来说仅占极少数。

强、弱分代引用假说奠定了多款GC的一致设计原则:收集器应该将Java堆划出不同的区域,然后将回收对象依据年龄(熬过GC的次数)分配到不同的区域之中存储。

分代收集理论在JVM中将Java堆划分为新生代老年代

对象不是孤立的,对象之间会存在跨代引用,从而引入跨代引用假说。

根据这条假说,不应该为了少量的跨代引用去扫描整个老年代,只需在新生代上建立一个全局的数据结构(记忆集)。他将老年代划分为若干个小块,标识出老年代的哪一块内存会存在跨代引用。

一些基本概念:

  • 部分收集:指目标不是完整收集整个Java堆的GC。其又分为新生代收集和老年代收集。
  • 新生代收集:指目标只是新生代的GC。
  • 老年代收集:指目标只是老年代的GC。
  • 混合收集:指目标是收集整个新生代和部分老年代的GC。目前只有G1收集器会有这种行为。
  • 整堆收集:收集整个Java堆和方法区的GC。

2.标记-清楚算法

两种方法:

标记出所有需要回收的对象,统一回收掉所有被标记的对象。

标记存活的对象,统一回收所有未被标记的对象。

缺点:

  1. 执行效率不稳定。如果Java堆包含大量对象,而其中大部分被回收,标记和清除效率随对象数量增长而降低。
  2. 内存空间的碎片化问题。

3.标记-复制算法

解决标记-清除算法面对大量可回收对象时执行效率低的问题。

1)半区复制

将内存按容量划分为大小相等的两块,每次只使用其中的一块。当一块用完后,将存活的对象复制到另一块上,将已使用的空间清除掉。

优点:实现简单,运行高效。

缺点:将可用的存储空间缩小了一半,空间浪费。

2)Appel式回收(新生代)

HotSpot虚拟机采用这种策略设计新生代内存布局。

Appel式回收:把新生代分为一块较大的Eden空间和两块较小的Survivor空间。每次分配内存只使用Eden和一块Survivor。当发生GC时,将Eden和一块Survivor中存活的对象一次性复制到另一块Survivor中,然后清掉Eden和一块Survivor。

HotSpot虚拟机默认Eden:Survivor空间为8:1。

逃生门设计:当Survivor空间不足以容纳一次Minor GC之后的存活对象时,需要依赖其他内存区域(大多数为老年代),进行分配担保。

4.标记-整理算法(老年代)

标记存活的对象,让所有存活的对象都向内存空间一端移动,直接清理掉边界以外的内存。

标记-整理是移动式算法,移动存活对象并更新所有引用对象的地方,负担很重,且必须全程暂停用户应用程序。

吞吐量:赋值器与收集器效率的总和。

HotSpot虚拟机中关注吞吐量的Parallel Scavenge收集器基于标记-整理算法,关注延迟的CMS收集器基于标记-清除算法。

和稀泥式:虚拟机平时采用标记-清除算法。当碎片化程度达到影响对象分配时,采用标记-整理算法收集一次。CMS收集器采用这种方法。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值