一、最常用:jmap -histo(JDK 自带)
# 查看所有对象的实例数和内存占用(按大小排序)
jmap -histo <pid>
# 只看存活对象(先触发一次 Full GC,再统计)
jmap -histo:live <pid>
输出示例
num #instances #bytes class name
----------------------------------------------
1: 1234567 98765432 [C (char数组,字符串底层)
2: 567890 45678901 java.lang.String
3: 345678 34567890 java.util.HashMap$Node
4: 234567 23456789 com.xxx.User
| 列 | 含义 |
|---|---|
#instances |
对象实例数量 |
#bytes |
占用内存字节数 |
class name |
类名 |
常用技巧
# 只看某个类的对象数量(用 grep 过滤)
jmap -histo <pid> | grep "SpringValue"
# 输出到文件,方便后续分析
jmap -histo <pid> > obj_histogram.txt
# 看 Top 20 最大的对象
jmap -histo <pid> | head -25
二、更强大:jcmd(JDK 自带,推荐)
jcmd 是 JDK 8+ 推荐的诊断工具,功能比 jmap 更全:
# 列出所有 Java 进程
jcmd -l
# 查看对象直方图(等价于 jmap -histo)
jcmd <pid> GC.class_histogram
# 只看存活对象
jcmd <pid> GC.class_histogram -all=false
三、实时监控:Arthas
阿里开源的 Java 诊断工具,功能最强大,不用重启应用:
# 安装启动
curl -O https://arthas.aliyun.com/arthas-boot.jar
java -jar arthas-boot.jar
# 选择进程后,查看对象统计
vmtool --action getInstances --className com.xxx.User --limit 10
# 查看某个类的实例数量
vmtool --action getInstances --className com.xxx.User | wc -l
# 查看对象详情
vmtool --action getInstances --className com.xxx.User --limit 1 -x 2
四、导出堆快照后分析
如果需要深度分析,先导出堆转储文件,再用 MAT / JVisualVM 分析:
# 导出堆快照(hprof 格式)
jmap -dump:format=b,file=heap.hprof <pid>
# 或用 jcmd
jcmd <pid> GC.heap_dump heap.hprof
然后用 MAT(Memory Analyzer Tool) 打开,可以:
- 查看对象数量、占比、内存泄漏分析
- 用 OQL(对象查询语言)写复杂查询
- 查看对象引用链
五、快速对比:哪个命令适合你
| 工具 | 自带 | 实时 | 功能 | 推荐场景 |
|---|---|---|---|---|
jmap -histo |
✅ JDK自带 | 快照 | 基础统计 | 快速排查、线上应急 |
jcmd |
✅ JDK自带 | 快照 | 比jmap全 | JDK8+ 首选 |
| Arthas | ❌ 需安装 | 实时 | 非常强大 | 深度诊断、日常开发 |
| MAT | ❌ 需安装 | 离线 | 最强分析 | 内存泄漏根因定位 |
快速上手示例
# 1. 先找到 Java 进程 ID
jps -l
# 2. 查看对象数量 Top 10
jmap -histo 12345 | head -15
# 3. 查特定类的实例数
jmap -histo 12345 | grep "SpringValue"
除非注明,否则均为李锋镝的博客原创文章,转载必须以链接形式标明本文链接
踩坑踩多了
文章评论