当前位置: 首页 > news >正文

JVM学习日记(十四)Day14——性能监控与调优(一)

经过前几篇的铺垫,现在开始正式进入调优篇,也是大火实际用的到的和感兴趣的,但是前期的知识积累还是有必要的,所以还对JVM基础没什么了解的,建议还是回看主包的前几篇内容,当然看其他优秀的博主也是可以的。

性能调优三步骤 

  1. 发现问题——性能监控:我们通过GUI图形工具或者JVM命令后对程序进行监控,如出现FullGC频率过高、CPU负载较高、死锁、OOM内存泄漏/溢出,或者更加简单的就是程序莫名其妙响应时间过长大白话就是卡顿。
  2. 排查问题——性能分析:通过对内存的分析、查看GC日志、查看JVM状态、已经堆栈信息来确定大概的调优方向,分析出那个区域需要调整。
  3. 解决问题——性能调优:经过监控和分析已经知道了问题的大致方向,然后进行处理,比如增加内存的大小、使用消息队列缓存、增加机器也就是分布式减轻压力、优化代码控制内存的使用。

 这个图来自于尚硅谷的宋红康老师的课程,主包也是跟着宋老师学习整理的资料,想学习的更加细节和系统化可以去某站搜索。

jps:列出当前用户的所有Java进程

jps -lvm 
//-q:只显示进程ID
//-l:显示完整包名
//-v:显示JVM参数
//-m:显示main方法的参数jps -l
22417 jdk.jcmd/sun.tools.jps.Jps  //jps也是个java进程
22260 org.jetbrains.jps.cmdline.Launcher //idea编译进程
2422                                     //僵尸或者特殊进程不用理会
32988 com.example.seed.SeedApplication//项目进程
89423 com.intellij.idea.Main //idea主进程

这里说一下,其实我们使用的命令全部是在JDK的bin目录下,主包这个是Mac文件的类型显示的就是Unix可执行的文件,要是Window就应该是.exe的文件,有兴趣的小伙伴可以自己去查看一下。 另外这个脚步使用的文件就在/home/lib/tools.jar中,在jar包的/sun/tools目录下,也是一个字节码文件,又兴趣的小伙伴可以自己去查看,这边就不演示了。(如果使用了-XX:-UserPerfData那么jps和jstat都无法探查这个进程,因为关闭了用户性能数据)

jstat - JVM统计监控工具

jstat -<option> [-t] [-h<lines>] <vmid> [<interval> [<count>]]
--<option>//操作参数(必填)
--[-t]    //JVM启动到现在的时间
[-h<lines>]//每几行重新打印表头
--<vmid>  //Java进程Pid
[<interval>//每次打印的间隔时间1000=1秒
[<count>]]//打印次数
选项说明
-class类加载统计
-compilerJIT编译器统计
-gcGC统计
-gccapacity各内存区域容量统计
-gcutilGC统计百分比
-gccauseGC统计及原因(同-gcutil,但包含最近一次GC原因)
-gcnew新生代GC统计
-gcnewcapacity新生代内存容量统计
-gcold老年代GC统计
-gcoldcapacity老年代内存容量统计
-gcmetacapacity元空间内存容量统计
-printcompilationJVM编译方法统计

 图太小的话就放大来看吧,这里就是完整的命令格式,当然必须要大就是操作和PID参数其他的看各自的需求了,这个命令也是查看JVM最多的命令,可以查的消息还是很全面的。

列名说明示例值
TimestampJVM 启动后的时间戳(秒)134663.6
S0CSurvivor 0 区容量(KB)0.0
S1CSurvivor 1 区容量(KB)6144.0
S0USurvivor 0 区已使用(KB)0.0
S1USurvivor 1 区已使用(KB)6144.0
ECEden 区容量(KB)51200.0
EUEden 区已使用(KB)32768.0
OC老年代容量(KB)40960.0
OU老年代已使用(KB)32549.8
MCMetaspace 容量(KB)54528.0
MUMetaspace 已使用(KB)53845.6
CCSC压缩类空间容量(KB)7488.0
CCSU压缩类空间已使用(KB)7206.5
YGC年轻代 GC 次数10
YGCT年轻代 GC 总时间(秒)0.126
FGCFull GC 次数0
FGCTFull GC 总时间(秒)0.000
CGCConcurrent GC 次数4
CGCTConcurrent GC 总时间(秒)0.002
GCT所有 GC 总时间(秒)0.128

这个呢就是各个打印代表的意思了。其他的操作主包我就不演示了。其实使用这个命令就可以判断内存是否有益处的风险,比如我们采用抽样调查的方法,相同的时间间隔下去对老年区进行监控,如果老年区内存占用在某一个时间段激增或者每段时间都增加的比较多,可能就是内存泄漏无法回收了。因为一般情况下除了静态文件和Spring容器、数据库连接池、监听器等不会被回收,其他的基本上这个请求已结束等到下一个E去GC就会被回收的,如果一直没有被回收肯定就是内存泄漏了。

jinfo :查看和修改正在运行的 Java 进程的配置参数

jinfo [option] <pid>
参数选项作用
-flags显示所有 JVM 参数(包括默认参数)
-sysprops显示所有系统属性(相当于 System.getProperties())
-flag <name>显示指定 JVM 参数的值
-flag [+/-]<name>启用或禁用指定的布尔型 JVM 参数
-flag <name>=<value>设置指定的 JVM 参数值
无参数同时显示系统属性和 JVM 参数
//查看最大的堆空间值jinfo -flag MaxHeapSize  32988     
-XX:MaxHeapSize=4294967296-flag [+/-]<name> - 修改布尔型参数
# 启用PrintGCDetails
jinfo -flag +PrintGCDetails 12345-flag <name>=<value> - 修改数值型参数
# 修改MaxHeapFreeRatio
jinfo -flag MaxHeapFreeRatio=70 12345

好了主包这里只示范简单的几个命令,主包个人其实这个命令只有两个操作,一个是flags一个就是flag,也很好记忆了,而且用处也是非常大的,就比如这个动态修改JVM参数了。不加任何参数查看的信息就非常的全了,大火快去自行尝试一下。另外不是所有的JVM参数都能被修改的,这也是人之常情了,只有被manageable标记的参数。java -XX:+PrintFlagsFinal | grep manageable这个命令可以查看,大概能改的参数就是这些了,主包这个是JDK21可能和大家的不一样,大家还是自己看看吧。

 jmap :用于生成Java堆转储快照(heap dump)和分析堆内存使用情况

这个命令的作用主要就是生成dump的二进制文件,然后进行内存分析的,当然需要借助工作不然我们可是看不懂二进制文件的,然后就是查询类加载器信息​、​查看finalizer队列​​、分析对象内存分布​(用的多多主包已经飙红了)。

jmap [options] <pid>               # 连接运行中的Java进程
jmap [options] <executable> <core>  # 连接核心转储文件
jmap [options] [server_id@]<remote server IP or hostname>  # 连接远程调试服务器
参数功能描述适用场景
-dump生成堆转储文件(Heap Dump)内存泄漏分析、OOM 问题诊断
-heap显示堆内存配置和使用摘要快速查看堆内存分配情况
-histo显示堆中对象统计直方图分析对象内存占用
-clstats显示类加载器统计信息类加载问题诊断
-finalizerinfo显示等待 finalize 的对象对象回收问题诊断
-F强制模式(当进程挂起时使用)JVM 无响应时的强制转储
#活着的对象
jmap -dump:[live,]format=b,file=<filename> <pid>
#全部的对象包括死的
jmap -dump:format=b,file=<filename> <pid>
//例如
jmap -dump:live,format=b,file=./Downloads/testH.hprof 32988
关键词作用是否可选示例值
-dump主命令,表示要执行堆转储操作必选-
live只转储存活对象(会触发Full GC)可选包含或不包含
format=b指定输出格式为二进制必选必须为b
file=<filename>指定输出文件路径必选heap.hprof
<pid>目标Java进程ID必选1234

在我们分析的时候大多数选择的都是存活的对象,因为 一般没有被回收的对象就是存活的而且要死全部都看的话一个是这个文件回很大,另一个就是分析起来不是那么好分析需要的时间也就是更长了,此外还有一个办法可以获得dump文件,那就是JVM参数,因为大多少程序出现OOM崩溃的时候开发人员是不能第一时间获得这个文件的,来不及和不可预测所有我们需要使用JVM参数来获取崩溃时的内存快照。

-XX:+HeapDumpOnOutOfMemoryError
-XX:HeapDumpPath=/path/to/dump/file.hprof

这俩参数相信大家也能看明白我就不介绍了。下面就是-heap和-histo的运行实例了,其他的就不演示了。

#查看堆内存信息
jmap -heap <pid>
Attaching to process ID 12345, please wait...
Debugger attached successfully.
Server compiler detected.
JVM version is 25.131-b11using thread-local object allocation.
Parallel GC with 4 thread(s)  # 使用的GC类型Heap Configuration:           # 堆配置参数MinHeapFreeRatio         = 40MaxHeapFreeRatio         = 70MaxHeapSize              = 2147483648 (2048.0MB)  # 最大堆NewSize                  = 715653120 (682.5MB)    # 新生代大小MaxNewSize               = 715653120 (682.5MB)OldSize                  = 1431830528 (1365.5MB)  # 老年代大小NewRatio                 = 2                      # 新生代/老年代比例SurvivorRatio           = 8                      # Eden/Survivor比例MetaspaceSize           = 21807104 (20.796875MB) # 元空间CompressedClassSpaceSize = 1073741824 (1024.0MB)G1HeapRegionSize        = 0 (0.0MB)Heap Usage:                  # 堆使用情况
PS Young Generation          # 并行年轻代
Eden Space:                  # Eden区capacity = 537919488 (513.0MB)used     = 536870912 (512.0MB)free     = 1048576 (1.0MB)99.8% used
From Space:                  # Survivor From区capacity = 89128960 (85.0MB)used     = 0 (0.0MB)free     = 89128960 (85.0MB)0.0% used
To Space:                    # Survivor To区capacity = 89128960 (85.0MB)used     = 0 (0.0MB)free     = 89128960 (85.0MB)0.0% used
PS Old Generation            # 并行老年代capacity = 1431830528 (1365.5MB)used     = 536870912 (512.0MB)free     = 894959616 (853.5MB)37.5% used# 其他信息...
jmap -histo[:live] <pid> [> 输出文件]
# 统计所有对象(包含未被回收的对象)前20个
jmap -histo 12345 | head -20jmap -histo:live 32988 | head -20num     #instances实例数量  #bytes字节大小  class name (module)
-------------------------------------------------------1:         81074       12879208  [B (java.base@21.0.5)2:         73927        1774248  java.lang.String (java.base@21.0.5)3:         18267        1607496  java.lang.reflect.Method (java.base@21.0.5)4:         48478        1551296  java.util.concurrent.ConcurrentHashMap$Node (java.base@21.0.5)5:         13055        1546952  java.lang.Class (java.base@21.0.5)6:          7083        1236824  [I (java.base@21.0.5)7:         13298         842456  [Ljava.lang.Object; (java.base@21.0.5)8:          6582         485232  [Ljava.util.HashMap$Node; (java.base@21.0.5)9:         12046         481840  java.util.LinkedHashMap$Entry (java.base@21.0.5)10:          7367         471488  java.util.LinkedHashMap (java.base@21.0.5)11:           393         452112  [Ljava.util.concurrent.ConcurrentHashMap$Node; (java.base@21.0.5)12:         11288         361216  java.util.HashMap$Node (java.base@21.0.5)13:         18351         293616  java.lang.Object (java.base@21.0.5)14:         10053         260904  [Ljava.lang.Class; (java.base@21.0.5)15:          4872         233856  java.lang.invoke.MemberName (java.base@21.0.5)16:          8861         212664  org.springframework.core.MethodClassKey17:          2970         166320  org.springframework.core.ResolvableType18:           353         158216  [Ljdk.internal.vm.FillerElement; (java.base@21.0.5)

总结

本篇主要讲了进行性能调优要做的那些步骤,以及jps、jstat、jinfo、jamp的命令介绍,请大家一定要多多尝试,光看肯定是记不住的。

http://www.lryc.cn/news/607820.html

相关文章:

  • 基于ELK Stack的实时日志分析与智能告警实践指南
  • SpringBoot 信用卡检测、OpenAI gym、OCR结合、DICOM图形处理、知识图谱、农业害虫识别实战
  • JVM 01 运行区域
  • Qwen3 Embedding:新一代文本表征与排序模型
  • Hyper-V + Centos stream 9 搭建K8s集群(一)
  • 手动开发一个TCP客户端调试工具(三):工具界面设计
  • 【人工智能agent】--服务器部署PaddleX 的 印章文本识别模型
  • Design Compiler:Milkyway库的创建与使用
  • 分布式微服务--Nacos作为配置中心(补)关于bosststrap.yml与@RefreshScope
  • 集成电路学习:什么是CMSIS微控制器软件接口标准
  • [创业之路-528]:技术成熟度曲线如何指导创业与投资?
  • UNet改进(28):KD Attention增强UNet的知识蒸馏方法详解
  • 深入解析 <component :is> 在 Vue3 组合式中的使用与局限
  • 【推荐100个unity插件】快速实现汽车控制器——PROMETEO: Car Controller插件
  • 除数博弈(动态规划)
  • [硬件电路-124]:模拟电路 - 信号处理电路 - 测量系统的前端电路详解
  • python匿名函数lambda
  • 【LeetCode刷题指南】--二叉树的前序遍历,二叉树的中序遍历
  • 2025熵密杯 -- 初始谜题 -- Reproducibility
  • 进阶向:自动化天气查询工具(API调用)
  • stm32是如何实现电源控制的?
  • 【7.5 Unity AssetPostprocessor】
  • 2-5 Dify案例实践—利用RAG技术构建企业私有知识库
  • 【最新区块链论文录用资讯】CCF A--WWW 2025 23篇
  • 第三章 用户和权限
  • 【C++】第二十一节—一文详解 | 红黑树实现(规则+效率+结构+插入+查找+验证)
  • 【RK3568 RTC 驱动开发详解】
  • 网安-中间件(updating..)
  • jenkins从入门到精通-P1—九五小庞
  • 【机器学习】非线性分类算法详解(下):决策树(最佳分裂特征选择的艺术)与支持向量机(最大间隔和核技巧)