探索進階 JVM 選項
1. 概述
Java 虛擬機器 (JVM) 是一個為 Java 應用程式提供支援的強大引擎。它是高度可自訂的,透過標準選項提供基本配置,透過非標準選項提供一般性能調整,並透過高級選項提供精確控制。
進階選項可讓開發人員微調效能、診斷問題並嘗試尖端功能。
在本教程中,我們將探討最著名的進階 JVM 選項以及如何使用它們,從而使我們能夠更細微地控制 JVM 行為。
2. JVM選項的分類
JVM 參數可分為三大類:
- 標準選項(
-version
、-help
) - 非標準選項(
-X:
選項) - 進階選項(
-XX:
選項)
3. 了解進階 JVM 選項
進階選項超越了基本配置,可以設定 JVM 的較低層級屬性。這些選項允許我們調整效能關鍵參數,例如垃圾收集、記憶體管理和運行時診斷。
其中一些進階選項也是常用的最重要的 JVM 參數之一。了解如何在 IntelliJ 中設定這些 JVM 選項有助於調整 JVM 以進行開發和偵錯。
但由於它們針對特定的應用場景提供了微調,我們必須謹慎使用它們。在沒有清楚了解應用程式行為的情況下進行過度自訂可能會導致效能不佳、崩潰或意外行為。
此外,不保證所有 JVM 實作都支援高階 JVM 選項,並且可能會變更。因此,由於這些選項隨著 JVM 更新而發展,因此某些選項可能會被棄用或在新版本中表現不同。
例如,Java 並發標記和清除垃圾收集演算法就發生過這種情況,該演算法在 Java 9 中已棄用,並在 Java 14 中被刪除。透過監控文檔,我們可以在發生任何變更之前隨時了解情況。
現在讓我們透過不同的類別來探索各種進階 JVM 選項。
4. 垃圾收集調優
垃圾收集對於記憶體管理至關重要,但可能會導致影響效能的暫停。進階選項提供對垃圾收集行為的控制,確保應用程式運作更順暢。
自 Java 9 以來,預設設定是垃圾優先垃圾收集器 (G1),旨在平衡吞吐量和延遲。
為了克服 G1 的延遲限制,JDK12 引入了 Shenandoah GC,可以透過
**-XX:+UseShenandoahGC
**選項。 Shenandoah 的可用性取決於 JDK 供應商和版本。
可以根據專門的工作負載使用其他實作。 Epsilon 垃圾收集器也非常適合效能調整,以檢查垃圾收集是否會影響我們程式的效能。
前面引用的主題探討了用於垃圾收集的各種有用的高級 JVM 選項。
5. 記憶體管理
正如我們上面所討論的,垃圾收集是記憶體管理的重要組成部分,但它只是 JVM 中更大的記憶體管理生態系統的一部分。
為了實現最佳效能,配置記憶體分配、管理堆大小以及了解堆外記憶體的工作原理同樣重要,特別是對於記憶體密集型應用程式或具有特定效能要求的系統。
現在,讓我們回顧一下與記憶體管理相關的一些進階 JVM 選項:
-
-XX:InitialHeapSize
**和-XX:MaxHeapSize
** – 這些選項定義初始堆大小和最大堆大小(以位元組為單位) -
-XX:MetaspaceSize
**和-XX:MaxMetaspaceSize
** – 這些選項定義元空間區域的初始大小和最大大小 -
-XX:InitialRAMPercentage
**和-XX:MaxRAMPercentage
** – 這些選項將初始和最大堆大小定義為系統可用記憶體的百分比。這些設定允許 JVM 動態擴展其記憶體使用量,提供更好的適應性 -
-XX:MinHeapFreeRatio
**和-XX:MaxHeapFreeRatio
** – 這些選項定義 GC 週期後堆中保留的可用空間的最小和最大百分比 -
-XX:+AlwaysPreTouch
– 透過在 JVM 初始化期間預先接觸 Java 堆來減少延遲。因此,每個堆頁都是在 JVM 啟動時初始化,而不是在應用程式執行期間增量初始化 -
-XX:MaxDirectMemorySize
– 定義可以為直接位元組緩衝區保留的記憶體量 -
-XX:CompressedClassSpaceSize
– 定義使用壓縮類別指標時在元空間中儲存類別元資料所分配的最大記憶體 (-XX:-UseCompressedClassPointers
)
6. 即時編譯
即時 (JIT) 編譯是一個重要的 JVM 元件,它在運行時將字節碼編譯為本機機器碼,從而提高 Java 應用程式的效能。 JIT 編譯器預設為啟用,除非調查 JIT 編譯問題,否則不建議停用它。
讓我們回顧一下用於設定和調整 JIT 編譯的高階 JVM 選項:
-
**-XX:CICompilerCount**
– 定義用於 JIT 編譯的編譯器執行緒數。預設值與可用 CPU 和記憶體的數量成正比 -
-XX:ReservedCodeCacheSize
– 定義分配用於儲存 JIT 編譯的本機程式碼的記憶體區域的最大大小 -
**-XX:CompileThreshold**
– 定義首次編譯方法之前的方法呼叫次數 -
**-XX:MaxInlineSize**
– 定義 JIT 編譯器可以內聯的方法的最大允許大小(以位元組為單位)
7. 診斷和調試
診斷和調試對於識別和解決 Java 應用程式中的問題至關重要,例如效能瓶頸、記憶體洩漏和意外行為。
讓我們回顧一下與診斷和調試相關的高級 JVM 選項,這些選項可以幫助我們更深入地了解應用程式的行為和效能:
-
-XX:+HeapDumpOnOutOfMemoryError
– 發生OutOfMemoryError
時產生堆轉儲 -
-XX:HeapDumpPath
– 定義保存堆轉儲的檔案路徑 -
-XX:+PrintCompilation
– 記錄 JIT 編譯 -
-XX:+LogCompilation
– 將詳細的 JIT 編譯日誌寫入文件 -
-XX:+UnlockDiagnosticVMOptions
– 解鎖預設不可用的診斷 JVM 選項 -
-XX:+ExitOnOutOfMemoryError
– 強制 JVM 在遇到OutOfMemoryError
時立即退出 -
-XX:+CrashOnOutOfMemoryError
– 強制 JVM 產生核心轉儲並在發生OutOfMemoryError
時崩潰 -
-XX:ErrorFile
– 定義發生不可回復錯誤時儲存錯誤資料的檔案路徑 -
-XX:NativeMemoryTracking
– 定義追蹤 JVM 本機記憶體使用情況的模式(關閉/摘要/詳細) -
-XX:+PrintNMTStatistics
– 允許在 JVM 退出時列印收集的本機記憶體追蹤資料。它只能在啟用本機記憶體追蹤時使用(-XX:NativeMemoryTracking
)
用於記錄 GC 資訊的高階 JVM 選項-XX:+PrintGC
和-XX:+PrintGCDetails
自 Java 9 起已被棄用,應替換為-Xlog
(統一日誌記錄選項)。
8. 人體工學
我們已經探索了許多強大的高級 JVM 選項,這可能會讓配置和調整 JVM 以滿足我們的特定要求感到不知所措。 JVM 透過人體工學提供了一種解決方案,根據底層硬體和運行時條件自動調整其行為,從而增強應用程式效能。
讓我們列出我們環境的所有人體工學預設值:
java -XX:+PrintFlagsFinal -version
然而,儘管人體工學旨在設定合理的預設值,但它們可能並不總是符合我們應用程式的需求。
9. 結論
在本文中,我們結合了全文引用的討論和所提供的分析中的見解,全面探討了高階 JVM 選項。
我們觀察了高級 JVM 參數以及它們如何增強垃圾收集、記憶體管理和運行時效能。雖然配置的範圍可能會讓人感到不知所措,但我們提到 JVM 人體工學是一種有用的解決方案,可以簡化調整流程並優化應用程式效能。