常见垃圾回收器

本文详细介绍了Java垃圾回收器中的CMS和G1。CMS追求最短停顿时间,分为初始标记、并发标记、重新标记和并发清除四个阶段,适合实时系统。G1则引入了Region概念,目标是可预测的停顿时间和高吞吐量,通过优先回收垃圾占比高的区域来优化性能。两者都采用并发收集,但CMS会有内存碎片问题,而G1使用标记整理算法避免了这个问题。
摘要由CSDN通过智能技术生成

CMS和G1是最重要的

新生代一般采用标记复制,老年代一般采用标记整理算法

Serial:垃圾回收线程只有一个,而且垃圾回收线程工作的时候其他用户线程要停下来

 Parnew:Serial的多线程版本,有多个垃圾回收线程,垃圾回收线程工作的时候,其他用户线程要停下来

Parrel:多个垃圾回收线程,垃圾线程工作的时候其他用户线程需要停止工作,跟Parnew很像。可以设置参数:垃圾收集导致地最大停顿时间和设置吞吐量的大小。通过GC自适应调节策略(虚拟机会根据系统的运行状况动态地设置参数)来达到目标停顿时间和吞吐量。特点是获取最大吞吐量(一共运行100分钟,垃圾回收器花掉3分钟,吞吐量就是97%)

 CMS:第一款实现垃圾收集线程和用户线程同时工作的垃圾回收器,第一款并发收集器,目的是追求最短停顿时间(垃圾回收线程工作导致用户线程停顿的时间

 CMS垃圾回收器工作的的四个阶段:在初始标记和重新标记阶段只能有垃圾回收线程在工作,用户线程需要停止,其他两个阶段垃圾回收线程和用户线程可以同时工作

(1)初始标记:标记和GC Root直接相连的对象,这个阶段很快,但是这个阶段其他用户线程无法工作,还是会发生stop the world(STW)

(2)并发标记:CMS线程会从与GC Roots直接相连的对象出发,遍历所有对象,标记所有存活的对象,这个阶段,CMS线程和其他用户线程在并发执行

(3)重新标记:并发标记阶段由于CMS线程和其他用户线程并行运行,所以其他用户线程可能产生一些新的对象,这些新对象还没有打上是否存活的标记,所以需要标记出这些新对象中存活的对象,这个过程是只有CMS线程,用户线程需要停止工作,所以这个过程会引起STW

(4)并发清除:清除那些没有标记存活的对象,然后最后将这些对象的标记取消

助记:三个标记阶段,一个清除阶段

缺点:这种标记清除的回收方式会产生内存碎片

虽然STW时间很短,但是没法预测,G1就建立了一个预测模型

G1:STW时间可预测,可设置

整个Java堆划分成约2048个大小相同的Region块,继续保留新生代和老年代的概念但是并不是一块连续的内存是新生代,另一块连续的内存是老年代,而是一些不连续的Region组成新生代,另一些不连续的Region组成老年代

G1会跟踪各个Region里存活对象的数量,回收该区域所需要的时间经验值,在后台维护一个优先队列,每次根据允许的收集时间优先回收垃圾对象数量Region(也就是价值最大的垃圾)

总结:

CMS:追求最短的停顿时间,并行的,垃圾回收线程可以和用户线程同时执行(只有初始标记阶段需要暂停用户线程,其他阶段不需要暂停用户线程)     采用三色标记法

G1:HotSpot 开发团队赋予它的使命是未来可以替换掉 CMS 收集器

Serial 单个垃圾回收线程执行(单线程),其他所有用户线程都要停下来

Serial是用于新生代的垃圾回收器,它的老年代版本是Serial old

Parnew多个垃圾回收线程执行(多线程),其他所有用户线程都要停下来

下面是 HotSpot 虚拟机中的 7 个垃圾收集器。上面是新生代的垃圾回收器,下面是老年代的垃圾回收器,G1既可以用于新生代的垃圾回收,也可以用于老年代的垃圾回收,连线表示垃圾收集器可以配合使用

首先要理解以下两个概念:

(1)单线程和多线程:  垃圾收集器只使用一个线程就说垃圾收集器是单线程的,垃圾收集器使用多个线程就说垃圾收集器是多线程

(2)串行和并行:

串行指的是垃圾收集器和用户程序交替执行(执行垃圾收集器的时候需要停止用户程序,即用户现线程和GC线程交替执行),

并行是指垃圾收集器和用户程序同时执行(也就是执行垃圾收集器的时候不需要停止用户程序,即用户线程和GC线程可以一起执行

1.Serial垃圾回收器

Serial(串行)收集器是最基本、历史最悠久的垃圾收集器了,是一个单线程收集器(也就是它只会使用一个垃圾收集线程去完成垃圾收集工作)              

它在进行垃圾收集工作的时候必须暂停其他所有的工作线程( "Stop The World" ),直到它收集结束

 Serial垃圾回收器在回收垃圾的时候,新生代采用标记-复制算法,老年代采用标记-整理算法。

Serial 收集器由于没有线程交互的开销,自然可以获得很高的单线程收集效率

2.ParNew收集器

 Serial 收集器的多线程版本,也是新生代采用标记-复制算法,老年代采用标记-整理算法

 除了 Serial 收集器,只有它能与 CMS 收集器配合使用

 3.CMS垃圾回收器

追求最短的停顿时间(STW),分为四个阶段:初始标记,并发标记,重新标记,并发清理,只有初始标记阶段和重新标记阶段需要暂停用户线程,其他阶段不需要暂停用户线程,可以和用户线程并行),所以适用于暂停时间要求比较高的,比如实时系统,交互式系统

整个过程分为以下几个步骤:

 (1)初始标记:标记直接与 root 相连的对象 (不直接相连,间接相连的不标记),这是一个STW(stop the world)阶段,其他用户线程是不能工作的

(2)并发标记:CMS线程会从与GC Roots直接相连的对象出发,遍历整个对象图 ,标记所有存活的对象,这个阶段,CMS线程和其他用户线程在并发执行,

(3)重新标记: 由于上一个阶段并发标记阶段其他用户线程实际上还是在运行的,有可能用户线程在这个阶段产生了新的对象(这些新的对象中的存活对象是没有打上标记的),这里采用三色标记法来标记那些新产生的对象中存活对象  

(4)并发清理:清除所有没有被标记的对象,这个阶段如果有新增对象会被标记为黑色,不做任何处理       

最后并发重置就是把 标记过的对象取消标记

 三色标记算法:

黑色:这个对象及其所有的引用的对象都被遍历过,那这个对象就是黑色,黑色的对象不会被回收

灰色:这个对象被遍历过,但是它的部分引用还没被遍历过,在重新标记阶段会将这个对象标记为灰色

白色:这个对象没有被遍历过,在重新标记阶段如果是白色的话,这个对象将被回收

4.G1垃圾收集算法:

G1(Garbage-First),HotSpot 开发团队赋予它的使命是未来可以替换掉 CMS 收集器

优先清理垃圾占比较高的区域

其它收集器将堆分为新生代和老年代,进行收集的范围都是整个新生代或者老年代,而 G1 垃圾回收器不再将堆分成新生代和老年代,而是将整个内存切成一段一段大小相等的内存区域(每块区域称为region),每个region可能处于新生代或者老年代,所有处于新生代的region组成新生代,所有处于老年代的region组成老年代,也就是说新生代和老年代不再物理隔离

工作流程

(1)初始标记:标记所有直接与GC Root相连的对象,用户线程暂停,STW

(2)并发标记:多线程标记所有存活的对象,用户线程可以继续运行

(3)最终标记:由于上一个阶段并发标记阶段其他用户线程实际上还是在运行的,有可能用户线程在这个阶段产生了新的对象(这些新的对象中的存活对象是没有打上标记的)STW

(4)筛选回收:清理所有没被标记的对象

G1垃圾回收器可以设置一个垃圾回收的预期时间(比如指定这个垃圾回收器在一个小时之内发生stw的停顿时间不超过1分钟,这样回收器就会尽量在这个时间范围内完成垃圾回收任务)

 G1 把堆划分成多个大小相等的独立区域(Region),,通过引入 Region 的概念,从而将原来的一整块内存空间划分成多个的小空间,使得每个小空间可以单独进行垃圾回收。这种划分方法带来了很大的灵活性

记录每个 Region 垃圾回收时间以及回收所获得的空间(这两个值是通过过去回收的经验获得),然后维护一个优先列表,每次根据允许的收集时间,优先回收价值最大的 Region。

 

  CMS垃圾回收器和G1垃圾回收器之间的区别:

(1)CMS是针对老年代的垃圾收集器,而G1既可以对年轻代,又可以对老年代进行收集

(2)CMS采用的是标记清除算法,会产生很多内存碎片,G1采用的是标记整理算法,避免了垃圾碎片

(3)CMS的设计目标是减少垃圾收集引起的用户线程暂停stop the world的时间,而G1垃圾回收器既能缩短暂停时间,又能适用于吞吐量较高的程序(相同时间内能处理更多任务)

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值