亚洲乱码中文字幕综合,中国熟女仑乱hd,亚洲精品乱拍国产一区二区三区,一本大道卡一卡二卡三乱码全集资源,又粗又黄又硬又爽的免费视频

怎樣通過分析GC日志來定位Java進(jìn)程的內(nèi)存問題

 更新時(shí)間:2025年07月01日 15:19:29   作者:alden_ygq  
這篇文章主要介紹了怎樣通過分析GC日志來定位Java進(jìn)程的內(nèi)存問題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教

GC 日志是排查 Java 內(nèi)存問題的核心工具,通過分析日志可以了解堆內(nèi)存使用模式、GC 頻率、對(duì)象晉升規(guī)律等關(guān)鍵信息。以下是系統(tǒng)化的分析方法:

一、GC 日志基礎(chǔ)配置

1. 啟用詳細(xì) GC 日志

java -XX:+PrintGCDetails \
     -XX:+PrintGCDateStamps \
     -XX:+PrintHeapAtGC \
     -XX:+PrintTenuringDistribution \
     -XX:+PrintGCApplicationStoppedTime \
     -Xloggc:/var/log/gc.log \
     -XX:+UseGCLogFileRotation \
     -XX:NumberOfGCLogFiles=5 \
     -XX:GCLogFileSize=20M \
     -jar your-app.jar

2. 不同收集器的日志格式

G1 收集器

[GC pause (G1 Evacuation Pause) (young), 0.0144227 secs]
   [Parallel Time: 13.0 ms, GC Workers: 8]
   [Code Root Fixup: 0.1 ms]
   [Code Root Scanning: 0.1 ms]
   [Object Copy: 12.6 ms]
   [Termination: 0.1 ms]
   [Termination Attempts: 1]
   [GC Worker Other: 0.1 ms]
   [GC Worker Total: 12.9 ms]
   [GC Worker End: 422.5 ms]
   [Code Root Fixup: 0.0 ms]
   [Code Root Scanning: 0.0 ms]
   [Clear CT: 0.2 ms]
   [Other: 1.2 ms]
   [Choose CSet: 0.0 ms]
   [Ref Proc: 0.6 ms]
   [Ref Enq: 0.0 ms]
   [Redirty Cards: 0.1 ms]
   [Humongous Register: 0.0 ms]
   [Humongous Reclaim: 0.0 ms]
   [Free CSet: 0.0 ms]
   [Eden: 24.0M(24.0M)->0.0B(20.0M) Survivors: 0.0B->4.0M Heap: 24.0M(256.0M)->20.4M(256.0M)]
 [Times: user=0.09 sys=0.00, real=0.01 secs]

CMS 收集器

[GC (Allocation Failure) [PSYoungGen: 8192K->512K(9216K)] 8192K->6848K(19456K), 0.0034949 secs] [Times: user=0.01 sys=0.00, real=0.00 secs]
[Full GC (Metadata GC Threshold) [PSYoungGen: 512K->0K(9216K)] [ParOldGen: 6336K->6848K(10240K)] 6848K->6848K(19456K), [Metaspace: 2560K->2560K(1056768K)], 0.0254310 secs] [Times: user=0.09 sys=0.00, real=0.03 secs]

二、關(guān)鍵指標(biāo)與分析維度

1. GC 頻率與耗時(shí)

問題表現(xiàn):頻繁 GC 或單次 GC 時(shí)間過長(zhǎng)。

日志特征

[GC (Allocation Failure) 514M->488M(1024M), 0.0124612 secs]

分析工具

# 使用grep統(tǒng)計(jì)GC次數(shù)和總耗時(shí)
grep "GC" gc.log | wc -l  # Minor GC次數(shù)
grep "Full GC" gc.log | wc -l  # Full GC次數(shù)

# 計(jì)算平均GC耗時(shí)
awk '/GC.*secs/ {sum+=$NF} END {print "Average GC time: " sum/NR " secs"}' gc.log

2. 堆內(nèi)存使用趨勢(shì)

問題表現(xiàn):堆內(nèi)存持續(xù)增長(zhǎng),接近上限。

日志特征

[Eden: 24.0M(24.0M)->0.0B(20.0M) Survivors: 0.0B->4.0M Heap: 24.0M(256.0M)->20.4M(256.0M)]

分析重點(diǎn)

  • Eden 區(qū):頻繁 GC 后 Eden 區(qū)是否能有效回收。
  • 老年代:是否持續(xù)增長(zhǎng),是否觸發(fā) Full GC。

3. 對(duì)象晉升情況

問題表現(xiàn):對(duì)象過早晉升到老年代,導(dǎo)致老年代空間不足。

日志特征

[Tenuring Distribution]
  age   1:    1310720 bytes,    1310720 total
  age   2:     655360 bytes,    1966080 total
  age   3:     327680 bytes,    2293760 total

分析工具

# 提取對(duì)象年齡分布
grep -A 5 "Tenuring Distribution" gc.log

4. 垃圾收集器行為

問題表現(xiàn):CMS 并發(fā)模式失敗、G1 Mixed GC 頻繁。

日志特征

[GC (CMS Initial Mark)] [1 CMS-initial-mark: 4194304K(8388608K)] 4294901K(12582912K), 0.0024210 secs] [Times: user=0.01 sys=0.00, real=0.00 secs]

三、常見內(nèi)存問題與日志特征

問題 1:頻繁 Minor GC

日志特征

[GC (Allocation Failure) 204800K->163840K(262144K), 0.0102400 secs]

可能原因

  • 新生代空間過?。?Xmn 配置不合理)。
  • 對(duì)象分配率過高(短時(shí)間內(nèi)創(chuàng)建大量對(duì)象)。

解決方案

# 增大新生代比例
java -Xmn2g -XX:NewRatio=1 YourApp

問題 2:頻繁 Full GC

日志特征

[Full GC (Metadata GC Threshold) 524288K->512000K(1048576K), 0.5234120 secs]

可能原因

  • 老年代空間不足(大對(duì)象直接進(jìn)入老年代)。
  • 永久代 / 元空間溢出(類加載過多)。
  • 內(nèi)存泄漏(對(duì)象無法被回收)。

解決方案

# 增大老年代空間
java -Xms8g -Xmx8g -XX:NewRatio=4 YourApp

# 限制元空間大小
java -XX:MetaspaceSize=256m -XX:MaxMetaspaceSize=512m YourApp

問題 3:長(zhǎng)時(shí)間 GC 停頓

日志特征

[GC pause (G1 Humongous Allocation) (young), 1.2345678 secs]

可能原因

  • 使用 CMS 收集器,并發(fā)階段失敗觸發(fā) Full GC。
  • 堆內(nèi)存過大,導(dǎo)致標(biāo)記和清理時(shí)間過長(zhǎng)。

解決方案

# 切換到G1或ZGC收集器
java -XX:+UseG1GC -XX:MaxGCPauseMillis=200 YourApp

# 限制單次GC最大停頓時(shí)間
java -XX:+UseZGC -XX:ConcGCThreads=8 YourApp

四、GC 日志分析工具

1. 命令行工具

# 統(tǒng)計(jì)GC頻率和耗時(shí)
grep "GC" gc.log | awk '{print $4, $NF}'

# 分析堆內(nèi)存變化趨勢(shì)
grep "\[Heap\]" gc.log | awk '{print $6, $8}'

2. 可視化工具

GCEasy(在線工具):

# 上傳gc.log到https://gceasy.io/分析

GCViewer(本地工具):

java -jar gcviewer-1.36.jar gc.log

Java Mission Control (JMC)

jmc &  # 打開JMC,導(dǎo)入GC日志

3. 關(guān)鍵報(bào)告指標(biāo)

  • GC 頻率:每分鐘 Minor GC 和 Full GC 次數(shù)。
  • GC 耗時(shí)占比:GC 時(shí)間占應(yīng)用運(yùn)行時(shí)間的百分比。
  • 內(nèi)存分配率:每秒分配的內(nèi)存大小。
  • 晉升率:每秒從新生代晉升到老年代的對(duì)象大小。

五、GC 日志分析流程

確認(rèn) GC 類型:區(qū)分 Minor GC、Major GC、Full GC。

檢查 GC 頻率:是否過于頻繁(如每分鐘超過 10 次 Full GC)。

分析內(nèi)存趨勢(shì)

  • 堆內(nèi)存是否持續(xù)增長(zhǎng)?
  • 老年代增長(zhǎng)速率是否異常?

檢查 GC 耗時(shí):?jiǎn)未?GC 時(shí)間是否過長(zhǎng)(如超過 500ms)。

查看對(duì)象晉升

  • 是否有大量對(duì)象過早晉升?
  • 晉升閾值是否合理(-XX:MaxTenuringThreshold)?

定位 GC 原因

  • 是 Allocation Failure 還是 CMS-concurrent-mode-failure?

結(jié)合堆轉(zhuǎn)儲(chǔ)分析

# 在GC前后生成堆轉(zhuǎn)儲(chǔ)文件
jmap -dump:format=b,file=before_gc.hprof <pid>
# 觸發(fā)GC
jcmd <pid> GC.run
jmap -dump:format=b,file=after_gc.hprof <pid>

六、優(yōu)化建議

合理分配堆內(nèi)存

# 根據(jù)應(yīng)用特性調(diào)整新生代和老年代比例
java -Xms4g -Xmx4g -Xmn2g YourApp

選擇合適的收集器

# 大內(nèi)存應(yīng)用推薦G1
java -XX:+UseG1GC -XX:MaxGCPauseMillis=200 YourApp

# 超低延遲場(chǎng)景推薦ZGC
java -XX:+UseZGC -XX:ConcGCThreads=8 YourApp

優(yōu)化對(duì)象生命周期

  • 減少長(zhǎng)生命周期對(duì)象持有短生命周期對(duì)象的引用。
  • 及時(shí)釋放不再使用的資源(如集合、連接池)。

監(jiān)控與預(yù)警

  • 設(shè)置 GC 頻率和耗時(shí)的告警閾值。
  • 定期分析 GC 日志,建立基線。

通過系統(tǒng)分析 GC 日志,可以精準(zhǔn)定位內(nèi)存泄漏、對(duì)象分配不合理、收集器選擇不當(dāng)?shù)葐栴},從而優(yōu)化 JVM 配置,提升應(yīng)用性能。

總結(jié)

以上為個(gè)人經(jīng)驗(yàn),希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。

相關(guān)文章

  • 三分鐘快速掌握J(rèn)ava中枚舉(enum)

    三分鐘快速掌握J(rèn)ava中枚舉(enum)

    enum的全稱為enumeration, 是 JDK 1.5中引入的新特性,存放在 java.lang包中。下面這篇文章是我在使用enum過程中的一些經(jīng)驗(yàn)和總結(jié),分享出來方便大家快速的掌握J(rèn)ava中枚舉(enum),有需要的朋友們下面跟著小編來一起看看吧。
    2016-12-12
  • SpringBoot基于沙箱環(huán)境實(shí)現(xiàn)支付寶支付教程

    SpringBoot基于沙箱環(huán)境實(shí)現(xiàn)支付寶支付教程

    本文介紹了如何使用支付寶沙箱環(huán)境進(jìn)行開發(fā)測(cè)試,包括沙箱環(huán)境的介紹、準(zhǔn)備步驟、在Spring Boot項(xiàng)目中結(jié)合支付寶沙箱進(jìn)行支付接口的實(shí)現(xiàn)與測(cè)試
    2025-03-03
  • 關(guān)于SaCheckPermission權(quán)限校驗(yàn)注解

    關(guān)于SaCheckPermission權(quán)限校驗(yàn)注解

    在若依框架(RuoYi)的前后端分離版4.8.x中,SaCheckPermission注解用于權(quán)限校驗(yàn),這個(gè)注解可以應(yīng)用在方法上,以確保只有具有相應(yīng)權(quán)限的用戶才能訪問該方法
    2024-11-11
  • SpringBoot中整合Minio文件存儲(chǔ)的安裝部署過程

    SpringBoot中整合Minio文件存儲(chǔ)的安裝部署過程

    這篇文章主要介紹了SpringBoot整合Minio文件存儲(chǔ)的相關(guān)知識(shí),詳細(xì)介紹了Minio安裝部署過程,需要的朋友可以參考下
    2022-04-04
  • 一篇文章帶你了解初始Spring

    一篇文章帶你了解初始Spring

    這篇文章主要給大家介紹了一個(gè)簡(jiǎn)單的Spring容器初始化流程的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-08-08
  • Java 訪問剪切板(復(fù)制,粘貼)的示例

    Java 訪問剪切板(復(fù)制,粘貼)的示例

    這篇文章主要介紹了Java 訪問剪切板(復(fù)制,粘貼)的示例,幫助大家更好的理解和使用Java,感興趣的朋友可以了解下
    2020-11-11
  • java自定義序列化的具體使用

    java自定義序列化的具體使用

    本文主要介紹了java自定義序列化的具體使用,文中通過示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2021-11-11
  • AJAX+JAVA用戶登陸注冊(cè)驗(yàn)證的實(shí)現(xiàn)代碼

    AJAX+JAVA用戶登陸注冊(cè)驗(yàn)證的實(shí)現(xiàn)代碼

    這篇文章主要介紹了AJAX+JAVA用戶登陸注冊(cè)驗(yàn)證的實(shí)現(xiàn)代碼,通過ajax異步刷新頁(yè)面驗(yàn)證用戶輸入的賬號(hào)密碼是否在數(shù)據(jù)庫(kù)中存在。非常具有實(shí)用價(jià)值,需要的朋友可以參考下
    2018-06-06
  • Java中final關(guān)鍵字詳解及實(shí)例

    Java中final關(guān)鍵字詳解及實(shí)例

    這篇文章主要介紹了Java中final關(guān)鍵字詳解及實(shí)例,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-03-03
  • Spring?Boot?基于?SCRAM?認(rèn)證集成?Kafka?的過程詳解

    Spring?Boot?基于?SCRAM?認(rèn)證集成?Kafka?的過程詳解

    在本篇文章中,我們將探討如何在?Spring?Boot?應(yīng)用中集成?Kafka?并使用?SCRAM?認(rèn)證機(jī)制進(jìn)行安全連接,并實(shí)現(xiàn)動(dòng)態(tài)創(chuàng)建賬號(hào)、ACL?權(quán)限、Topic,以及生產(chǎn)者和消費(fèi)者等操作,感興趣的朋友跟隨小編一起看看吧
    2024-08-08

最新評(píng)論