詳解Java虛擬機(jī)(第⑥篇)——內(nèi)存分配與回收策略-創(chuàng)新互聯(lián)

詳解Java 虛擬機(jī)(第⑥篇)——內(nèi)存分配與回收策略

一、Minor GC 和 Full GC

  • Minor GC:回收新生代,因?yàn)樾律鷮?duì)象存活時(shí)間很短,因此 Minor GC 會(huì)頻繁執(zhí)行,執(zhí)行的速度一般也會(huì)比較快。
  • Full GC:回收老年代和新生代,老年代對(duì)象其存活時(shí)間長(zhǎng),因此 Full GC 很少執(zhí)行,執(zhí)行速度會(huì)比 Minor GC 慢很多。

二、內(nèi)存分配策略

1. 對(duì)象優(yōu)先在 Eden 分配

創(chuàng)新互聯(lián)建站憑借專業(yè)的設(shè)計(jì)團(tuán)隊(duì)扎實(shí)的技術(shù)支持、優(yōu)質(zhì)高效的服務(wù)意識(shí)和豐厚的資源優(yōu)勢(shì),提供專業(yè)的網(wǎng)站策劃、成都網(wǎng)站制作、成都網(wǎng)站設(shè)計(jì)、網(wǎng)站優(yōu)化、軟件開發(fā)、網(wǎng)站改版等服務(wù),在成都10多年的網(wǎng)站建設(shè)設(shè)計(jì)經(jīng)驗(yàn),為成都上千多家中小型企業(yè)策劃設(shè)計(jì)了網(wǎng)站。

大多數(shù)情況下,對(duì)象在新生代 Eden 上分配,當(dāng) Eden 空間不夠時(shí),發(fā)起 Minor GC。

2. 大對(duì)象直接進(jìn)入老年代

大對(duì)象是指需要連續(xù)內(nèi)存空間的對(duì)象,最典型的大對(duì)象是那種很長(zhǎng)的字符串以及數(shù)組。

經(jīng)常出現(xiàn)大對(duì)象會(huì)提前觸發(fā)垃圾收集以獲取足夠的連續(xù)空間分配給大對(duì)象。

-XX:PretenureSizeThreshold,大于此值的對(duì)象直接在老年代分配,避免在 Eden 和 Survivor 之間的大量?jī)?nèi)存復(fù)制。

3. 長(zhǎng)期存活的對(duì)象進(jìn)入老年代

為對(duì)象定義年齡計(jì)數(shù)器,對(duì)象在 Eden 出生并經(jīng)過 Minor GC 依然存活,將移動(dòng)到 Survivor 中,年齡就增加 1 歲,增加到一定年齡則移動(dòng)到老年代中。

-XX:MaxTenuringThreshold 用來定義年齡的閾值,默認(rèn)值為15。

4. 動(dòng)態(tài)對(duì)象年齡判定

虛擬機(jī)并不是永遠(yuǎn)要求對(duì)象的年齡必須達(dá)到 MaxTenuringThreshold 才能晉升老年代,如果在 Survivor 中相同年齡所有對(duì)象大小的總和大于 Survivor 空間的一半,則年齡大于或等于該年齡的對(duì)象可以直接進(jìn)入老年代,無需等到 MaxTenuringThreshold 中要求的年齡。

5. 空間分配擔(dān)保

在發(fā)生 Minor GC 之前,虛擬機(jī)先檢查老年代大可用的連續(xù)空間是否大于新生代所有對(duì)象總空間,如果條件成立的話,那么 Minor GC 可以確認(rèn)是安全的。

如果不成立的話虛擬機(jī)會(huì)查看 HandlePromotionFailure 的值是否允許擔(dān)保失敗,如果允許那么就會(huì)繼續(xù)檢查老年代大可用的連續(xù)空間是否大于歷次晉升到老年代對(duì)象的平均大小,如果大于,將嘗試著進(jìn)行一次 Minor GC;如果小于,或者 HandlePromotionFailure 的值不允許冒險(xiǎn),那么就要進(jìn)行一次 Full GC。

三、Full GC 的觸發(fā)條件

對(duì)于 Minor GC,其觸發(fā)條件非常簡(jiǎn)單,當(dāng) Eden 空間滿時(shí),就將觸發(fā)一次 Minor GC。而 Full GC 則相對(duì)復(fù)雜,有以下條件:

1. 調(diào)用 System.gc()

只是建議虛擬機(jī)執(zhí)行 Full GC,但是虛擬機(jī)不一定真正去執(zhí)行。不建議使用這種方式,而是讓虛擬機(jī)管理內(nèi)存。

2. 老年代空間不足

老年代空間不足的常見場(chǎng)景為前文所講的大對(duì)象直接進(jìn)入老年代、長(zhǎng)期存活的對(duì)象進(jìn)入老年代等。

為了避免以上原因引起的 Full GC,應(yīng)當(dāng)盡量不要?jiǎng)?chuàng)建過大的對(duì)象以及數(shù)組。除此之外,可以通過 -Xmn 虛擬機(jī)參數(shù)調(diào)大新生代的大小,讓對(duì)象盡量在新生代被回收掉,不進(jìn)入老年代。還可以通過 -XX:MaxTenuringThreshold 調(diào)大對(duì)象進(jìn)入老年代的年齡,讓對(duì)象在新生代多存活一段時(shí)間。

3. 空間分配擔(dān)保失敗

使用復(fù)制算法的 Minor GC 需要老年代的內(nèi)存空間作擔(dān)保,如果擔(dān)保失敗會(huì)執(zhí)行一次 Full GC。具體內(nèi)容請(qǐng)參考上面的第 5 小節(jié)。

4. JDK 1.7 及以前的永久代空間不足

在 JDK 1.7 及以前,HotSpot 虛擬機(jī)中的方法區(qū)是用永久代實(shí)現(xiàn)的,永久代中存放的為一些 Class 的信息、常量、靜態(tài)變量等數(shù)據(jù)。

當(dāng)系統(tǒng)中要加載的類、反射的類和調(diào)用的方法較多時(shí),永久代可能會(huì)被占滿,在未配置為采用 CMS GC 的情況下也會(huì)執(zhí)行 Full GC。如果經(jīng)過 Full GC 仍然回收不了,那么虛擬機(jī)會(huì)拋出 java.lang.OutOfMemoryError。

為避免以上原因引起的 Full GC,可采用的方法為增大永久代空間或轉(zhuǎn)為使用 CMS GC。

5. Concurrent Mode Failure

執(zhí)行 CMS GC 的過程中同時(shí)有對(duì)象要放入老年代,而此時(shí)老年代空間不足(可能是 GC 過程中浮動(dòng)垃圾過多導(dǎo)致暫時(shí)性的空間不足),便會(huì)報(bào) Concurrent Mode Failure 錯(cuò)誤,并觸發(fā) Full GC。

四、常見的調(diào)優(yōu)參數(shù)

詳解Java 虛擬機(jī)(第⑥篇)——內(nèi)存分配與回收策略

分享文章:詳解Java虛擬機(jī)(第⑥篇)——內(nèi)存分配與回收策略-創(chuàng)新互聯(lián)
本文來源:http://www.bm7419.com/article46/dpcgeg.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供外貿(mào)建站、商城網(wǎng)站、做網(wǎng)站、網(wǎng)站改版App設(shè)計(jì)、網(wǎng)站排名

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來源: 創(chuàng)新互聯(lián)

h5響應(yīng)式網(wǎng)站建設(shè)