java性能調(diào)優(yōu)System的gc垃圾回收方法
一、什么是System.gc()?
System.gc()是用Java,C#和許多其他流行的高級(jí)編程語(yǔ)言提供的API。當(dāng)它被調(diào)用時(shí),它將盡最大努力從內(nèi)存中清除垃圾(即未被引用的對(duì)象)。名詞解釋?zhuān)篏C,Garbage Collection,垃圾回收,下文會(huì)經(jīng)常使用。
二、誰(shuí)可以調(diào)用System.gc()?
System.gc() 可以從應(yīng)用程序堆棧的各個(gè)部分調(diào)用:
- 您自己開(kāi)發(fā)的應(yīng)用程序可以顯式的調(diào)用 System.gc() 方法。
- System.gc() 也可以由您的第三方庫(kù),框架觸發(fā)。
- 可以由外部工具(如VisualVM)通過(guò)使用JMX觸發(fā)
- 如果您的應(yīng)用程序使用了RMI,RMI會(huì)定期調(diào)用 System.gc() 。
三、調(diào)用System.gc()有什么弊端?
當(dāng) System.gc() 或 Runtime.getRuntime().gc()API被調(diào)用時(shí),將觸發(fā)完整的GC事件。在GC完成之前,整個(gè)JVM將凍結(jié)(即正在運(yùn)行的所有服務(wù)將被暫停),通常完整的GC需要很長(zhǎng)時(shí)間才能完成。因此在不合適的時(shí)間運(yùn)行GC,將導(dǎo)致不良的用戶體驗(yàn),甚至是崩潰。JVM具有復(fù)雜的算法,該算法始終在后臺(tái)運(yùn)行,進(jìn)行所有計(jì)算以及有關(guān)何時(shí)觸發(fā)GC的計(jì)算。當(dāng)您顯式調(diào)用System.gc()調(diào)用時(shí),所有這些計(jì)算都將被拋掉。
四、哪些場(chǎng)景適合顯式調(diào)用System.gc()?
GC操作應(yīng)該由JVM自行控制,在絕大部分的場(chǎng)景都不建議程序員手動(dòng)寫(xiě)代碼顯式進(jìn)行System.gc()操作,但是也不排除其中個(gè)別例外:在我們開(kāi)發(fā)多個(gè)微服務(wù)時(shí),每個(gè)服務(wù)都有多個(gè)備份節(jié)點(diǎn)。在非業(yè)務(wù)高峰時(shí)段,我們可以從微服務(wù)-負(fù)載均衡的節(jié)點(diǎn)池中取出其中一個(gè)JVM實(shí)例。然后通過(guò)該JVM上的JMX顯式觸發(fā)System.gc()調(diào)用,一旦GC事件完成并且從內(nèi)存中清除了垃圾,將該JVM放回到微服務(wù)-負(fù)載均衡的節(jié)點(diǎn)池中。當(dāng)然這個(gè)過(guò)程需要很好的微服務(wù)管理及服務(wù)發(fā)布機(jī)制配合,這樣既能保證JVM垃圾內(nèi)存的有效清理,又不影響業(yè)務(wù)的正常運(yùn)行。
五、如何檢測(cè)您的應(yīng)用程序正在進(jìn)行System.gc()?
如第二小節(jié)所講: System.gc() 可以從多個(gè)渠道進(jìn)行的調(diào)用,而不僅僅是從您的應(yīng)用程序源代碼進(jìn)行的調(diào)用。因此,搜索您的應(yīng)用程序代碼System.gc() 字符串,不足以知道 GC是否正在被調(diào)用。這就構(gòu)成了一個(gè)挑戰(zhàn):如何檢測(cè)應(yīng)用程序是否正在進(jìn)行垃圾回收?這就是GC日志派上用場(chǎng)的地方。
// java 8 啟用GC日志: // -XX: PrintGCDetails -Xloggc:<gc-log-file-path> ,例如下面這行代碼 -XX: PrintGCDetails -Xloggc:/opt/tmp/myapp-gc.log // java 9 啟用GC日志:-Xlog:gc*:file=<gc-log-file-path> ,例如下面這行代碼 -Xlog:gc*:file=/opt/tmp/myapp-gc.log
建議始終在所有生產(chǎn)服務(wù)器中始終啟用GC日志,因?yàn)樗兄谀懦收喜?yōu)化應(yīng)用程序性能。啟用GC日志只會(huì)增加微不足道的開(kāi)銷(xiāo)。還可以將您的GC日志上傳到垃圾收集日志分析器工具,例如GCeasy,HP JMeter等。這些工具將生成豐富的垃圾收集分析報(bào)告。

上圖摘自GCeasy生成的報(bào)告。
六、如何禁止GC顯式調(diào)用或調(diào)整調(diào)用GC的頻率?
如果我們就是想避免程序員顯式調(diào)用GC,避免不成熟的程序員在不合適時(shí)間調(diào)用GC,避免人為造成的GC崩潰,該怎么辦?可以通過(guò)如下方法:
搜索和替換
在代碼庫(kù)中搜索 System.gc() 和Runtime.getRuntime().gc()。如果看到匹配項(xiàng),則將其刪除。但是這種方法無(wú)法避免第三方庫(kù)、框架或通過(guò)外部源進(jìn)行調(diào)用,那么參考第二種方法。
通過(guò)JVM參數(shù)強(qiáng)制禁止
通過(guò)傳遞JVM參數(shù) -XX: DisableExplicitGC來(lái)強(qiáng)制禁止顯式調(diào)用。這種方式強(qiáng)制、有效,應(yīng)用程序內(nèi)的任何GC顯式代碼調(diào)用System.gc() 都將被禁止生效。JVM自身的GC策略不受此參數(shù)影響,只禁止人為的觸發(fā)GC。
RMI
如果您的應(yīng)用程序正在使用RMI,則可以控制GC調(diào)用的頻率 。啟動(dòng)應(yīng)用程序時(shí),可以使用以下JVM參數(shù)配置該頻率:
-Dsun.rmi.dgc.server.gcInterval=n
-Dsun.rmi.dgc.client.gcInterval=n
這些屬性的默認(rèn)值在
- JDK 1.4.2和5.0是60000毫秒(即60秒)
- JDK 6和更高版本是3600000毫秒(即60分鐘)
如果您的應(yīng)用主機(jī)內(nèi)存資源非常富余,您可以將這些屬性設(shè)置為很高的值,以便可以將GC帶來(lái)的對(duì)應(yīng)用程序的影響最小化。這也是應(yīng)用程序性能優(yōu)化的一種方式之一。
以上就是java性能調(diào)優(yōu)System的gc垃圾回收方法的詳細(xì)內(nèi)容,更多關(guān)于java性能調(diào)優(yōu)Systemgc垃圾回收的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
JAVA異常信息Exception?e及e的相關(guān)方法解讀
這篇文章主要介紹了JAVA異常信息Exception?e及e的相關(guān)方法解讀,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-06-06
SpringBoot啟動(dòng)時(shí)如何通過(guò)啟動(dòng)參數(shù)指定logback的位置
這篇文章主要介紹了SpringBoot啟動(dòng)時(shí)如何通過(guò)啟動(dòng)參數(shù)指定logback的位置,在spring boot中,使用logback配置的方式常用的有兩種,本文給大家介紹的非常詳細(xì),需要的朋友可以參考下2023-07-07
Spring Security 在 Spring Boot 中的使用詳解【集中式】
這篇文章主要介紹了Spring Security 在 Spring Boot 中的使用【集中式】,本文通過(guò)圖文并茂的形式給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-10-10
淺談SpringMVC+Spring3+Hibernate4開(kāi)發(fā)環(huán)境搭建
MVC已經(jīng)是現(xiàn)代Web開(kāi)發(fā)中的一個(gè)很重要的部分,本文介紹一下SpringMVC+Spring3+Hibernate4的開(kāi)發(fā)環(huán)境搭建,有興趣的可以了解一下。2017-01-01
Java返回文件時(shí)為圖片或pdf等設(shè)置在線預(yù)覽或下載功能
這篇文章主要介紹了Java返回文件時(shí)為圖片或pdf等設(shè)置在線預(yù)覽或下載功能,本文給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友參考下吧2024-01-01
springboot 多數(shù)據(jù)源配置不生效遇到的坑及解決
這篇文章主要介紹了springboot 多數(shù)據(jù)源配置不生效遇到的坑及解決,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2021-11-11
Java使用Jsoup解析html網(wǎng)頁(yè)的實(shí)現(xiàn)步驟
Jsoup是一個(gè)用于解析HTML文檔的Java庫(kù),本文主要介紹了Java使用Jsoup解析html網(wǎng)頁(yè)的實(shí)現(xiàn)步驟,可以提取文本、鏈接、圖片等,具有一定的參考價(jià)值,感興趣的可以了解一下2024-02-02
前后端項(xiàng)目分離解決cors錯(cuò)誤的方法詳解
隨著前后端分離技術(shù)的越來(lái)越盛行,跨域問(wèn)題也逐漸凸顯了出來(lái),下面這篇文章主要給大家介紹了關(guān)于前后端項(xiàng)目分離解決cors錯(cuò)誤的相關(guān)資料,文中通過(guò)實(shí)例代碼介紹的非常詳細(xì),需要的朋友可以參考下2023-02-02

