JVM垃圾收集算法

本文介绍了垃圾收集的几种算法,如引用计数、可达性分析、标记-清除、标记-复制和标记-整理,以及它们各自的优缺点。讨论了新生代与老年代的选择,安全点和安全区域的概念,以及如何通过卡表和写屏障来提高效率。此外,还提到了内存管理中的挑战,如循环引用和空间碎片化。
摘要由CSDN通过智能技术生成

引用计数

每个对象添加一个计数器,对象引用时,计数器+1,失效时-1,根据是否为0判断(无法解决循环引用问题)

可达性分析算法

选择根节点GC root进行搜索,与GC root没有可达路径的对象则进行清除,解决了循环调用问题。

分代收集理论

弱分代(朝夕生灭)

强分代(熬过越多次垃圾收集过程的对象越难以消亡)

跨代引用(存在相互引用关系的两个对象,倾向于同时生存或者同时消亡,随着年龄增长晋升到老年代,跨代引用消除 [标记老年代中存在跨代引用的内存,Minor GC时只需扫描这一小块内存)–相对于同代引用仅占少数

标记-清除算法

标记部分对象,同意回收或者使标记对象存活(造成空间碎片化)

标记-复制算法

将内存分为若干块,每次一块内存用完则将其中存活对象复制到另一块上,再将原来的内存块全部清除(运行高效,但是将可用内存缩小一半,空间浪费大 ------复制算法在对象存活率较高时需要较多复制操作,降低效率,并且需要进行分配担保,防止原块上对象100%存活的极端情况)

标记-整理算法

将存活对象都向内存空间的一端移动,然后清理掉边界以外的内存(移动时需要全程暂停程序—“Stop the world”)

和稀泥

多数时间采用标记-清除算法,空间碎片化程度大时执行一次标记-整理算法。

  • [ ]

在新生代中,每次垃圾收集时都发现有大批对象死去,只有少量存活,那就选用复制算法,只需要付出少量存活对象的复制成本就可以完成收集。

在老年代中,因为对象存活率高、没有额外空间对它进行分配担保,就必须使用标记-清理算法或者标记-整理算法来进行回收。

安全点

程序运行到达安全点才能进行暂停回收对象。为了让线程都跑到安全点暂停:

1. 抢先式中断
垃圾收集发生时,暂停全部线程,再开启未到达安全点的线程,直至到达安全点
3. 主动式中断
中断线程时,各个线程主动轮询一个标志位,一旦发现中断标志为真则在最近安全点主动中断挂起。

安全区域(拉伸的安全点)

线程进入安全区域时主动等待,直至虚拟机完成根节点枚举。

记忆集与卡表

记录精度

  1. 字长精度
    精确到一个机器字长(该字包涵跨代指针)
  2. 对象精度
    精确到一个对象(该对象包涵跨代指针)
  3. 卡精度(卡表)
    内存块分为卡页(HotSpot中为2的九次方幂大小字节数)
    卡页内存在跨代指针则将对应卡表数组元素置1(元素变脏)垃圾收集时只需要扫描变脏的卡页,将其加入GC Roots

写屏障

类似spring中AOP切面,防止活动对象漏掉未被压入标记栈
在这里插入图片描述
(A所有子对象遍历完后A出栈,此时B又取消对C的连接,导致C对象被遗漏,使用写屏障防止活动对象被遗漏

write_barrier(obj, field, newobj){
        if(newobj.mark == FALSE)
            newobj.mark = TRUE
            push(newobj, $mark_stack)
        *field = newobj
    }
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值