垃圾收集算法(GC) 学习指南

不同的内存区域采用不同的算法 不同的算法决定了垃圾收集的效率 效果
垃圾收集算法共有四种 标记-清除算法 复制算法 标记-整理算法 分代收集算法

标记-清除算法

1 标记阶段 标记出所有需要回收的对象
2 清除阶段 统一清除 回收所有被标记对象
标记阶段主要分为:(先进行可达性分析)
	第一次标记 & 筛选
	第二次标记 & 筛选
优点 算法简单 实现简单
缺点 效率问题:标记和清楚两个过程效率不高  空间问题:标记清除后 会产生大量不连续的空间碎片
这导致后续程序需要分配大空间对象时 无法找到足够大的连续内存 从而触发另一次GC 非常浪费资源
应用于对象存活率低 垃圾回收行为频率低的场景 比如老年代区

二 复制算法

为了解决标记-清除算法中的效率空间问题
将内存分为大小相等的两块 每次使用其中一块 每当使用的这块内存空间用尽 就将这块内存上还存活的对	象移动到另一块没使用的内存上 最终将已用的那一块内存一次性清理掉
优点 解决了标记-清除算法效率低的问题 解决了标记-清除算法产生不连续内存空间的问题
缺点 可用内存变为原来的一半 当对象存活率高的情况下需要做较多的复制操作 效率变低
应用场景 对象存活率低&需要频繁GC的区域 比如新生代区域(新生代区域在进行垃圾回收时,98%对象都必须得回收)
改进方法 8:1:1 Eden:FromSurvivor:ToSurvivor
假如 Eden、From Survivor区域上存活对象所需内存大小 > To Survivor区域,依赖老年代内存区域 做 内存分配担保。即To Survivor区域 存不下来的对象 会通过 内存分配担保机制 暂时保存在老年代

三 标记-整理算法

类似标记-清楚算法 但是多了一步整理内存 三个阶段
	1 标记阶段 标记所有需要回收的对象
	2 整理阶段 让所有存活对象都向一端移动
	3清除阶段 统一清除回收端以外的对象
优点:解决了标记-清除算法效率低的问题 一次性清除端以外的对象 解决了标记-清除算法产生不连续空间的问题,将已使用内存上的存活对象 移动到栈顶的指针,按顺序分配内存即可
应用场景 对象存活率低 GC频率低的场景 比如老年代区域

四分代收集算法

主流虚拟机均用此方法
根据对象存活周期不同 将java堆分为新生代 老年代 分配比例1:2,新生代内部(Eden:FromS:Tos=8:1:1)
根据两块区域的特点选择不同的GC算法
	新生代 复制算法(Eden空间不足触发)
	老年代 主要为标记-整理算法 辅助为标记-清除算法(老年代空间不足触发)
新建对象一般会被分配到Eden FromS区 (大对象 比如很长的字符串和数组会直接进入老年代 这是为了避	免新生代产生大量的内存复制行为)
这些对象如果经历过一次MinorGC仍然存活 就进入Survivor区 每经历一次GC 该对象年龄就+1 当对象年龄达到阈值(默认15)就移动到老年区 另一种情况是动态年龄判断 即MinorGC后 Survivor区中所有年龄为N的对象所占总和达到S区一半时,所有年龄大于等于N的对象都进入老年代
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值