垃圾收集器底层算法实现

12 篇文章 0 订阅


讲具体的底层算法前,先说明一个概念–三色标记

一、三色标记

根据可达性分析,将“是否访问过”作为条件标记成以下三种颜色:

  • 黑色:表示对象已经被垃圾收集器访问过,而且这个对象的所有引用都已经扫描过。黑色的对象代表已经扫描过,它是安全存活的,如果有其他对象引用指向了黑色对象,无序重新扫描一遍。黑色对象不可能直接(不经过灰色对象)指向某个白色对象。
  • 灰色:表示对象已经被垃圾收集器访问过,但这个对象上至少存在一个引用未被扫描过。
  • 白色:表示对象尚未被垃圾收集器访问过。显然在可达性分析刚刚开始的阶段,所有的对象都是白色的,若在分析结束的阶段,对象仍然是白色的,说明该对象没有被引用,即不可达。

二、漏标处理办法

漏标会导致被引用的对象被当成垃圾误删除,这是严重的BUG,必须解决。解决办法主要有两种:增量更新、原始快照

1、增量更新

增量更新就是当黑色对象插入新的指向白色对象的引用关系时,就将这个新插入的引用记录下来,等并发扫描结束之后,再将这些记录过的引用关系中黑色的对象为gc roots,重新扫描一次。这可以简化理解为,黑色对象一旦插入了指向白色对象的引用之后,它的颜色就变成灰色的了。

2、原始快照

原始快照就是当灰色对象要删除指向白色对象的引用关系时,就将这个要删除的引用记录下来,再并发扫描结束之后,再将这些记录过的引用关系中灰色对象为gc roots重新扫描一遍,这样就能扫描到白色的对象,将白色的对象直接标记为黑色(目的就是让这种对象在本轮GC清理中能存活下来,待下一轮GC的时候重新扫描,这个对象也有可能是浮动垃圾)

以上无论是对引用关系的记录还是删除,虚拟机的记录操作都是通过写屏障来实现的

三、读写屏障

1、写屏障

写屏障是基于类似AOP的思想实现的,大体上就是在新增对象的引用之后、置空对象的引用之前添加一个方法来记录原来的操作数据,以便重新标记的时候来处理问题。

2、读屏障

和写屏障的原理类似,读屏障是针对第一步,当读取成员变量的时候一律记录下来,以便之后处理问题。

四、记忆集与卡表

这种算法主要是处理可达性扫描时出现的跨代引用的问题

在新生代引入记录集(Remember Set)的数据结构(记录从非收集区到收集区的指针集合),避免把整个老年代加入GCRoots的扫描范围。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

缘丶沐逸尘

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值