JAVA系列之JVM内存调优( 三 )


4、堆溢出(java.lang.OutOfMemoryError: Java heap space)堆溢出是常见也是最复杂的一种情况 。导致堆溢出可能的情况有:

  • 堆内存配置太小
  • 超出预期的访问量:访问量飙升
  • 超出预期的数据量:系统中是否存在一次性提取大量数据到内存的代码
  • 内存泄漏
解决思路一般是:
一、堆dump文件获取1、通过参数配置自动获取dump文件(推荐)2、jmap -dump:format=b,file=filename.hprof pid二、MAT工具分析1、分析大对象、堆中存储信息、可能存在的内存泄漏地方,便于定位问题位置
五、JVM监控常用的监控工具或命令有:jstack、jstat、jConsole、jvisualvm 。监控指标主要是各内存区域大小是否合理、fullGC频率及耗时、youngGC耗时、线程数等 。
1、jstackjstack主要用于打印线程堆栈信息,帮助问题的定位 。一般配合top -Hp PID使用 。
通过top命令发现某个java服务占用1234%的CPU,如图:
JAVA系列之JVM内存调优

文章插图
通过top -Hp PID命令可以看到占用CPU比较高的线程,如图:
JAVA系列之JVM内存调优

文章插图
再次通过jstack PID>log.txt,输出堆栈信息即可进行排查定位 。
2、jstatjstat命令是分析JVM运行状况的常用命令 。
jstat -options-class 用于查看类加载情况的统计-compiler 用于查看HotSpot中即时编译器编译情况的统计-gc 用于查看JVM中堆的垃圾收集情况的统计-gccapacity 用于查看新生代、老生代及持久代的存储容量情况-gcmetacapacity 显示metaspace的大小-gcnew 用于查看新生代垃圾收集的情况-gcnewcapacity 用于查看新生代存储容量的情况-gcold 用于查看老生代及持久代垃圾收集的情况-gcoldcapacity 用于查看老生代的容量-gcutil 显示垃圾收集信息-gccause 显示垃圾回收的相关信息(通-gcutil),同时显示最后一次仅当前正在发生的垃圾收集的原因-printcompilation 输出JIT编译的方法信息
以jstat -gcutil为例:
[root@hadoop ~]# jstat -gcutil 3346 #显示垃圾收集信息S0 S1 E O M CCS YGC YGCT FGC FGCT GCT52.97 0.00 42.10 13.92 97.39 98.02 8 0.020 0 0.000 0.020 
  • S0:年轻代中第一个survivor(幸存区)已使用的占当前容量百分比
  • S1:年轻代中第二个survivor(幸存区)已使用的占当前容量百分比
  • E:年轻代中Eden(伊甸园)已使用的占当前容量百分比
  • O:old代已使用的占当前容量百分比
  • M:元数据区已使用的占当前容量百分比
  • CCS:压缩类空间已使用的占当前容量百分比
  • YGC :从应用程序启动到采样时年轻代中gc次数
  • YGCT :从应用程序启动到采样时年轻代中gc所用时间(s)
  • FGC :从应用程序启动到采样时old代(全gc)gc次数
  • FGCT :从应用程序启动到采样时old代(全gc)gc所用时间(s)
  • GCT:从应用程序启动到采样时gc用的总时间(s)
3、jConsoleJConsole是基于JMX的可视化监视、管理工具 。可以很方便的监视本地及远程服务器的java进程的内存使用情况 。
3.1 被监控的程序运行时给虚拟机添加一些运行的参数
无需认证的远程监控配置-Dcom.sun.management.jmxremote.port=60001//监控的端口号-Dcom.sun.management.jmxremote.authenticate=false//关闭认证-Dcom.sun.management.jmxremote.ssl=false-Djava.rmi.server.hostname=192.168.1.2
3.2 客户端连接被监控程序找到 JDK 安装路径,打开bin文件夹 , 双击jconsole.exe,在已经打开的JConsole界面操作“连接->新建连接->选择远程进程->输入远程主机IP和端口号->点击“连接
JAVA系列之JVM内存调优

文章插图
JAVA系列之JVM内存调优

文章插图
4、jvisualvmjvisualvm与jConsole连接方式一致,连接后界面如下:
JAVA系列之JVM内存调优

文章插图

推荐阅读