Java的GC機(jī)制

判斷哪些對(duì)象需要被GC

  • 方法區(qū)

可達(dá)性分析方法(Java使用):通過(guò)判斷對(duì)象是否被GC Root 直接或間接引用,進(jìn)而判斷對(duì)象是否可用,如果對(duì)象不可以就可以對(duì)這個(gè)對(duì)象進(jìn)行GC

引用計(jì)數(shù)方法(python使用):每個(gè)對(duì)象有一個(gè)引用計(jì)數(shù)屬性,新增一個(gè)引用時(shí)計(jì)數(shù)加1,引用釋放時(shí)計(jì)數(shù)減1,計(jì)數(shù)為0時(shí)可以回收。此方法簡(jiǎn)單,但無(wú)法解決對(duì)象相互循環(huán)引用的問(wèn)題。

如何觸發(fā)GC

  • 程序調(diào)用System.gc()
  • 根據(jù)Eden區(qū)和FromSpace區(qū)的內(nèi)存大小來(lái)決定,如果內(nèi)存不足,則會(huì)啟動(dòng)GC(此時(shí)應(yīng)用線程停止)

GC又分為 minor GC 和 Full GC (也稱為 Major GC )

Minor GC觸發(fā)條件:當(dāng)Eden區(qū)滿時(shí),觸發(fā)Minor GC。

Full GC觸發(fā)條件:

a.調(diào)用System.gc時(shí),系統(tǒng)建議執(zhí)行Full GC,但是不必然執(zhí)行

b.老年代空間不足

c.方法去空間不足

d.通過(guò)Minor GC后進(jìn)入老年代的平均大小大于老年代的可用內(nèi)存

e.由Eden區(qū)、From Space區(qū)向To Space區(qū)復(fù)制時(shí),對(duì)象大小大于To Space可用內(nèi)存,則把該對(duì)象轉(zhuǎn)存到老年代,且老年代的可用內(nèi)存小于該對(duì)象大小

GC算法

GC常用算法有:標(biāo)記-清除算法,標(biāo)記-壓縮算法,復(fù)制算法,分代收集算法。

新生代、老年代的轉(zhuǎn)化過(guò)程

具體過(guò)程:新生代(Young)分為Eden區(qū),F(xiàn)rom區(qū)與To區(qū)

image

當(dāng)系統(tǒng)創(chuàng)建一個(gè)對(duì)象的時(shí)候,總是在Eden區(qū)操作,當(dāng)這個(gè)區(qū)滿了,那么就會(huì)觸發(fā)一次YoungGC,也就是年輕代的垃圾回收。一般來(lái)說(shuō)這時(shí)候不是所有的對(duì)象都沒(méi)用了,所以就會(huì)把還能用的對(duì)象復(fù)制到From區(qū)。

image

這樣整個(gè)Eden區(qū)就被清理干凈了,可以繼續(xù)創(chuàng)建新的對(duì)象,當(dāng)Eden區(qū)再次被用完,就再觸發(fā)一次YoungGC,然后呢,注意,這個(gè)時(shí)候跟剛才稍稍有點(diǎn)區(qū)別。這次觸發(fā)YoungGC后,會(huì)將Eden區(qū)與From區(qū)還在被使用的對(duì)象復(fù)制到To區(qū),

image

再下一次YoungGC的時(shí)候,則是將Eden區(qū)與To區(qū)中的還在被使用的對(duì)象復(fù)制到From區(qū)。

image

經(jīng)過(guò)若干次YoungGC后,有些對(duì)象在From與To之間來(lái)回游蕩,這時(shí)候From區(qū)與To區(qū)亮出了底線(閾值),這些家伙要是到現(xiàn)在還沒(méi)掛掉,對(duì)不起,一起滾到(復(fù)制)老年代吧。

image

老年代經(jīng)過(guò)這么幾次折騰,也就扛不住了(空間被用完),好,那就來(lái)次集體大掃除(Full GC),也就是全量回收。如果Full GC使用太頻繁的話,無(wú)疑會(huì)對(duì)系統(tǒng)性能產(chǎn)生很大的影響。所以要合理設(shè)置年輕代與老年代的大小,盡量減少Full GC的操作。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡(jiǎn)書(shū)系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 一 、java虛擬機(jī)底層結(jié)構(gòu)詳解 我們知道,一個(gè)JVM實(shí)例的行為不光是它自己的事,還涉及到它的子系統(tǒng)、存儲(chǔ)區(qū)域、...
    葡萄喃喃囈語(yǔ)閱讀 1,582評(píng)論 0 4
  • JVM架構(gòu) 當(dāng)一個(gè)程序啟動(dòng)之前,它的class會(huì)被類(lèi)裝載器裝入方法區(qū)(Permanent區(qū)),執(zhí)行引擎讀取方法區(qū)的...
    cocohaifang閱讀 1,845評(píng)論 0 7
  • 一、垃圾收集的意義 ?相對(duì)于C++來(lái)說(shuō),Java預(yù)言顯著的特點(diǎn)就是引入了垃圾回收機(jī)制,它使得Java程序員在編寫(xiě)程...
    SunnyMore閱讀 2,224評(píng)論 0 50
  • http://www.cnblogs.com/angeldevil/p/3801189.html值得一看 Clas...
    snail_knight閱讀 1,611評(píng)論 1 0
  • java基礎(chǔ)volidate、線程生命周期、反射、NIO 內(nèi)存分區(qū)GC、類(lèi)加載 強(qiáng)弱等引用 基本數(shù)據(jù)結(jié)構(gòu) 線程池 ...
    RichardLee123閱讀 336評(píng)論 0 3

友情鏈接更多精彩內(nèi)容