JVM调优的GC日志观察解读

如果各项参数设置合理,系统没有超时日志出现,GC 频率不高,GC 耗时不高,那么没有必要进行 GC 优化
如果 GC 时间超过 1-3 秒,或者频繁 GC,则必须优化。

一、参数解读

  1. Jvm 调优典型参数设置;
    -Xms: 堆内存的最小值 :默认情况下,当堆中可用内存小于 40%时,堆内存会开始增加,一直增加到-Xmx 的大小。
    -Xmx :堆内存的最大值:默认值是总内存/64(且小于 1G),默认情况下,当堆中可用内存大于 70%时,堆内存会开始减少,一直减小到-Xms的大小;
    -Xmn: 新生代内存的最大值:包括 Eden 区和两个 Survivor 区的总和,配置写法如:-Xmn1024k,-Xmn1024m,-Xmn1g
    -Xss: 每个线程的栈内存:默认 1M,一般来说是不需要改。线程栈越小意味着可以创建的线程数越多

整个堆的大小 = 年轻代大小 + 年老代大小,堆的大小不包含元空间大小,如果增大了年轻代,年老代相应就会减小,官方默认的配置为年老代大小/年轻代大小=2/1 左右;
建议在开发测试环境可以用 Xms 和 Xmx 分别设置最小值最大值,但是在线上生产环境,Xms 和 Xmx 设置的值必须一样,防止抖动;

  1. GC 日志
    -XX:+PrintGCDetails 开启 GC 日志创建更详细的 GC 日志 ,默认情况下,GC 日志是关闭的
    -XX:+PrintGCTimeStamps -XX:+PrintGCDateStamps :开启 GC 时间提示
    开启时间便于我们更精确地判断几次 GC 操作之间的时两个参数的区别
    时间戳是相对于 0 (依据 JVM 启动的时间)的值,而日期戳(date stamp)是实际的日期字符串
    由于日期戳需要进行格式化,所以它的效率可能会受轻微的影响,不过这种操作并不频繁,它造成的影响也很难被我们感知。
    -XX:+PrintHeapAtGC 打印堆的 GC 日志
    -Xloggc:./logs/gc.log 指定 GC 日志路径

  2. jdk11的gc日志打印
    -Xlog:gc*:file=gc.log:time,uptime,pid,tid,tags:filecount=5,filesize=10M

gc.log是日志打印位置

二、打印日志出来

package com.zhk.study.log;import java.util.ArrayList;
import java.util.List;//测试代码
public class TestHeap {public static void main(String[] args) {List<Heap> list = new ArrayList<Heap>();while (true) {list.add(new Heap());}}
}class Heap {String HeapName = "Java Heap 测试";
}

1.jdk8

配置jvm参数
在这里插入图片描述

-XX:+PrintGCDetails
-XX:+PrintGCTimeStamps
-XX:+PrintGCDateStamps
-XX:+PrintHeapAtGC
-Xloggc:E:/gc-default.log

在这里插入图片描述

在这里插入图片描述

  1. 日志解读
2022-08-05T13:45:23.336+0800: 4.866: [GC (Metadata GC Threshold) [PSYoungGen: 136353K->20975K(405504K)] 160049K->48437K(720384K), 0.0092260 secs] [Times: user=0.00 sys=0.02, real=0.02 secs]
2022-08-05T13:45:23.336+0800: 本次GC发生时间
4.866: 举例启动应用的时间
[GC【表示GC的类型,youngGC】 (Metadata GC Threshold) 元空间超阈值
[PSYoungGen: 136353K->20975K(405504K年轻代总空间)] 160049K->48437K(720384K)整堆), 0.0092260 secs本次垃圾回收耗时]
[Times: user=0.00本次GC消耗CPU的时间 sys=0.02系统暂停时间, real=0.02 secs实际应用暂停时间]
  1. FullGC 日志含义
2022-08-05T20:24:47.815+0800: 6.955: [Full GC (Metadata GC Threshold) [PSYoungGen: 701K->0K(72704K)] [ParOldGen: 38678K->35960K(175104K)] 39380K->35960K(247808K), [Metaspace: 56706K->56706K(1099776K)], 0.1921975 secs] [Times: user=1.03 sys=0.00, real=0.19 secs]
2022-08-05T20:24:47.815+0800:
6.955: 刚启动服务就Full GC【整堆回收!!】[Full GC (Metadata GC Threshold) Metaspace空间超限!
[PSYoungGen: 701K->0K(72704K)] 年轻代没有回收空间
[ParOldGen: 38678K->35960K(175104K)] 39380K->35960K(247808K), 老年代也没有到阈值,整堆更没有到阈值
[Metaspace: 56706K->56706K(1099776K)], 0.1921975 secs]
[Times: user=1.03本次GC消耗CPU的时间 sys=0.00系统暂停时间, real=0.19 secs实际应用暂停时间]

2、jdk11默认G1回收

启动参数修改为

-Xlog:gc*:file=gc.log:time,uptime,pid,tid,tags:filecount=5,filesize=10M

在这里插入图片描述

  1. 日志解读
[2023-09-14T11:38:32.994+0800][0.017s][12940][11992][gc,heap] Heap region size: 1M
[2023-09-14T11:38:33.001+0800][0.024s][12940][11992][gc     ] Using G1
[2023-09-14T11:38:33.001+0800][0.024s][12940][11992][gc,heap,coops] Heap address: 0x0000000701c00000, size: 4068 MB, Compressed Oops mode: Zero based, Oop shift amount: 3
[2023-09-14T11:38:33.201+0800][0.225s][12940][8148 ][gc,start     ] GC(0) Pause Young (Normal) (G1 Evacuation Pause)
[2023-09-14T11:38:33.202+0800][0.225s][12940][8148 ][gc,task      ] GC(0) Using 3 workers of 3 for evacuation
[2023-09-14T11:38:33.215+0800][0.238s][12940][8148 ][gc,phases    ] GC(0)   Pre Evacuate Collection Set: 0.0ms
[2023-09-14T11:38:33.215+0800][0.238s][12940][8148 ][gc,phases    ] GC(0)   Evacuate Collection Set: 12.7ms
[2023-09-14T11:38:33.215+0800][0.239s][12940][8148 ][gc,phases    ] GC(0)   Post Evacuate Collection Set: 0.2ms
[2023-09-14T11:38:33.215+0800][0.239s][12940][8148 ][gc,phases    ] GC(0)   Other: 0.3ms
[2023-09-14T11:38:33.215+0800][0.239s][12940][8148 ][gc,heap      ] GC(0) Eden regions: 12->0(10)
[2023-09-14T11:38:33.215+0800][0.239s][12940][8148 ][gc,heap      ] GC(0) Survivor regions: 0->2(2)
[2023-09-14T11:38:33.215+0800][0.239s][12940][8148 ][gc,heap      ] GC(0) Old regions: 0->7
[2023-09-14T11:38:33.215+0800][0.239s][12940][8148 ][gc,heap      ] GC(0) Humongous regions: 4->4
[2023-09-14T11:38:33.215+0800][0.239s][12940][8148 ][gc,metaspace ] GC(0) Metaspace: 6551K->6551K(1056768K)
[2023-09-14T11:38:33.215+0800][0.239s][12940][8148 ][gc           ] GC(0) Pause Young (Normal) (G1 Evacuation Pause) 16M->12M(256M) 14.012ms
[2023-09-14T11:38:33.215+0800][0.239s][12940][8148 ][gc,cpu       ] GC(0) User=0.03s Sys=0.02s Real=0.01s

这段日志描述了Java应用程序的垃圾收集事件的详细信息。让我解释一下每个部分的含义:
[2023-09-14T11:38:32.994+0800] - 这是时间戳,表示日志记录的时间。

[0.017s] - 这是相对于日志记录的时间的时间戳,表示日志记录发生的相对时间。

[12940][11992] - 这两个数字可能是线程的标识符,用于标识执行垃圾收集的线程。

[gc,heap] Heap region size: 1M - 这表示Java堆的分区大小为1MB。

[gc] Using G1 - 这表示Java使用了G1垃圾收集器。

[gc,heap,coops] Heap address: 0x0000000701c00000, size: 4068 MB, Compressed Oops mode: Zero based, Oop shift amount: 3 - 这描述了Java堆的地址、大小以及压缩指针(Compressed Oops)的信息。

[gc,start] GC(0) Pause Young (Normal) (G1 Evacuation Pause) - 这是垃圾收集事件的开始,GC(0) 表示第0次垃圾收集,Pause Young (Normal) (G1 Evacuation Pause) 表示这是一次Young代正常的G1垃圾收集事件。

[gc,task] GC(0) Using 3 workers of 3 for evacuation - 这表示在这次垃圾收集事件中,有3个工作线程用于执行对象的迁移。

[gc,phases] - 这一系列的行描述了垃圾收集的不同阶段,包括 Pre Evacuate Collection Set、Evacuate Collection Set、Post Evacuate Collection Set 等。

[gc,heap] - 这行提供了有关堆内存的信息,包括Eden、Survivor、Old、Humongous等区域的变化。

[gc,metaspace] - 这行提供了有关元数据空间(Metaspace)的信息,包括它的大小变化。

[gc] Pause Young (Normal) (G1 Evacuation Pause) 16M->12M(256M) 14.012ms - 这行提供了垃圾收集事件的摘要信息,包括收集前后的堆内存使用量变化,以及事件的持续时间。

[gc,cpu] - 这行提供了垃圾收集事件的CPU占用情况。

总的来说,这些日志记录提供了关于Java应用程序中垃圾收集事件的详细信息,包括时间戳、线程标识、垃圾收集器类型、堆内存情况以及事件持续时间等。这些信息对于分析和调整Java应用程序的性能非常有用。

三、优化

优化垃圾回收性能通常需要仔细分析应用程序的行为和垃圾回收日志,然后根据分析的结果采取相应的措施。以下是一些可能的优化建议,但请注意,具体的优化策略会根据应用程序的需求和行为而变化:

  • 分析垃圾回收模式:首先要了解应用程序的垃圾回收模式。从日志中可以看出,这里使用的是G1(Garbage-First)垃圾回收器。不同的垃圾回收器适用于不同的应用程序,因此确保选择了最适合应用程序需求的回收器是很重要的。

  • 调整堆大小:根据应用程序的需求,可能需要调整堆大小(-Xms 和 -Xmx 参数)。如果应用程序频繁触发垃圾回收,可能需要增加堆大小以减少回收的频率。但要注意,堆大小的过分增加也可能导致长时间的垃圾回收停顿,因此需要谨慎调整。

  • 分析垃圾回收暂停时间:从日志中可以看到每次Young区和Mixed区垃圾回收的停顿时间。优化的目标是减少这些停顿时间,以提高应用程序的响应性。可以使用参数来控制垃圾回收暂停时间,例如使用 -XX:MaxGCPauseMillis 参数。

  • 分析内存分配模式:查看日志中的Eden、Survivor和Old区的分配情况。如果发现频繁的对象进入Old区,可能需要调整各个区域的大小或者调整年轻代的比例,以减少对象在Old区的存活时间。

  • 检查Metaspace使用:从日志中可以看到Metaspace的使用情况。如果Metaspace的使用不断增长,可能需要增加Metaspace的大小或者检查是否有类加载器泄漏。

  • 分析对象生命周期:了解应用程序中对象的生命周期模式,可以帮助确定何时进行垃圾回收。如果对象的生命周期很短,可以采用更侧重于Young区的策略。如果对象生命周期很长,需要确保Old区的管理足够高效。

  • 监控和调整:使用性能监控工具和垃圾回收日志持续监控应用程序的性能。如果发现性能问题,可以根据实时数据来调整垃圾回收参数。

  • 并行和并发:根据应用程序的特性,可以选择并行垃圾回收或并发垃圾回收。并行回收器适用于多核系统,而并发回收器适用于需要最小停顿时间的应用程序。

  • 分析吞吐量:了解应用程序的吞吐量需求,可以选择适当的垃圾回收策略。某些垃圾回收器更适合高吞吐量,而某些回收器更适合低停顿时间。

  • 版本升级:考虑将JVM版本升级到最新的稳定版本,因为新版本通常会带来性能和垃圾回收方面的改进。

综上所述,优化垃圾回收性能是一个复杂的过程,需要深入了解应用程序的行为和需求。建议在开发和测试环境中进行多次测试和调整,以找到最佳的垃圾回收配置。同时,密切关注生产环境中的性能指标,以及随着应用程序负载变化而进行必要的调整。

四、gc次数判断

gc次数

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/108454.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Timeline的使用心得

timeline使用教程 timeline使用主要分为一下几步&#xff1a; 1、新建表格&#xff1b; 2、设置数据 3、发布网址 4、修改表格样式&#xff1b; 5、快速预览 需要用到的几个网址&#xff1a; 1、timeline官网网址&#xff1a;timeline 2、本地图片转链接&#xff1a;图片转链…

【JAVA】异常

作者主页&#xff1a;paper jie 的博客 本文作者&#xff1a;大家好&#xff0c;我是paper jie&#xff0c;感谢你阅读本文&#xff0c;欢迎一建三连哦。 本文录入于《JAVASE语法系列》专栏&#xff0c;本专栏是针对于大学生&#xff0c;编程小白精心打造的。笔者用重金(时间和…

无涯教程-JavaScript - ISODD函数

描述 如果数字为奇数,则ISODD函数返回TRUE,如果数字为偶数,则返回FALSE。 语法 ISODD (number) 争论 Argument描述Required/OptionalNumber 要测试的值或表达式。 如果number不是整数,则将其截断。 Required Notes 您可以在执行计算之前使用此功能测试单元格的内容。 如果…

MySQL优化第二篇

MySQL优化第二篇 性能分析小表驱动大表慢查询日志日志分析工具mysqldumpslow Show Profile进行SQL分析&#xff08;重中之重&#xff09; 七种JOIN 1、inner join &#xff1a;可以简写为join&#xff0c;表示的是交集&#xff0c;也就是两张表的共同数据 sql语句&#xff1a…

详解TCP/IP协议第三篇:通信数据在OSI通信模型的上下传输

文章目录 一&#xff1a;OSI通信模型间数据传输展示 二&#xff1a;应用层到会话层解析 1&#xff1a;应用层 2&#xff1a;表现层 3&#xff1a;会话层 三&#xff1a;传输层到物理层解析 1&#xff1a;传输层 2&#xff1a;网络层 3&#xff1a;数据链路层、与物理层…

Python实现猎人猎物优化算法(HPO)优化Catboost分类模型(CatBoostClassifier算法)项目实战

说明&#xff1a;这是一个机器学习实战项目&#xff08;附带数据代码文档视频讲解&#xff09;&#xff0c;如需数据代码文档视频讲解可以直接到文章最后获取。 1.项目背景 猎人猎物优化搜索算法(Hunter–prey optimizer, HPO)是由Naruei& Keynia于2022年提出的一种最新的…

vue学习之属性绑定

内容渲染 采用 &#xff1a;进行属性渲染创建 demo3.html,内容如下 <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"&…

LeetCode 1359. Count All Valid Pickup and Delivery Options【动态规划,组合数学】1722

本文属于「征服LeetCode」系列文章之一&#xff0c;这一系列正式开始于2021/08/12。由于LeetCode上部分题目有锁&#xff0c;本系列将至少持续到刷完所有无锁题之日为止&#xff1b;由于LeetCode还在不断地创建新题&#xff0c;本系列的终止日期可能是永远。在这一系列刷题文章…

BGP路由属性

任何一条BGP路由都拥有多个路径属性&#xff08;Path Attributes&#xff09;&#xff0c;当路由器通告BGP路由给它的对等体时&#xff0c;该路由将会携带多个路径属性&#xff0c;这些属性描述了BGP路由的各项特征&#xff0c;同时在某些场景下也会影响BGP路由优选的决策。 一…

百度收录和权重怎么提升-网站如何获得百度权重

你是否一直苦恼于网站权重的低迷&#xff1f;不知道如何开始提升网站权重&#xff0c;缺乏优质内容更新网站。不清楚如何进行关键词优化来提升网站排名和权重。SEO是一个需要持续投入时间和资源的过程。每个网站的情况都会有所不同&#xff0c;因此所花费的时间也会有所差异。然…

Spring基础(2w字---学习总结版)

目录 一、Spirng概括 1、什么是Spring 2、什么是容器 3、什么是IoC 4、模拟实现IoC 4.1、传统的对象创建开发 5、理解IoC容器 6、DI概括 二、创建Spring项目 1、创建spring项目 2、Bean对象 2.1、创建Bean对象 2.2、存储Bean对象&#xff08;将Bean对象注册到容器…

Apollo介绍和入门

文章目录 Apollo介绍配置中心介绍apollo介绍主流配置中心功能特性对比 Apollo简介 入门简单的执行流程Apollo具体的执行流程Apollo对象执行流程分步执行流程 核心概念应用&#xff0c;环境&#xff0c;集群&#xff0c;命名空间企业部署方案灰度发布全量发布 配置发布的原理发送…