jmap命令详解

jmap(Java Memory Map)是 JDK 自带的工具,用于分析 Java 堆内存的分布和对象信息。以下是 jmap 命令的详细说明及代码案例:


一、核心用途

  1. 查看堆内存配置‌:堆内存各区(Eden、Survivor、Old Gen)的分配和使用情况。
  2. 生成堆转储快照‌(Heap Dump):将堆内存保存为 .hprof 文件,用于离线分析内存泄漏。
  3. 统计对象分布‌:显示堆中对象的类型、数量及占用内存大小。
  4. 类加载器统计‌:查看类加载器的存活对象信息。

二、命令语法

jmap [options] <pid>
  • <pid>‌:目标 Java 进程的进程 ID(可通过 jps 或 ps -ef | grep java 获取)。
  • [options]‌:常用参数如下:
参数作用
-heap打印堆内存配置信息(JDK 8 及之前可用)
-histo[:live]统计堆中对象分布(live 仅统计存活对象,触发 Full GC)
-dump:live,format=b,file=<file>生成堆转储文件(live 仅转存活对象)
-clstats打印类加载器统计信息
-finalizerinfo显示等待执行 finalize() 方法的对象

三、关键场景及代码案例

1. 查看堆内存配置(JDK 8 及之前)
jmap -heap <pid>

输出示例‌:

Attaching to process ID 12345, please wait...
Debugger attached successfully.
Server compiler detected.
JVM version is 25.291-b10

using thread-local object allocation.
Parallel GC with 4 thread(s)

Heap Configuration:
   MinHeapFreeRatio         = 0    # 堆最小空闲比例
   MaxHeapFreeRatio         = 100  # 堆最大空闲比例
   MaxHeapSize              = 2147483648 (2048.0MB)  # 最大堆内存
   NewSize                  = 44564480 (42.5MB)      # 新生代初始大小
   MaxNewSize               = 715653120 (682.5MB)    # 新生代最大大小
   OldSize                  = 89522176 (85.375MB)    # 老年代大小
   NewRatio                 = 2                      # 新生代:老年代 = 1:2
   SurvivorRatio            = 8                      # Eden:Survivor = 8:1:1
   MetaspaceSize            = 21807104 (20.796875MB) # 元空间初始大小
   CompressedClassSpaceSize = 1073741824 (1024.0MB)  # 压缩类空间大小
   G1HeapRegionSize         = 0 (0.0MB)              # G1 区域大小

Heap Usage:
PS Young Generation  # 新生代使用情况
Eden Space:
   capacity = 33554432 (32.0MB)
   used     = 16777216 (16.0MB)
   free     = 16777216 (16.0MB)
   50.0% used
From Space:  # Survivor 区
   capacity = 5242880 (5.0MB)
   used     = 0 (0.0MB)
   free     = 5242880 (5.0MB)
   0.0% used
To Space:
   capacity = 5242880 (5.0MB)
   used     = 0 (0.0MB)
   free     = 5242880 (5.0MB)
   0.0% used
PS Old Generation  # 老年代使用情况
   capacity = 89522176 (85.375MB)
   used     = 0 (0.0MB)
   free     = 89522176 (85.375MB)
   0.0% used

2. 统计对象分布(-histo
jmap -histo:live <pid> > heap_objects.log

输出示例‌:

 num     #instances         #bytes  class name
----------------------------------------------
   1:        200000      200000000  [B  # byte 数组
   2:        100000       8000000  java.lang.String
   3:         50000       4000000  java.util.HashMap$Node
   4:         10000        160000  java.lang.Class
   5:          5000         80000  java.util.concurrent.ConcurrentHashMap$Node
  • [B‌:表示 byte[] 数组,通常占用内存最多。
  • live 参数‌:触发 Full GC 后统计存活对象(生产环境慎用)。

3. 生成堆转储文件(-dump
jmap -dump:live,format=b,file=heapdump.hprof <pid>
  • heapdump.hprof‌:生成的堆转储文件,可用工具(如 MAT、JVisualVM)分析。
  • 适用场景‌:内存泄漏分析、大对象定位。

4. 查看类加载器统计(-clstats
jmap -clstats <pid>

输出示例‌:

ClassLoader         Parent              #Classes  #Instances  Bytes
====================================================================
sun/misc/Launcher$AppClassLoader        null        500        20000    16MB
jdk/internal/loader/ClassLoaders$AppClassLoader  null  300        15000    12MB
  • #Classes‌:该类加载器加载的类数量。
  • #Instances‌:该加载器创建的实例数。

四、注意事项

  1. 权限问题‌:执行 jmap 的用户需与启动 Java 进程的用户一致。
  2. 生产环境慎用 live‌:-histo:live 和 -dump:live 会触发 Full GC,可能导致应用短暂停顿。
  3. JDK 版本兼容性‌:JDK 9+ 中 -heap 参数已弃用,改用 jhsdb jmap --heap <pid>

五、结合其他工具分析

  • MAT(Memory Analyzer Tool)‌:分析 .hprof 文件,定位内存泄漏。
  • JVisualVM‌:实时监控堆内存,生成和分析堆转储。
  • jstat‌:监控堆内存各区使用率(如 jstat -gcutil <pid> 1000)。

通过 jmap 可以快速定位内存瓶颈,结合其他工具能更高效地解决 Java 内存问题

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值