首页 > 编程技术 > java

JVM常用垃圾收集器详细解说

发布时间:2022-7-18 19:00 作者:小码农叔叔

前言

在上一篇,我们谈到了jvm垃圾回收算法详细解析,并了解了JVM中针对堆区中不同的分代采用不同的垃圾回收算法

在了解了垃圾回收算法之后,很多伙伴不禁在想,既然是分代垃圾回收,自然新生代和老年代的垃圾收集器也是不同的,事实上确实是这样,分代的回收算法也产生了不同的垃圾收集器

先来看一下下面这张简图:

左边表示年轻代中可选的垃圾收集器,右边表示老年代中可选的垃圾收集器,任何两个连线之间的两种垃圾收集器可以进行组合使用,在年轻代中,Parallel Scavenge 是默认的GC收集器,而在老年代中,SerialOld为默认的GC收集器

上面的看到的年轻代和老年代收集器属于分代收集器,在JDK1.8中,由于采用了分代垃圾回收,故使用分代垃圾收集器进行GC,各个垃圾收集器根据自身的特点都有着不同的使用场景,下面针对各个垃圾收集器进行简单的说明,以便深入理解各款垃圾收集器的使用原理

可以使用下面的命令查看本机或者虚拟机上的JVM的垃圾收集器(默认安装的JDK版本)

java -XX:+PrintCommandLineFlags -version

新生代垃圾收集器

Serial

Serial垃圾收集器也叫做串行收集器,串行垃圾收集器的特点:

ParNew

这是对单线程的Serial的一种改进,ParNew收集器是并行的,在多CPU的场景下会有比串行收集器更好的性能,除此之外,实现算法跟Serial完全一样

ParNew垃圾收集器特点:

Parallel Scavenge

也称作PS收集器,这也是一种新生代垃圾收集器,它采用的也是复制算法,与前两种收集器最大的区别是,它关注的是吞吐量而不是延迟,也被称为是吞吐量优先的收集器

其特点为:

以追求吞吐率最小(每一次GC消耗的时间 / 总时间)优先JDK1.8默认的垃圾收集器(年轻代)STW时间长,GC次数少(目前Java应用的部署的服务器更多的是进行后台任务的计算,直接与用户交互的过程较少,因此减少GC次数就很有必要)多线程GC,执行效率较高适合多核CPU适合后台计算任务

老年代垃圾收集器

SerialOld

这个是jdk1.2以前的默认收集器,适合单线程下作为CMS的备用收集器,由于运行效率较低,目前基本上很少使用,其运行原理和年轻代的Serial相似

Parallel Old

该收集器可以理解为PS收集器的老年代版本(对比理解PS收集器),其主要特点包括:

关注吞吐率STW时间较长,GC次数少多线程GC,执行效率较高适合多线程CPU适合后台计算任务

CM

CMS,Concurrent Mark Sweep,这是一款真正的并发收集器,属于老年代的垃圾收集器中最复杂的一款垃圾收集器,其主要特点为:

从上图中我们发现,CMS垃圾回收器在执行一次完整的垃圾回收时要经历几个阶段:初始标记(会产生一个很短的STW) ,并发标记,重新标记,并发清理,

对其中的几个关键点做简单的说明:

在实际工作中如何通过参数设置进行搭配使用呢?可以参考下面的表格:

如果想要自定义自己的应用使用某种收集器,以springboot的jar包为例,可以使用下面的命令:

java -jar -XX:+UseParallelGC XXX.jar

以上是关于分代垃圾收集器中,新生代和老年代各款收集器的说明,但是随着JVM的持续迭代与优化,垃圾收集器也在持续完善,比如JDK9开始就出现了不分代垃圾收集器,像CMS收集器,在JDK14中被废弃,说明了在迭代中,有更好的收集器取代它,下面再介绍几种常用的不分代垃圾收集器

不分代垃圾收集器

常用的不分代垃圾收集器包括下面几种:

G1收集器

G1收集器,是比前面的更优秀,真正有突破的一款垃圾收集器,在G1中还是保留了分代的概念,是实际上已经在新生代和老年代中没有物理隔离了,在G1中,内存空间被分割成一个个的Region区,所谓新生代和老年代,都是由一个个region组成的,同时G1也不需要跟别的收集器一起配合使用,自己就可以搞定所有内存区域。整体上来讲不是一个分代收集器,是一个通吃收集器。这也是JVM内存管理和垃圾收集的一个发展趋势。从后面zgc中我们可以更清晰的看到这个变化

G1采用了标记-整理算法,避免了CMS中的内存碎片问题,另外它能达到可控的垃圾时间

整体来说,G1收集器的特点:

G1垃圾回收过程可以和CMS垃圾回收过程进行类比,可以认为是G1收集器吸收了CMS的某些优秀的特点并进行了改良,但在其内部,仍然是以分代的思想进行垃圾回收,即采用了: 新生代 + 老年代 的混合回收算法(Mixed GC),触发条件为:老年代超过了堆内存的45%

ZGC

zgc是jdk11中要发布的最新垃圾收集器,不管是CMS收集器,还是G1收集器(尽管物理上没有分代的概念,但是逻辑上仍然采用了分代的思想进行垃圾回收),都有一个特点,就是在整个垃圾收集过程中的初始标记最终标记阶段,会有一个STW的产生,尽管G1相比CMS有了更大的提升,但是由于分代的概念存在,始终无法绕过这个问题

ZGC特点:

Shenandoah收集器

Shenandoah收集器目前在JDK12中也处于实验性阶段,其主要特点包括:

后面两种收集器可以作为学习进行了解,尽管目前还没有大规模的投入商用,但是其设计理念却为未来的垃圾收集器的持续优化和改进提供了很好的思路和方向,尤其是ZGC 和Shenandoah的超低延迟STW,可以说在分代收集器的基础上进行了相当大的提升,让我们拭目以待吧

到此这篇关于JVM常用垃圾收集器详细解说的文章就介绍到这了,更多相关JVM垃圾收集器内容请搜索猪先飞以前的文章或继续浏览下面的相关文章希望大家以后多多支持猪先飞!

原文出处:https://blog.csdn.net/zhangcongyi420/article/details/1134822

标签:[!--infotagslink--]

您可能感兴趣的文章: