調用 System.gc() 的弊端及修復方式

弊端分析
  1. 不可控的執行時機
    System.gc()?僅是?建議?JVM 執行垃圾回收,但 JVM 可自由忽略該請求(尤其是高負載時)。實際回收時機不確定,無法保證內存及時釋放。

  2. 嚴重的性能問題

    • Stop-The-World 停頓:觸發 Full GC 時會暫停所有應用線程(可達秒級),導致系統卡頓。

    • 冗余回收:JVM 已有成熟的垃圾回收策略(如分代回收)。手動調用可能打斷優化策略,觸發不必要的 Full GC,浪費 CPU 資源。

  3. 干擾 JVM 自優化機制
    現代 JVM(如 HotSpot)基于內存分配/回收模式動態調整堆大小和 GC 策略。手動調用?System.gc()?會干擾此過程,降低自適應效率。

  4. 不同 JVM 行為差異

    • 部分 JVM(如 Oracle HotSpot)默認響應?System.gc()?并執行 Full GC。

    • 其他 JVM(如 Azul Zing)可能完全忽略。
      代碼可移植性降低。

  5. 掩蓋真實內存問題
    開發者可能誤用?System.gc()?作為“內存優化”手段,掩蓋內存泄漏或設計缺陷,延誤根本問題修復。


修復方式與最佳實踐
  1. 完全避免顯式調用?System.gc()
    原則:99% 的場景無需手動 GC。JVM 的內存管理優于人工干預。
    措施:刪除代碼中所有?System.gc()?調用。

  2. 通過 JVM 參數禁用顯式 GC
    添加啟動參數,強制忽略?System.gc()?調用:

    bash

    -XX:+DisableExplicitGC  # 禁止 System.gc() 觸發 Full GC

    適用場景:確保遺留代碼或第三方庫中的調用無效。

  3. 替換為建議式回收(謹慎使用)
    若必須請求回收(如性能測試),使用?輕量級建議

    java

    // Java 9+ 推薦
    java.lang.ref.Reference.reachabilityFence(obj); // 提示 JVM 可回收對象

    java

    // 或僅回收部分區域(JDK 8+)
    java.lang.management.MemoryMXBean bean = ManagementFactory.getMemoryMXBean();
    bean.gc(); // 觸發管理接口的 GC(仍不保證執行)
  4. 優化內存使用設計

    • 及時解引用:不再用的大對象顯式置?null(如緩存、集合)。

    • 使用弱引用:對緩存場景用?WeakHashMap?或?SoftReference,允許內存不足時自動回收。

    • 分治大對象:拆分大數據塊,避免單對象生命周期過長。

  5. 精準監控與調優 GC

    • 啟用 GC 日志

      bash

      -Xlog:gc*:file=gc.log:time:filecount=5,filesize=10m
    • 分析工具

      • JDK Mission Control / VisualVM

      • G1 GC 分析器(如 GCViewer)

    • 調優參數示例

      bash

      # G1 GC 優化(JDK 9+)
      -XX:+UseG1GC -XX:MaxGCPauseMillis=200 -XX:G1HeapRegionSize=4m

何時可能“需要”手動 GC?(極少見場景)
  1. 內存敏感測試:測量特定操作后內存占用量。
    方案:在測試中調用?System.gc()?前/后,但需配合?-XX:+DisableExplicitGC?避免生產環境生效。

  2. Native 資源管理:DirectByteBuffer 等堆外內存釋放。
    方案:用?sun.misc.Cleaner?或 JDK 14+ 的?MemorySegment?替代手動 GC。


總結

問題解決方案
不可控執行時機刪除調用 + JVM 參數禁用
Stop-The-World 停頓優化 GC 參數 + 選擇低延遲收集器
干擾 JVM 自優化依賴 JVM 默認策略
掩蓋內存泄漏用 Profiler 定位真實問題

核心原則:信任 JVM 的 GC 算法。通過監控、參數調優和代碼優化解決內存問題,而非手動調用?System.gc()

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/web/89324.shtml
繁體地址,請注明出處:http://hk.pswp.cn/web/89324.shtml
英文地址,請注明出處:http://en.pswp.cn/web/89324.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

git merge 和 git rebase 的區別

主要靠一張圖:區別 git merge git checkout feature git merge master此時在feature上git會自動產生一個新的commit 修改的是當前分支 feature。 git rebase git checkout feature git rebase master(在feature分支上執行,修改的是master分支…

Java學習--JVM(2)

JVM提供垃圾回收機制,其也是JVM的核心機制,其主要是實現自動回收不再被引用的對象所占用的內存;對內存進行整理,防止內存碎片化;以及對內存分配配進行管理。JVM 通過兩種主要算法判斷對象是否可回收:引用計…

用大模型(qwen)提取知識三元組并構建可視化知識圖譜:從文本到圖譜的完整實現

引言 知識圖譜作為一種結構化的知識表示方式,在智能問答、推薦系統、數據分析等領域有著廣泛應用。在信息爆炸的時代,如何從非結構化文本中提取有價值的知識并進行結構化展示,是NLP領域的重要任務。知識三元組(Subject-Relation-O…

(附源碼)基于 Go 和 gopacket+Fyne 的跨平臺網絡抓包工具開發實錄

基于 Go 和 gopacket Fyne 的跨平臺網絡抓包工具開發實錄 一、項目背景 在網絡安全、協議分析、運維排查等場景中,抓包工具是不可或缺的利器。Wireshark 雖然功能強大,但對于部分初學者或有定制需求的開發者來說,學習曲線較陡,且…

Langchain和Faiss搭建本地知識庫對比

對比 對比維度及優缺點分析對比維度LangChain(封裝 FAISS)直接使用 FAISS易用性? 高,提供高級封裝,簡化開發流程? 中等,需要熟悉 FAISS API學習成本? 低,適合快速開發? 高,需要掌握 FAISS 的…

Java常用命令匯總

JDK 工具命令jps(Java Virtual Machine Process Status Tool)命令示例:jps -l 應用場景:列出當前系統中所有Java進程的PID和主類名,常用于快速定位Java應用的進程ID。javac(Java Compiler)命令示…

Llama 2:開放基礎模型與微調聊天模型

溫馨提示: 本篇文章已同步至"AI專題精講" Llama 2:開放基礎模型與微調聊天模型 摘要 在本研究中,我們開發并發布了 Llama 2,一組預訓練和微調的大型語言模型(LLMs),其規模從 70 億參…

ThinkPHP 8 在 Apache 下啟用偽靜態

ThinkPHP 8 在 Apache 下啟用偽靜態,需要配置 .htaccess 文件并確保 Apache 支持 URL 重寫。以下是詳細設置步驟:1. 啟用 Apache 重寫模塊首先確保 Apache 的 mod_rewrite 模塊已啟用。編輯 Apache 配置文件(通常是 /etc/apache2/apache2.con…

Android開發中Retrofit使用方法與底層原理詳解

Retrofit 是 Android 開發中一個 類型安全、基于注解、高度解耦 的 RESTful HTTP 客戶端庫,由 Square 公司開發。它極大地簡化了 Android 應用與 Web 服務進行網絡交互的過程。 核心價值: 聲明式 API 定義: 使用 Java/Kotlin 接口和注解描述 …

基于FPGA的IIC控制EEPROM讀寫(2)

基于FPGA的IIC控制EEPROM讀寫 文章目錄基于FPGA的IIC控制EEPROM讀寫一、EEPROM簡介二、代碼實現——個人理解1、狀態機2、仿真效果3、上板驗證4、代碼top.viic_master.vuart三、代碼實現——復用性較高的IIC模塊1、框架設計2、狀態機設計3、仿真效果4、上板驗證5、代碼top.viic…

C# 界面程序在23H2型號系統中無法退出

20250716記錄 環境:c# winform問題描述:主界面退出直接使用了Environment.Exit(0); 程序假死,無法關閉解決措施://使用 this.Close();以下代碼目標:執行完程序自身后,刪除指定文件(可用于程序文…

Kafka——集群核心參數配置

引言在分布式系統中,Kafka 憑借其高吞吐量、低延遲和強大的擴展性,成為數據管道和流處理的首選解決方案。然而,要充分發揮 Kafka 的性能和穩定性,正確配置集群參數至關重要。為什么參數配置如此重要?Kafka 的參數配置直…

單臂路由實現VLAN互通實驗

實驗拓撲圖實驗需求:按照圖示為 PC3 和 PC4 配置 IP 地址和網關PC3 屬于 Vlan10,PC4 屬于 Vlan20,配置單臂路由實現 Vlan10 和 Vlan20 三層互通PC3 和 PC4 可以互通實驗步驟:1.PC 配置 IP 地址2.PC3 屬于 Vlan10,PC4 屬…

基于漸進式遷移學習網絡(PTLN)?的小樣本故障診斷模型

目錄 一、研究背景與挑戰? ?二、創新方法:漸進式遷移學習網絡(PTLN)?? ?1. 核心架構?編輯 ?2. 訓練優化? 三、核心代碼 四、實驗結果與優勢? ?1. 數據集? ?2. 性能對比? ?3. 關鍵驗證? 五、工程價值與未來方向? 六、補充信息? 一、研究背景與挑…

網絡原理 —— HTTP

通過網絡初識,我們認識了網絡的協議棧,TCP/IP 分為五層:應用層,傳輸層,網絡層,數據鏈路層,物理層。也介紹了其中的關鍵協議。而這些協議的理解,是我們寫網絡代碼的基礎。 應用層&…

docker--安裝--原理

安裝 鏈接 啟動之后,docker狀態查看: sudo systemctl status docker 添加普通用戶到docker用戶組: sudo usermod -aG docker $USER# 重啟或者使用以下命令刷新組權限:newgrp docker 原理

Java并發第一篇(從零開始:一文讀懂Java并發編程核心基礎)

從零開始:一文讀懂Java并發編程核心基礎一. 為什么需要并發編程?二. 并發編程的“另一面”:挑戰與代價2.1 頻繁的上下文切換2.2 線程安全問題(如:死鎖)三. 夯實基礎:必須掌握的核心概念與操作3.…

【刪庫跑路】一次刪除pip的所有第三方庫

進入命令行,先list看下庫存pip list導出所有的第三方庫至一文件列表pip freeze >requirements.txt按照列表卸載所有庫pip uninstall -r requirements.txt -y再list看下,可見庫存已清空

python 【技術面試題和HR面試題】?列表操作、條件判斷、循環、函數定義編程題

1.技術面試題 (1)解釋Linux中的進程、線程和守護進程的概念,以及如何管理它們? 答: 進程 概念:程序運行的實例,有獨立資源(如內存),是系統調度的基本單位。 管…

Debian 12中利用dpkg命令安裝MariaDB 11.8.2

MariaDB 11.8解決了2038問題,即在32位系統中將timestamp從2038-01-19 03:14:07 UTC擴展到2106-02-07 06:28:15 UTC,向后延長了68年。由于寫此文時Debian 12的源中還沒有MariaDB 11.8,采用源碼編譯又太費時,可用二進制碼或dpkg安裝 .下面簡要記…