java垃圾回收算法和经典垃圾收集器

主要总结jvm中的垃圾收集算法和垃圾收集器


垃圾收集算法:
标记-清除算法
标记-复制算法
标记-整理算法


一、jvm实用工具

1.查看和修改jvm配置

	# 查看14进程的所有jvm配置
	jinfo -flags 14
	# 查看某一项配置,比如查看dump文件路径
	jinfo -flag HeapDumpPath 14
	# 增加gc日志打印相关的jvm配置(删除则使用-号)
	jinfo -flag +PrintGC 14 			// 开启gc日志
	jinfo -flag +PrintGCDetails 14		// 打印详情
	jinfo -flag +PrintGCDateStamps 14	// 格式化时间
	jinfo -flag +HeapDumpBeforeFullGC 14	// fgc前dump
	jinfo -flag HeapDumpPath=/logs/dump_xxx.bin 14 // 设置dump路径
如果不清楚具体的配置项的名称,可以通过以下命令进行过滤查找(以下manageable为关键字):
	java -XX:+PrintFlagsFinal -version | grep manageable

2.使用MAT工具打开后发现占用内存很少

	默认不显示不可达对象。打开MAT的设置,reference,保留不可达的对象。如果实时设置不生效,尝试重新打开dump文件。

二、垃圾收集算法

1.标记-清除算法

2.标记-复制算法

3.标记-整理算法

三、垃圾收集器

垃圾收集器也分为新生代收集器和老年代收集器,目前比较常用的有以下,在jvm运行时几乎也都是两个收集器同时配置运行:
经典的垃圾收集器

新生代收集器

1.Serial

最基础、历史最悠久的收集器。曾经在1.3是HotSpot新生代收集器的唯一选择。
采用复制算法。
生产组合:Serial/Serial Old

2.ParMew

实质上是Serial收集器的多线程并行版本,很多Serial收集器的jvm控制参数、算法、分配规则等也都完全一致。
采用复制算法。
生产组合:ParNew/Serial Old
ParNew/CMS

3.Parallel Scavenge

一款新生代收集器,基于标记-复制算法实现,也是能够并行收集的多线程收集器。CMS等收集器的关注点是尽可能缩短垃圾收集时用户线程的停顿时间,而Parallel Scavenge收集器的目标则是达到一个可控制的吞吐量(throughput),也被称为“吞吐量优先收集器”。
吞吐量 = 运行用户代码时间 / 运行用户代码时间 + 运行垃圾收集时间
生产组合:Parallel Scavenge / Parallel Old

总结:新生代收集器常用复制算法

老年代收集器

1.Serial Old

作为Serial收集器的老年代版本,是一个单线程收集器,使用标记-整理算法。
生产组合:Serial/Serial Old

2.Parallel Old

是Parallel Scavenge收集器的老年代版本,支持多线程并发收集,基于标记-整理算法实现,1.6才开始提供。
生产组合:Parallel Scavenge / Parallel Old

3.CMS

CMS(Concurrent Mark Swep)并发-标记-清除收集算法是一种以获取最短回收停顿时间为把目标的收集器,是1.8版本常用的老年代回收器。
整个垃圾清理过程主要分为四步:

  • 初始标记(CMS Initial Mark)
  • 并发标记 CMS-concurrent
  • 重新标记(CMS Final Remark)
  • 并发清除CMS-concurrent-sweep
    在打印出GC日志可以观察到如下GC过程:
2023-09-15T16:58:11.672+0800: [GC (CMS Initial Mark) [1 CMS-initial-mark: 643954K(701184K)] 661721K(777920K), 0.0067740 secs] [Times: user=0.01 sys=0.00, real=0.01 secs] 
2023-09-15T16:58:11.678+0800: [CMS-concurrent-mark-start]
2023-09-15T16:58:11.853+0800: [GC (Allocation Failure) 2023-09-15T16:58:11.853+0800: [ParNew: 75932K->8512K(76736K), 0.0570174 secs] 719886K->678318K(777920K), 0.0571620 secs] [Times: user=0.06 sys=0.00, real=0.06 secs] 
2023-09-15T16:58:11.989+0800: [CMS-concurrent-mark: 0.252/0.310 secs] [Times: user=0.50 sys=0.00, real=0.31 secs] 
2023-09-15T16:58:11.989+0800: [CMS-concurrent-preclean-start]
2023-09-15T16:58:11.995+0800: [CMS-concurrent-preclean: 0.006/0.006 secs] [Times: user=0.01 sys=0.00, real=0.00 secs] 
2023-09-15T16:58:11.995+0800: [CMS-concurrent-abortable-preclean-start]
2023-09-15T16:58:12.347+0800: [CMS-concurrent-abortable-preclean: 0.052/0.352 secs] [Times: user=0.10 sys=0.01, real=0.36 secs] 
2023-09-15T16:58:12.349+0800: [GC (CMS Final Remark) [YG occupancy: 32938 K (76736 K)]2023-09-15T16:58:12.349+0800: [Rescan (parallel) , 0.0162113 secs]2023-09-15T16:58:12.365+0800: [weak refs processing, 0.0027552 secs]2023-09-15T16:58:12.368+0800: [class unloading, 0.1680965 secs]2023-09-15T16:58:12.536+0800: [scrub symbol table, 0.0499563 secs]2023-09-15T16:58:12.586+0800: [scrub string table, 0.0075458 secs][1 CMS-remark: 669806K(701184K)] 702744K(777920K), 0.2450178 secs] [Times: user=0.23 sys=0.01, real=0.24 secs] 
2023-09-15T16:58:12.594+0800: [CMS-concurrent-sweep-start]
2023-09-15T16:58:12.770+0800: [CMS-concurrent-sweep: 0.176/0.176 secs] [Times: user=0.30 sys=0.03, real=0.18 secs] 
2023-09-15T16:58:12.770+0800: [CMS-concurrent-reset-start]
2023-09-15T16:58:12.772+0800: [CMS-concurrent-reset: 0.001/0.001 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] 

jinfo -flags 15命令查询结果可以看到CMS的配置默认和ParNew组合使用:
在这里插入图片描述
生产组合:ParNew/CMS

混合收集器

1.G1

在G1出现之前,垃圾收集的目标范围要么是整个新生代(Minor GC),要么是整个老年代(Major GC),再要么就是整个java堆(Full GC)。而G1收集器是面向堆内存任何部分来组成回收集进行回收,衡量标准不是属于哪个分代,而是哪块内存中存放的垃圾数量最多,回收收益最大,这就是G1收集器的Mixed GC模式。

G1将连续的java堆划分为多个大小相等的独立区域(Region),每个region都可以根据需要扮演新生代的Eden空间,Survivor空间或者老年代空间。

Region中还有一类特殊的Humongous区域,抓门用来存储大对象。G1认为只要大小超过一个Region容量一半的对象即可判定为大对象。

从整体上来看G1是基于“标记-复制算法”实现,但从局部(两个Region)之间上看又是基于“标记-整理”算法实现的,但都意味着G1运行期间不会产生内存空间碎片。

在这里插入图片描述

其他垃圾收集器:

  1. Shenandoah(低延时收集器)
  2. ZGC(低延时收集器,jdk11加入,基于Region,使用了读屏障、染色指针、内存多重映射等技术实现可并发的标标记-整理算法的)
  3. Epsilon
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值