JVM参数调优——G1收集器
开启 G1 Collector
G1收集器的出现除了提供可控的低延迟GC,解决历史收集器的一些弊病,同时还尽力简化调优参数
对于大多数应用,开启收集器,再配置一下Xms和Xmx就足够了(不建议配置Xmn)
-XX:+UseG1GC
核心参数
- 最大暂停时间的目标值
默认值为200毫秒。
太大会导致延迟大,太小会导致频繁GC,吞吐下降,请结合堆大小酌情谨慎调节。一般情况下,使用默认值就好。
-XX:MaxGCPauseMillis=200
- G1每个Region的大小
该值为2的幂,范围为1MB到32MB。我们的目标是根据最小Java堆大小拥有大约2048个区域。
建议交给JVM自动分配
-XX:G1HeapRegionSize=n
重要参数
-
年轻代堆大小的最小值
设置年轻代堆大小占整个堆的百分比。
默认值是Java堆的5% (experimental VM flag) -
年轻代堆大小的最大值
设置年轻代堆大小占整个堆的百分比。
默认值是Java堆的60%。(experimental VM flag)
-XX:G1NewSizePercent=5-XX:G1MaxNewSizePercent=60
- 触发标记周期的Java堆占用率阈值
触发标记周期的Java堆占用率阈值。默认占用率是整个Java堆的45%。
-XX:InitiatingHeapOccupancyPercent=45
- MixedGC周期中的老年代的占用率阈值
设置要包含在混合垃圾收集周期中的老年代的占用率阈值。默认占用率为85%。(experimental VM flag)
-XX:G1MixedGCLiveThresholdPercent=85
- 允许堆浪费的百分比
设置您愿意浪费的堆的百分比。默认值为10%。
当可回收百分比小于堆浪费百分比时,Java HotSpot VM不会启动混合垃圾收集周期。
-XX:G1HeapWastePercent=10
- MixedGC周期中收集老年代区域的上限
设置在混合垃圾收集周期中要收集的老年代区域的上限。默认值为Java堆的10%。
-XX:G1OldCSetRegionThresholdPercent=10
- 保留空闲内存百分比
设置保持空闲的保留内存百分比,以降低到空间溢出的风险。默认值为10%。
-XX:G1ReservePercent=10
- MixedGC收集的目标数量
设置标记周期后混合垃圾收集的目标数量,以收集最多包含 G1MixedGCLIveThresholdPercent 实时数据的旧区域。默认值为8个混合垃圾回收。混合集合的目标是在此目标数量内。
-XX:G1MixedGCCountTarget=8
GC问题分析
问题特征
使用默认配置参数,(MaxGCPauseMillis=200)多个服务GC收集器从CMS转到G1效果都很好,GC耗时每分钟 大都在40ms以内,但是有个服务就与众不同了。
- YoungGC耗时长 300~500ms 有时1s+;
- mixedGC 频次低,耗时短,都在50ms以内;
- 日志中常见 to survivor 耗尽 (to-space exhausted);
分析思路
- 调小年轻代
让yongGC频繁一些,快一些
默认5%~60%
-XX:+UnlockExperimentalVMOptions
-XX:G1NewSizePercent=25
-XX:G1MaxNewSizePercent=40
- mixedGC调节
提前触发,每次多回收一些
提前触发标记周期 45%–>35%
触发mixedGC的老年代的占用率阈值 85%–>60% (experimentalVMOptions)
mixedGC中要收集的老年代区域占整个堆的百分比上限 10%–>20%
混合垃圾收集的目标数量 8–>12
-XX:InitiatingHeapOccupancyPercent=35
-XX:+UnlockExperimentalVMOptions -XX:G1MixedGCLiveThresholdPercent=60
-XX:G1OldCSetRegionThresholdPercent=20
-XX:G1MixedGCCountTarget=12
- 防止晋升失败
少浪费一些:10%–>5%
空闲空间多留一些:10%–>20%
如大对象晋升失败,可调大Region
-XX:G1HeapWastePercent=5
-XX:G1ReservePercent=20
-XX:G1HeapRegionSize=8
常用命令
- 查看G1 experimental flag
java -XX:+UnlockExperimentalVMOptions -XX:+PrintFlagsFinal -version|grep 'experimental' |grep G1
- 查看某进程X设定的VM参数
例如查看 MaxGCPauseMillis 的值
jinfo -flag MaxGCPauseMillis pid
- 查看进程GC情况
各分区使用情况,GC次数和时间
jstat -gc pid
- 查看进程VM参数
jinfo -flags pid
reference
- https://www.oracle.com/technical-resources/articles/java/g1gc.html
- https://code84.com/882088.html