Loading [MathJax]/jax/output/CommonHTML/config.js
首页
学习
活动
专区
圈层
工具
发布
社区首页 >专栏 >jvm系列(五):Java GC 分析

jvm系列(五):Java GC 分析

作者头像
纯洁的微笑
发布于 2018-04-18 09:55:56
发布于 2018-04-18 09:55:56
2K0
举报
文章被收录于专栏:纯洁的微笑纯洁的微笑

Java GC就是JVM记录仪,书画了JVM各个分区的表演。

什么是 Java GC

Java GC(Garbage Collection,垃圾收集,垃圾回收)机制,是Java与C++/C的主要区别之一,作为Java开发者,一般不需要专门编写内存回收和垃圾清理代码,对内存泄露和溢出的问题,也不需要像C程序员那样战战兢兢。这是因为在Java虚拟机中,存在自动内存管理和垃圾清扫机制。概括地说,该机制对JVM(Java Virtual Machine)中的内存进行标记,并确定哪些内存需要回收,根据一定的回收策略,自动的回收内存,永不停息(Nerver Stop)的保证JVM中的内存空间,防止出现内存泄露和溢出问题。

在Java语言出现之前,就有GC机制的存在,如Lisp语言),Java GC机制已经日臻完善,几乎可以自动的为我们做绝大多数的事情。然而,如果我们从事较大型的应用软件开发,曾经出现过内存优化的需求,就必定要研究Java GC机制。

简单总结一下,Java GC就是通过GC收集器回收不在存活的对象,保证JVM更加高效的运转。如果不了解GC算法和垃圾回收器可以参考这篇文章:jvm系列(三):GC算法 垃圾收集器。

如何获取 Java GC日志

一般情况可以通过两种方式来获取GC日志,一种是使用命令动态查看,一种是在容器中设置相关参数打印GC日志。

命令动态查看

Java 自动的工具行命令,jstat可以用来动态监控JVM内存的使用,统计垃圾回收的各项信息。

比如常用命令, jstat-gc 统计垃圾回收堆的行为

代码语言:javascript
AI代码解释
复制
$ jstat -gc 1262
 S0C    S1C     S0U     S1U   EC       EU        OC         OU        PC       PU         YGC    YGCT    FGC    FGCT     GCT   
26112.0 24064.0 6562.5  0.0   564224.0 76274.5   434176.0   388518.3  524288.0 42724.7    320    6.417   1      0.398    6.815

也可以设置间隔固定时间来打印:

代码语言:javascript
AI代码解释
复制
$ jstat -gc 1262 2000 20

这个命令意思就是每隔2000ms输出1262的gc情况,一共输出20次

更详细的内容参考这篇文章:jvm系列(四):jvm调优-命令篇

GC参数

JVM的GC日志的主要参数包括如下几个:

  • -XX:+PrintGC 输出GC日志
  • -XX:+PrintGCDetails 输出GC的详细日志
  • -XX:+PrintGCTimeStamps 输出GC的时间戳(以基准时间的形式)
  • -XX:+PrintGCDateStamps 输出GC的时间戳(以日期的形式,如 2017-09-04T21:53:59.234+0800)
  • -XX:+PrintHeapAtGC 在进行GC的前后打印出堆的信息
  • -Xloggc:../logs/gc.log 日志文件的输出路径

在生产环境中,根据需要配置相应的参数来监控JVM运行情况。

Tomcat 设置示例

我们经常在tomcat的启动参数中添加JVM相关参数,这里有一个典型的示例:

代码语言:javascript
AI代码解释
复制
JAVA_OPTS="-server -Xms2000m -Xmx2000m -Xmn800m -XX:PermSize=64m -XX:MaxPermSize=256m -XX:SurvivorRatio=4
-verbose:gc -Xloggc:$CATALINA_HOME/logs/gc.log 
-Djava.awt.headless=true 
-XX:+PrintGCTimeStamps -XX:+PrintGCDetails 
-Dsun.rmi.dgc.server.gcInterval=600000 -Dsun.rmi.dgc.client.gcInterval=600000
-XX:+UseConcMarkSweepGC -XX:MaxTenuringThreshold=15"

根据上面的参数我们来做一下解析:

-Xms2000m-Xmx2000m-Xmn800m-XX:PermSize=64m-XX:MaxPermSize=256m Xms,即为jvm启动时得JVM初始堆大小,Xmx为jvm的最大堆大小,xmn为新生代的大小,permsize为永久代的初始大小,MaxPermSize为永久代的最大空间。

-XX:SurvivorRatio=4 SurvivorRatio为新生代空间中的Eden区和救助空间Survivor区的大小比值,默认是32,也就是说Eden区是 Survivor区的32倍大小,要注意Survivo是有两个区的,因此Surivivor其实占整个young genertation的1/34。调小这个参数将增大survivor区,让对象尽量在survitor区呆长一点,减少进入年老代的对象。去掉救助空间的想法是让大部分不能马上回收的数据尽快进入年老代,加快年老代的回收频率,减少年老代暴涨的可能性,这个是通过将-XX:SurvivorRatio 设置成比较大的值(比如65536)来做到。

-verbose:gc-Xloggc:$CATALINA_HOME/logs/gc.log 将虚拟机每次垃圾回收的信息写到日志文件中,文件名由file指定,文件格式是平文件,内容和-verbose:gc输出内容相同。

-Djava.awt.headless=true Headless模式是系统的一种配置模式。在该模式下,系统缺少了显示设备、键盘或鼠标。

-XX:+PrintGCTimeStamps-XX:+PrintGCDetails 设置gc日志的格式

-Dsun.rmi.dgc.server.gcInterval=600000-Dsun.rmi.dgc.client.gcInterval=600000 指定rmi调用时gc的时间间隔

-XX:+UseConcMarkSweepGC-XX:MaxTenuringThreshold=15 采用并发gc方式,经过15次minor gc 后进入年老代

如何分析GC日志

摘录GC日志一部分

Young GC回收日志:

代码语言:javascript
AI代码解释
复制
2016-07-05T10:43:18.093+0800: 25.395: [GC [PSYoungGen: 274931K->10738K(274944K)] 371093K->147186K(450048K), 0.0668480 secs] [Times: user=0.17 sys=0.08, real=0.07 secs]

Full GC回收日志:

代码语言:javascript
AI代码解释
复制
2016-07-05T10:43:18.160+0800: 25.462: [Full GC [PSYoungGen: 10738K->0K(274944K)] [ParOldGen: 136447K->140379K(302592K)] 147186K->140379K(577536K) [PSPermGen: 85411K->85376K(171008K)], 0.6763541 secs] [Times: user=1.75 sys=0.02, real=0.68 secs]

通过上面日志分析得出,PSYoungGen、ParOldGen、PSPermGen属于Parallel收集器。其中PSYoungGen表示gc回收前后年轻代的内存变化;ParOldGen表示gc回收前后老年代的内存变化;PSPermGen表示gc回收前后永久区的内存变化。young gc 主要是针对年轻代进行内存回收比较频繁,耗时短;full gc 会对整个堆内存进行回城,耗时长,因此一般尽量减少full gc的次数

通过两张图非常明显看出gc日志构成:

Young GC日志:

Full GC日志:

GC分析工具

GChisto

GChisto是一款专业分析gc日志的工具,可以通过gc日志来分析:Minor GC、full gc的时间、频率等等,通过列表、报表、图表等不同的形式来反应gc的情况。虽然界面略显粗糙,但是功能还是不错的。

配置好本地的jdk环境之后,双击GChisto.jar,在弹出的输入框中点击 add 选择gc.log日志

GC Pause Stats:可以查看GC 的次数、GC的时间、GC的开销、最大GC时间和最小GC时间等,以及相应的柱状图

GC Pause Distribution:查看GC停顿的详细分布,x轴表示垃圾收集停顿时间,y轴表示是停顿次数。

GC Timeline:显示整个时间线上的垃圾收集

不过这款工具已经不再维护

GC Easy

这是一个web工具,在线使用非常方便.

地址: http://gceasy.io

进入官网,讲打包好的zip或者gz为后缀的压缩包上传,过一会就会拿到分析结果。

推荐使用此工具进行gc分析。

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2017-09-19,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 纯洁的微笑 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
暂无评论
推荐阅读
编辑精选文章
换一批
GC - Java 垃圾回收机制教科书级教学
注意:垃圾收集主要是针对堆和方法区进行;程序计数器、虚拟机栈和本地方法栈这三个区域属于线程私有的,只存在于线程的生命周期内,线程结束之后也会消失,因此不需要对这三个区域进行垃圾回收。
Java编程指南
2022/05/31
1.2K0
GC - Java 垃圾回收机制教科书级教学
JVM性能调优篇
GC 优化的基本原则是:将不同的 GC 参数应用到两个及以上的服务器上然后比较它们的性能,然后将那些被证明可以提高性能或减少 GC 执行时间的参数应用于最终的工作服务器上。
李红
2019/05/29
1.1K0
【GC分析】Java GC日志查看「建议收藏」
大家好,我是架构君,一个会写代码吟诗的架构师。今天说一说【GC分析】Java GC日志查看「建议收藏」,希望能够帮助大家进步!!!
Java架构师必看
2022/02/16
2K0
【GC分析】Java GC日志查看「建议收藏」
JVM系列四:生产环境参数实例及分析【生产环境实例增加中】
说明一下, -XX:SurvivorRatio=65536 -XX:MaxTenuringThreshold=0就是去掉了救助空间;
贺公子之数据科学与艺术
2025/08/29
1640
生产环境下JVM调优参数的设置实例
◆ NewSize较大,old gen 剩余空间64m,一方面可能会带来old区容易增长到报警范围(监控数据显示oldgenused长期在50m左右,接近78%,容易出现full gc),另一方面也存在promontion fail风险。
小勇DW3
2018/08/30
2K0
GC 日志分析
GC 日志分析 首先,如果需要查看 GC 日志,需要在 jvm 参数中加入如下参数 -XX:+PrintGCTimeStamps -XX:+PrintGCDetails -Xloggc:d:/GClogs/tomcat6-gc.log GC 日志 2016-11-23T11:01:27.738+0800: 0.150: [GC [PSYoungGen: 331K->288K(5952K)] 331K->288K(19648K), 0.0006495 secs] [Times: user=0.00 sys=
王小明_HIT
2020/05/08
1.6K0
GC 日志分析
JVM调优日志解析分析
-XX:+PrintGCTimeStamps 输出GC的时间戳(以基准时间的形式)
小勇DW3
2018/08/30
5550
JVM调优日志解析分析
JVM性能调优
程序在上线前的测试或运行中有时会出现一些大大小小的JVM问题,比如cpu load过高、请求延迟、tps降低等,甚至出现内存泄漏(每次垃圾收集使用的时间越来越长,垃圾收集频率越来越高,每次垃圾收集清理掉的垃圾数据越来越少)、内存溢出导致系统崩溃,因此需要对JVM进行调优,使得程序在正常运行的前提下,获得更高的用户体验和运行效率。
全栈程序员站长
2022/06/30
7860
JVM性能调优
JVM 监控,调优,调试
Java的安装包自带了很多优秀的工具,善用这些工具对于监控和调试Java程序非常有帮助。常用工具如下:
大道七哥
2019/08/23
9970
JVM之GC日志解读
通过阅读Gc日志,我们可以了解Java虚拟机内存分配与回收策略。 内存分配与垃圾回收的参数列表
一个风轻云淡
2023/10/15
6560
JVM之GC日志解读
一次频繁cms gc问题的排查
前几天收到线上某机器cms-initial-remark次数超过13次报警,这台机器长时间没有过新功能上线,为啥会出现频繁cms gc告警呢,遂一起排查。
LNAmp
2018/09/05
1.7K0
Java虚拟机(七):JVM调优案列
   什么是jvm调优呢?jvm调优就是根据gc日志分析jvm内存分配、回收的情况来调整各区域内存比例或者gc回收的策略;更深一层就是根据dump出来的内存结构和线程栈来分析代码中不合理的地方给予改进。eclipse优化主要涉及的是前者,通过gc日志来分析。本文主要是通过分析eclipse gc日志为例来示例如何根据gc日志来分析jvm内存而进行调优,像根据关闭eclipse启动项、关闭各种校验等措施来优化eclipse本文不再阐述,网上有很多,本次测试的eclipse已经进行了配置上面的优化。
朝雨忆轻尘
2019/06/19
7240
Java虚拟机(七):JVM调优案列
频繁GC (Allocation Failure)及young gc时间过长分析
本文主要分析一个频繁GC (Allocation Failure)及young gc时间过长的case。
code4it
2018/09/17
13.7K0
JVM调优--GC2
昨天上了马士兵老师的公开课第一节, 这节课前半部分基本上是对预习资料的巩固(还好我预习了)和延伸.这部分, 巩固的成分更高. 这节课的收获有如下:
用户7798898
2022/05/06
4290
JVM调优--GC2
jvm系列(八):jvm知识点总览
在江湖中要练就绝世武功必须内外兼备,精妙的招式和深厚的内功,武功的基础是内功。对于武功低(就像江南七怪)的人,招式更重要,因为他们不能靠内功直接去伤人,只能靠招式,利刃上优势来取胜了,但是练到高手之后,内功就更主要了。一个内功低的人招式在奇妙也打不过一个内功高的人。比如,你剑法再厉害,一剑刺过来,别人一掌打断你的剑,你还怎么使剑法,你一掌打到一个武功高的人身上,那人没什么事,却把你震伤了,你还怎么打。同样两者也是相辅相成的,内功深厚之后,原来普通的一招一式威力也会倍增。 对于搞开发的我们其实也是一样,现在流
纯洁的微笑
2018/04/19
1.1K0
jvm系列(八):jvm知识点总览
jvm系列:jvm知识点总览
在江湖中要练就绝世武功必须内外兼备,精妙的招式和深厚的内功,武功的基础是内功。对于武功低(就像江南七怪)的人,招式更重要,因为他们不能靠内功直接去伤人,只能靠招式,利刃上优势来取胜了,但是练到高手之后,内功就更主要了。一个内功低的人招式在奇妙也打不过一个内功高的人。比如,你剑法再厉害,一剑刺过来,别人一掌打断你的剑,你还怎么使剑法,你一掌打到一个武功高的人身上,那人没什么事,却把你震伤了,你还怎么打。同样两者也是相辅相成的,内功深厚之后,原来普通的一招一式威力也会倍增。 对于搞开发的我们其实也是一样,现在
Java高级架构
2018/04/19
9520
阿里终面:用过GC日志可视化工具进行JVM调优吗?
上周知识星球的小伙伴面了阿里,在二面中被问到GC日志分析,感觉回答的不是很好,过来找我复盘,大致听了他的回答,虽然回答出了部分,但是没抓到重点。
码猿技术专栏
2023/12/28
4160
阿里终面:用过GC日志可视化工具进行JVM调优吗?
Java-Parallel GC介绍
http://hg.openjdk.java.net/jdk8u/jdk8u/hotspot/rev/24cae3e4cbaa
开源日记
2020/12/23
2.7K0
JVM架构和GC垃圾回收机制(JVM面试不用愁)[通俗易懂]
JVM全称是Java Virtual Machine(Java虚拟机),Java虚拟机是一种程序虚拟机(相对操作系统虚拟机),Java的运行环境实现跨平台。
全栈程序员站长
2022/08/11
4780
JVM架构和GC垃圾回收机制(JVM面试不用愁)[通俗易懂]
JVM架构和GC垃圾回收机制详解
Java的动态类加载功能是由类加载器子系统处理。当它在运行时(不是编译时)首次引用一个类时,它加载、链接并初始化该类文件。
用户1212940
2022/04/13
3470
JVM架构和GC垃圾回收机制详解
相关推荐
GC - Java 垃圾回收机制教科书级教学
更多 >
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
首页
学习
活动
专区
圈层
工具
MCP广场
首页
学习
活动
专区
圈层
工具
MCP广场