Full GC 排查

在 Java 中,Full GC(完全垃圾回收)会对整个堆(包括年轻代和老年代,甚至可能包括永久代/元空间)进行垃圾回收,通常会导致较长的停顿(STW,Stop-The-World)。如果 Full GC 频繁发生,可能会影响应用的性能,甚至导致 OOM(OutOfMemoryError)。以下是排查 Full GC 的方法和工具:

1. 启用 GC 日志进行分析

(1)JDK 8 及以下版本

在 JVM 启动参数中添加:

-XX:+PrintGCDetails -XX:+PrintGCDateStamps -Xloggc:gc.log

解释:

  • -XX:+PrintGCDetails:输出 GC 详细信息。
  • -XX:+PrintGCDateStamps:打印 GC 发生的时间戳。
  • -Xloggc:gc.log:指定 GC 日志文件。

GC 日志示例:

2025-02-28T10:00:00.123+0000: [Full GC (System.gc())  [PSYoungGen: 1024K->0K(2048K)] [ParOldGen: 4096K->1024K(8192K)], 0.2356780 secs] 

分析重点:

  • Full GC (System.gc()):说明 GC 是由 System.gc() 触发的。
  • ParOldGen: 4096K->1024K(8192K):老年代的使用变化。
  • 0.2356780 secs:GC 停顿时间。

(2)JDK 9 及以上

JDK 9 引入了 统一日志框架(JEP 158),可以使用 -Xlog 进行更细粒度的 GC 日志控制:

-Xlog:gc*:file=gc.log:time,uptime,level,tags

示例:

[2025-02-28T10:00:00.123+0000][info][gc] GC(5) Pause Full (G1 Evacuation Pause) 235ms

2. 使用 jstat 监控 GC

jstat 是 JDK 自带的工具,可以用来实时监控 GC 的情况。

(1)查看 GC 统计信息

jstat -gcutil <pid> 1000

示例输出:

  S0     S1     E      O      M     CCS   YGC    YGCT   FGC   FGCT    GCT0.00  98.65  64.32  92.12  80.45  65.23   150  12.34   20   30.12  42.46

重点关注:

  • O(Old Gen):如果 O 长期接近 100%,说明老年代快满了,可能会触发 Full GC
  • FGC(Full GC 次数):如果这个值增长很快,说明 Full GC 频繁发生。
  • FGCT(Full GC 耗时):观察 Full GC 是否导致了长时间的 STW。

(2)查看具体 GC 详细信息

jstat -gc <pid> 1000

可以看到 Eden、Survivor、Old 区域的内存变化,帮助判断是否因老年代空间不足导致 Full GC

3. 使用 jmap 检查堆内存

如果怀疑 Full GC 频繁发生是由于内存不足,可以用 jmap 生成 堆转储文件(Heap Dump) 进行分析:

jmap -dump:format=b,file=heapdump.hprof <pid>

然后用 Eclipse MATVisualVM 分析内存使用情况,检查是否有内存泄漏或对象无法回收的问题。

此外,可以使用:

jmap -histo <pid>

查看当前堆中的对象分布,重点关注大对象或数量异常的对象。

4. 使用 jconsoleVisualVM 监控

  • JConsole

    jconsole
    
    • 连接到目标 JVM 后,查看 “内存”(Memory) 选项卡,观察老年代的占用情况。
    • 如果 Old Gen 长期接近 100%,可能会触发 Full GC
  • VisualVM

    jvisualvm
    
    • 连接到目标进程,打开 “监视”(Monitor) 选项卡,观察 GC 活动
    • 使用 “Profiler”(分析器) 记录 GC 发生的时间和影响。

5. 检查 Full GC 触发原因

(1)老年代空间不足

  • 观察老年代(Old Gen)占用情况,如果频繁接近 100%,说明 Full GC 可能是由于老年代空间不足导致的。
  • 优化方案
    • 增大老年代:
      -Xmx4g -Xms4g
      
    • 调整 GC 算法(如 G1 或 ZGC):
      -XX:+UseG1GC
      
    • 调整老年代比例:
      -XX:NewRatio=2
      

(2)过多的 System.gc()

  • 某些代码可能显式调用了 System.gc(),强制触发 Full GC
  • 检查代码是否有 System.gc() 调用,可以禁用:
    -XX:+DisableExplicitGC
    

(3)大对象直接进入老年代

  • 如果对象过大,可能会直接分配到老年代,导致 Full GC
  • 优化方案
    • 增大 -XX:PretenureSizeThreshold 以避免大对象直接进入老年代:
      -XX:PretenureSizeThreshold=16m
      
    • 使用 G1GC,可以通过 -XX:InitiatingHeapOccupancyPercent 控制老年代回收时机。

(4)元空间(Metaspace)不足

  • 在 JDK 8+,类元数据存放在 元空间(Metaspace),如果元空间不足也会触发 Full GC
  • 优化方案
    • 增大元空间:
      -XX:MetaspaceSize=512m -XX:MaxMetaspaceSize=1g
      

6. 结论

快速排查 Full GC 的步骤

  1. 启用 GC 日志-Xlog:gc*-XX:+PrintGCDetails)分析 Full GC 触发原因。
  2. 使用 jstat -gcutil <pid> 1000 观察老年代是否满了。
  3. 使用 jmap -histo <pid>jmap -dump 分析堆对象,检查是否有内存泄漏或大对象。
  4. 使用 jconsoleVisualVM 监控 GC 活动,观察 Full GC 频率。
  5. 检查是否有 System.gc() 调用,可以通过 -XX:+DisableExplicitGC 禁用。
  6. 调整 JVM 参数,如 -Xmx, -XX:NewRatio, -XX:MetaspaceSize,或尝试 G1/ZGC。

这样可以快速找出 Full GC 发生的原因,并进行针对性的优化 🚀。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/71251.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

go语言中字符串嵌套

在Go语言中&#xff0c;字符串嵌套通常是指在字符串中包含另一个字符串。可以通过以下几种方式实现&#xff1a; 1. 使用双引号和转义字符 如果需要在字符串中嵌套双引号&#xff0c;可以使用转义字符 \ 来表示内部的双引号。例如&#xff1a; s : "He said, \"He…

Docker 学习(二)——基于Registry、Harbor搭建私有仓库

Docker仓库是集中存储和管理Docker镜像的平台&#xff0c;支持镜像的上传、下载、版本管理等功能。 一、Docker仓库分类 1.公有仓库 Docker Hub&#xff1a;官方默认公共仓库&#xff0c;提供超过10万镜像&#xff0c;支持用户上传和管理镜像。 第三方平台&#xff1a;如阿里…

js的简单介绍

一.javascript&#xff08;是什么&#xff09; 是一种运行在客户端(浏览器)的编程语言&#xff0c;实现人机交互效果 作用 网页特效&#xff08;监听客户的一些行为让网页做出对应的反馈&#xff09;表单验证(针对表格数据的合法性进行判断)数据交互(获取后台的数据&#xf…

k8s架构及服务详解

目录 1.1.容器是什么1.2.Namespace1.3.rootfs5.1.Service介绍5.1.1.Serice简介 5.1.1.1什么是Service5.1.1.2.Service的创建5.1.1.3.检测服务5.1.1.4.在运行的容器中远程执行命令 5.2.连接集群外部的服务 5.2.1.介绍服务endpoint5.2.2.手动配置服务的endpoint5.2.3.为外部服务…

01. HarmonyOS应用开发实践与技术解析

文章目录 前言项目概述HarmonyOS应用架构项目结构Ability生命周期 ArkTS语言特性装饰器状态管理 UI组件与布局基础组件响应式布局样式与主题 页面路由与参数传递页面跳转参数接收 数据绑定与循环渲染数据接口定义循环渲染 条件渲染组件生命周期最佳实践与性能优化组件复用响应式…

【虚拟机 IP 配置深度剖析】

虚拟机 IP 配置深度剖析 在虚拟机的使用过程中&#xff0c;IP 配置犹如搭建房屋的基石&#xff0c;是确保虚拟机与外部网络顺畅通信、与其他设备高效交互的关键所在。本文将以 CentOS 虚拟机为例&#xff0c;深入解读 IP 配置的奥秘。 一、认识网络模式 • NAT 模式&#xf…

【Python 数据结构 5.栈】

目录 一、栈的基本概念 1.栈的概念 2.入栈 入栈的步骤 3.出栈 出栈的步骤 4.获取栈顶元素 获取栈顶元素的步骤 二、 Python中的栈 顺序表实现 链表实现 三、栈的实战 1.LCR 123. 图书整理 I 思路与算法 2.LCR 027. 回文链表 思路与算法 3.1614. 括号的最大嵌套深度 思路与算法 …

Machine Learning 初探

前置知识 pandas 读取文件&#xff1a;read_csv查看信息 describe&#xff1a;查看整体信息&#xff0c;包括每列的平均值、最大最小值、标准差等head&#xff1a;输出头部几行数据columns&#xff1a;输出所有列名loc&#xff1a;查询数据&#xff0c;或是根据索引取对应的数…

2025年2月个人工作生活总结

本文为 2025年2月工作生活总结。 工作记录 AI浪潮 AI非常火&#xff0c;春节至今&#xff0c;到处充斥着大量和AI、DeepSeek有关的新闻。领导也一再强调要用AI&#xff0c;甚至纳入到新一年的考核里。再往上&#xff0c;大领导开会的新闻稿里也作出要求&#xff0c;不能停下脚…

SpringBoot @ConfigurationProperties 注解使用

ConfigurationProperties 用于将配置文件&#xff08;如 application.properties 或 application.yml&#xff09;中的属性批量绑定到一个 Java Bean 中。 1. 定义配置文件 在 application.properties 或 application.yml 中定义一组具有相同前缀的属性。 application.yml &a…

刚安装docker并启动docker服务: systemctl restart docker报错解决

root:/home/lzw# sudo systemctl restart docker Job for docker.service failed because the control process exited with error code. See "systemctl status docker.service" and "journalctl -xeu docker.service" for details. 1、问题描述 启动doc…

JavaScript的this指向,一次彻底讲清楚

JavaScript 中的 this 指向是一个非常重要且容易混淆的概念。它的值取决于函数被调用的上下文,而不是函数定义的位置。以下是 this 指向的详细解析: 1. 默认绑定(Default Binding) 在非严格模式下,如果函数是直接调用(而不是作为对象的方法或构造函数等),this 默认指向…

MFC: 控件根据文本内容大小自动调整

背景&#xff1a; 针对不同语言下&#xff0c;控件显示不全的现象&#xff1b; 例如&#xff1a; 现象1&#xff1a;中文下显示全部信息&#xff0c;英语下只能显示部分文字 现象2&#xff1a;中文下显示不全## 实现思路&#xff1a; 控件绑定按钮计算控件文本长度根据文本长…

SpringBoot 整合mongoDB并自定义连接池,实现多数据源配置

要想在同一个springboot项目中使用多个数据源&#xff0c;最主要是每个数据源都有自己的mongoTemplate和MongoDbFactory。mongoTemplate和MongoDbFactory是负责对数据源进行交互的并管理链接的。 spring提供了一个注解EnableMongoRepositories 用来注释在某些路径下的MongoRepo…

软件测试中的BUG

文章目录 软件测试的生命周期BugBug 的概念描述 Bug 的要素案例Bug 级别Bug 的生命周期与开发产生争执怎么办&#xff1f;【高频面试题】先检查自身&#xff0c;Bug 是否描述的不清楚站在用户角度考虑并抛出问题Bug 的定级要有理有据提⾼自身技术和业务水平&#xff0c;做到不仅…

泵吸式激光可燃气体监测仪:快速精准守护燃气管网安全

在城市化进程加速的今天&#xff0c;燃气泄漏、地下管网老化等问题时刻威胁着城市安全。如何实现精准、高效的可燃气体监测&#xff0c;守护“城市生命线”&#xff0c;成为新型基础设施建设的核心课题。泵吸式激光可燃气体监测仪&#xff0c;以创新科技赋能安全监测&#xff0…

第J3-1周:DenseNet算法 实现乳腺癌识别

文章目录 一、前言二、前期准备1.设置GPU2.划分数据集 三、搭建网络模型1.DenseLayer模块2.DenseBlock模块3.Transition模块4.构建DenseNet5.构建densenet121 四、训练模型1.编写训练函数2.编写测试函数3.正式训练 五、结果可视化1.Loss与Accuracy图2.模型评估 总结&#xff1a…

【JAVA面试题】== 和 equals() 的区别与使用场景

在 Java 面试中&#xff0c; 和 equals() 的区别是一个高频考点。理解它们的底层原理和使用场景&#xff0c;对于掌握 Java 基础知识至关重要。本文将从 基本概念、底层实现 和 实际应用 三个方面&#xff0c;深入解析 和 equals() 的区别。 1. 基本概念 1.1 运算符 作用&a…

-bash: lsof: command not found

一、问题说明 执行如下命令时报错&#xff1a; # lsof |grep deleted > deleted_file -bash: lsof: command not found二、处理方法 # yum -y install lsof安装完成后可成功执行上面的命令。

摄像头应用编程(三):多平面视频采集

文章目录 1、前言2、环境介绍3、步骤4、应用程序编写5、测试5.1、编译应用程序5.2、运行应用程序 6、总结 1、前言 在查看摄像头类型时&#xff0c;大致可以分为两类&#xff1a;Video Capture 和 Video Capture Multiplanar。 本次应用程序主要针对类型为Video Capture Multi…