JVM性能調(diào)優(yōu)之運(yùn)行時(shí)參數(shù)小結(jié)
熟悉JVM參數(shù)對(duì)于系統(tǒng)調(diào)優(yōu)是非常重要的。比如一個(gè)高流量的延遲的電子交易平臺(tái),它要求的響應(yīng)時(shí)間都是毫秒級(jí)的。要獲得適合的參數(shù)組合需要大量的分析和不斷地嘗試,更依賴交易系統(tǒng)的特性。
本帖將主要講解JVM的運(yùn)行時(shí)參數(shù)的分類及其使用方式。
1、JVM參數(shù)選項(xiàng)類型
JVM參數(shù)總體上來(lái)說(shuō)分為三大類,分別是標(biāo)準(zhǔn)參數(shù)選項(xiàng)、非標(biāo)準(zhǔn)參數(shù)選項(xiàng)和非穩(wěn)定參數(shù)選項(xiàng),下面分別詳細(xì)介紹三大參數(shù)類型。
1.1、標(biāo)準(zhǔn)參數(shù)選項(xiàng)
所有的JVM都必須實(shí)現(xiàn)標(biāo)準(zhǔn)參數(shù)的功能,而且向后兼容。標(biāo)準(zhǔn)參數(shù)是相對(duì)比較穩(wěn)定的參數(shù),后續(xù)版本基本不會(huì)發(fā)生變化,參數(shù)以“-”開頭,例如大家常見(jiàn)的“-version”參數(shù)就是標(biāo)準(zhǔn)參數(shù)。獲取標(biāo)準(zhǔn)參數(shù)的命令是在終端輸入“java”或者“java -help”命令即可,獲取結(jié)果如下表所示:
需要注意的是HotSpot虛擬機(jī)的兩種模式,分別是Server和Client,分別通過(guò)-server和-client模式設(shè)置。
在32位Windows系統(tǒng)上,默認(rèn)使用Client類型的JVM。要想使用Server模式,則機(jī)器配置至少有2個(gè)以上的CPU和2GB以上的物理內(nèi)存。Client模式適用于對(duì)內(nèi)存要求較小的桌面應(yīng)用程序,默認(rèn)使用Serial串行垃圾收集器。
64位機(jī)器上只支持Server模式的JVM,適用于需要大內(nèi)存的應(yīng)用程序,默認(rèn)使用并行垃圾收集器。
1.2、非標(biāo)準(zhǔn)參數(shù)選項(xiàng)
我們知道JVM可以有不同的生產(chǎn)廠商,非標(biāo)準(zhǔn)參數(shù)的意思是并不保證所有JVM都對(duì)非標(biāo)準(zhǔn)參數(shù)進(jìn)行實(shí)現(xiàn),即只能被部分JVM識(shí)別且不保證向后兼容,功能相對(duì)來(lái)說(shuō)也是比較穩(wěn)定的,但是后續(xù)版本有可能會(huì)變更,參數(shù)以“-X”開頭。可以用java -X來(lái)檢索非標(biāo)準(zhǔn)參數(shù),不能保證所有參數(shù)都可以被檢索出來(lái),例如其中就沒(méi)有-Xcomp。下表列出了常見(jiàn)的非標(biāo)準(zhǔn)參數(shù)。
特別注意的是-Xint參數(shù)表示禁用JIT,所有的字節(jié)碼都被解釋執(zhí)行,這個(gè)模式下系統(tǒng)啟動(dòng)最快,但是執(zhí)行效率最低。-Xcomp表示JVM采用編譯模式,代碼執(zhí)行很快,但是啟動(dòng)會(huì)比較慢。-Xmixed表示JVM采用混合模式,啟動(dòng)速度較快,讓JIT根據(jù)程序運(yùn)行的情況,對(duì)熱點(diǎn)代碼實(shí)行檢測(cè)和編譯。
雖然-Xms、-Xmx和-Xss三個(gè)參數(shù)歸屬于-X參數(shù)選項(xiàng),但是這三個(gè)參數(shù)的執(zhí)行效果分別等同于非穩(wěn)定參數(shù)中的-XX:InitialHeapSize、-XX:MaxHeapSize和-XX:ThreadStackSize。
1.3、非穩(wěn)定參數(shù)選項(xiàng)
非穩(wěn)定參數(shù)選項(xiàng)以-XX開頭,也屬于非標(biāo)準(zhǔn)參數(shù),相對(duì)不穩(wěn)定,在JVM中是不健壯的,也可能會(huì)突然直接取消某項(xiàng)參數(shù),主要用于JVM調(diào)優(yōu)和調(diào)試。但是這些參數(shù)中有很多參數(shù)對(duì)于JVM調(diào)優(yōu)很有用處,所以也是使用最多的參數(shù)選項(xiàng)。
-XX參數(shù)又分為布爾類型參數(shù)和非布爾類型參數(shù)。布爾類型的格式為-XX:+/-,-XX:+表示啟用option,-XX:-表示禁用option。例如-XX:+UseParallelGC表示開啟ParallelGC垃圾收集器,-XX:-UseParallelGC表示關(guān)閉ParallelGC垃圾收集器,有些參數(shù)是默認(rèn)開啟的,調(diào)優(yōu)的時(shí)候可以考慮關(guān)閉某些參數(shù)。
非布爾類型的參數(shù)也可以理解為Key-Value型的參數(shù),可以分為數(shù)值類型和非數(shù)值類型。數(shù)值類型格式為-XX:=,number可以帶上單位(k、K表示千字節(jié),m、M表示兆,或者使用更大的內(nèi)存單位g、G),例如-XX:NewSize=1024m表示設(shè)置新生代初始大小為1024MB。非數(shù)值類型格式為-XX:=,例如-XX:HeapDumpPath=/usr/local/heapdump.hprof用來(lái)指定heap轉(zhuǎn)存文件的存儲(chǔ)路徑。
通過(guò)“java -XX:+PrintFlagsFinal”命令可以查看所有的-XX參數(shù),如下圖所示,篇幅原因截取部分截圖。
上圖最后一列參數(shù)的取值有多種,如下所示:
- (1)product表示該類型參數(shù)是官方支持的,屬于JVM內(nèi)部選項(xiàng)。
- (2)rw表示可動(dòng)態(tài)寫入。
- (3)C1表示Client JIT編譯器。
- (4)C2表示Server JIT編譯器。
- (5)pd表示平臺(tái)獨(dú)立。
- (6)lp64表示僅支持64位JVM。
- (7)manageable表示可以運(yùn)行時(shí)修改。
- (8)diagnostic表示用于JVM調(diào)試。
- (9)experimental表示非官方支持的參數(shù)。
默認(rèn)不包含diagnostic和experimental兩種類型,想要包含該類型的參數(shù)可以配合參數(shù)-XX:+UnlockDiagnosticVMOptions和-XX:+UnlockExperimentalVMOptions使用,例如java-XX:+PrintFlagsFinal -XX:+UnlockDiagnosticVMOptions命令結(jié)果如下(部分結(jié)果),包含了diagnostic類型的參數(shù)。同理可以添加-XX:+UnlockExperimentalVMOptions參數(shù)用于包含experimental類型的參數(shù),不再演示。
2、添加JVM參數(shù)的方式
在工作中經(jīng)常需要配置JVM參數(shù),一般有以下幾種方式:
2.1、IDEA界面配置
鼠標(biāo)右鍵選中目標(biāo)工程,選擇“Run”→“Edit Configurations”選項(xiàng),選中要添加JVM參數(shù)的Application,然后在Configuration里面的VM options中輸入想要添加的JVM參數(shù)即可,如下圖所示,例如填入-Xmx256m,這樣就可以設(shè)置運(yùn)行時(shí)最大內(nèi)存為256MB。
2.2、通過(guò)java命令配置
通過(guò)java命令運(yùn)行class或者jar包的時(shí)候也可以添加JVM參數(shù),一般多用于工程測(cè)試,如下所示:
//運(yùn)行jar包時(shí)添加JVM參數(shù) java -Xms128m -Xmx256m -jar demo.jar //運(yùn)行類的字節(jié)碼文件時(shí)添加JVM參數(shù) java -Xms128m -Xmx256m 類名
2.3、通過(guò)web服務(wù)器配置
Linux系統(tǒng)下可以在tomcat/bin/catalina.sh中添加如下JVM配置。
JAVA_OPTS="-Xms512M -Xmx1024M"
Windows系統(tǒng)下可以在catalina.bat中添加如下配置。
set"JAVA_OPTS=-Xms512M -Xmx1024M"
2.4、通過(guò)jinfo命令配置
3、常用JVM參數(shù)選項(xiàng)
JVM參數(shù)選項(xiàng)那么多,在工作中有很多參數(shù)是很少用到的,這里匯總了幾大常用的參數(shù)分類,如下所示:
(1)輸出設(shè)置的-XX參數(shù)以及參數(shù)值的參數(shù)選項(xiàng)如下表所示:
(2)堆、棧、方法區(qū)等內(nèi)存大小設(shè)置的參數(shù)選項(xiàng)如下表所示:
(3)OutOfMemory相關(guān)的參數(shù)選項(xiàng)如下表所示:
-XX:OnOutOfMemoryError表示當(dāng)發(fā)生內(nèi)存溢出的時(shí)候,還可以讓JVM調(diào)用任一個(gè)shell腳本。大多數(shù)時(shí)候,內(nèi)存溢出并不會(huì)導(dǎo)致整個(gè)應(yīng)用都掛掉,但是最好還是把應(yīng)用重啟一下,因?yàn)橐坏┌l(fā)生了內(nèi)存溢出,可能會(huì)讓應(yīng)用處于一種不穩(wěn)定的狀態(tài),一個(gè)不穩(wěn)定的應(yīng)用可能會(huì)提供錯(cuò)誤的響應(yīng)。例如使用以下命令:
-XX:OnOutOfMemoryError=/opt/Server/restart.sh
當(dāng)給JVM傳遞上述參數(shù)的時(shí)候,如果發(fā)生了內(nèi)存溢出,JVM會(huì)調(diào)用/opt/Server/restart.sh這個(gè)腳本,在這個(gè)腳本中可以去用優(yōu)雅的辦法來(lái)重啟應(yīng)用。restart.sh腳本如下所示。
(4)垃圾收集器相關(guān)的參數(shù)選項(xiàng)因垃圾收集器的不同而不同,關(guān)于垃圾收集器的分類以及配合使用。使用-XX:+PrintCommandLineFlags查看命令行相關(guān)參數(shù),從中可以查看到當(dāng)前系統(tǒng)使用的垃圾收集器,也可以使用命令行指令jinfo查看。
Serial收集器作為HotSpot中Client模式下的默認(rèn)新生代垃圾收集器。Serial Old收集器是運(yùn)行在Client模式下默認(rèn)的老年代的垃圾收集器。-XX:+UseSerialGC參數(shù)可以指定新生代和老年代都使用串行收集器,表示新生代用Serial GC,且老年代用Serial Old收集器。可以獲得最高的單線程收集效率?,F(xiàn)在已經(jīng)很少使用Serial收集器了。
ParNew收集器可以使用-XX:+UseParNewGC參數(shù)指定。它表示新生代使用并行收集器,不影響老年代。Parallel收集器的相關(guān)JVM參數(shù)選項(xiàng)如下表:
CMS收集器的相關(guān)JVM參數(shù)選項(xiàng)如下表所示:
需要注意的是JDK 9新特性中CMS被標(biāo)記為Deprecate了,如果對(duì)JDK 9及以上版本的HotSpot虛擬機(jī)使用參數(shù)-XX:+UseConcMarkSweepGC來(lái)開啟CMS收集器的話,用戶會(huì)收到一個(gè)警告信息,提示CMS未來(lái)將會(huì)被廢棄。JDK 14新特性中刪除了CMS垃圾收集器,如果在JDK 14中使用-XX:+UseConcMarkSweepGC的話,JVM不會(huì)報(bào)錯(cuò),只是給出一個(gè)warning信息,但是不會(huì)exit。JVM會(huì)自動(dòng)回退以默認(rèn)GC方式啟動(dòng)JVM。
G1收集器的相關(guān)JVM參數(shù)選項(xiàng)如下表所示:
G1收集器主要涉及Mixed GC,Mixed GC會(huì)回收新生代和部分老年代,G1關(guān)于Mixed GC調(diào)優(yōu)常用參數(shù)選項(xiàng)如下表所示:
(5)GC日志相關(guān)的參數(shù)選項(xiàng)如下表所示:
(6)其他常用的參數(shù)選項(xiàng)如下表所示:
4、通過(guò)Java代碼獲取JVM參數(shù)
Java提供了java.lang.management包用于監(jiān)視和管理JVM和Java運(yùn)行時(shí)中的其他組件,它允許本地和遠(yuǎn)程監(jiān)控和管理運(yùn)行的JVM,會(huì)經(jīng)常使用到其中的ManagementFactory類。另外還有Runtime類也可以獲取一些內(nèi)存、CPU核數(shù)等相關(guān)的數(shù)據(jù)。通過(guò)這些API可以監(jiān)控我們的應(yīng)用服務(wù)器的堆內(nèi)存使用情況,也可以設(shè)置一些閾值進(jìn)行報(bào)警等處理,代碼清單如下演示了Java代碼獲取應(yīng)用的內(nèi)存使用情況:
運(yùn)行結(jié)果如下,可以看到堆內(nèi)存的各項(xiàng)信息:
5、小結(jié)
講解了JVM運(yùn)行時(shí)參數(shù),JVM參數(shù)對(duì)于系統(tǒng)調(diào)優(yōu)是非常重要的,參數(shù)分為三類,分別是標(biāo)準(zhǔn)參數(shù)選項(xiàng)、非標(biāo)準(zhǔn)參數(shù)選項(xiàng)和非穩(wěn)定參數(shù)選項(xiàng)。標(biāo)準(zhǔn)參數(shù)是所有的JVM實(shí)現(xiàn)都必須要實(shí)現(xiàn)的參數(shù),不同的JVM擁有相同的參數(shù)功能。非標(biāo)準(zhǔn)參數(shù)無(wú)法保證所有的JVM都會(huì)有對(duì)應(yīng)的實(shí)現(xiàn),該類型參數(shù)一般以“-X”開頭。非穩(wěn)定參數(shù)在JVM中是不健壯的,屬于試驗(yàn)性質(zhì)的參數(shù),有可能在不同的JVM版本中會(huì)被取消,該類型參數(shù)一般以“-XX”開頭,對(duì)于JVM調(diào)優(yōu)有很大的用處。
到此這篇關(guān)于JVM性能調(diào)優(yōu)之運(yùn)行時(shí)參數(shù)小結(jié)的文章就介紹到這了,更多相關(guān)JVM 運(yùn)行時(shí)參數(shù)內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Hibernate連接三種數(shù)據(jù)庫(kù)的配置文件
今天小編就為大家分享一篇關(guān)于Hibernate連接三種數(shù)據(jù)庫(kù)的配置文件,小編覺(jué)得內(nèi)容挺不錯(cuò)的,現(xiàn)在分享給大家,具有很好的參考價(jià)值,需要的朋友一起跟隨小編來(lái)看看吧2019-03-03SpringMVC記錄我遇到的坑_AOP注解無(wú)效,切面不執(zhí)行的解決
這篇文章主要介紹了SpringMVC記錄我遇到的坑_AOP注解無(wú)效,切面不執(zhí)行的解決方案,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2021-07-07使用Java打印數(shù)字組成的魔方陣及字符組成的鉆石圖形
這篇文章主要介紹了使用Java打印數(shù)字組成的魔方陣及字符組成的鉆石圖形,可作為一些CLI程序界面的基礎(chǔ)部分,需要的朋友可以參考下2016-03-03java?中如何實(shí)現(xiàn)?List?集合去重
這篇文章主要介紹了java?中如何實(shí)現(xiàn)?List?集合去重,List?去重指的是將?List?中的重復(fù)元素刪除掉的過(guò)程,下文操作操作過(guò)程介紹需要的小伙伴可以參考一下2022-05-05Java Spring動(dòng)態(tài)生成Mysql存儲(chǔ)過(guò)程詳解
這篇文章主要介紹了Java Spring動(dòng)態(tài)生成Mysql存儲(chǔ)過(guò)程詳解,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2020-06-06springboot使用Thymeleaf報(bào)錯(cuò)常見(jiàn)的幾種解決方案
這篇文章主要介紹了springboot使用Thymeleaf報(bào)錯(cuò)常見(jiàn)的幾種解決方案,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-11-11Java繪圖技術(shù)基礎(chǔ)(實(shí)例講解)
下面小編就為大家?guī)?lái)一篇Java繪圖技術(shù)基礎(chǔ)(實(shí)例講解)。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2017-08-08