主要討論默認的Serial/Serial Old內存分配:html
1. 對象優先在Eden分配;安全
通常狀況下,對象會在新生代的Eden區分配,Eden區沒有足夠空間時,虛擬機會 發起一次MinorGC;當MinorGC時,若沒法放入survivor空間,就會再經過分配擔保機制轉移到老年代中;post
2. 大對象直接進入老年代;url
經過 -XX:PretenureSizeThreshold參數設置;spa
3. 長期存活的對象進入老年代:htm
經過 -XX:MaxTenuringThreshold參數設置;每MinorGC一次還存活在Survivor中,則年齡加1;對象
4. 組團進入 老年代:blog
在survivor中年齡相同的全部對象大小總和大於 PretenureSizeThreshold 參數的一半,年齡大於或等於該年齡的對象進入老年代。生命週期
5. 空間擔保進入 老年代:內存
每次MinorGC以前,會檢查老年代最大連續可用空間是否大於 新生代全部對象的總空間,大於則表示安全可進行MinorGC;
若是小於:(JDK 6U24再也不檢查HandlePromotionFailure,必定會冒險)
a. 檢查HandlePromotionFailure 爲 true ,表示容許冒險,則與歷次晉升到老年代的對象平均大小比較,若大於則進行MinorGC,若小於則進行FullGC;
b. HandlePromotionFailure 爲 false,進行FullGC;
MinorGC:指發生在新生代的GC,因大多數新生對象生命週期很短,因此MinorGC一般很頻繁,回收速度也較快;
MajorGC/FullGC:指老年代GC,速度通常較慢,通常是MinorGC的10倍;一般MajorGC會伴隨一次MinorGC;(書原話,有歧義)
參考知乎R大答案:Major GC和Full GC的區別是什麼?觸發條件呢?
觸發條件:
MinorGC:Eden區滿時觸發;FullGC也會伴隨有MinorGC;一般會使得Old gen變大;
FullGC:a. MinorGC觸發前,檢查歷次進入老年代的平均大小,若小於則FullGC;
b. 若是有永久代(perm gen),在不足哆分配時,觸發FullGC;
c. 調用System.gc(),提醒JVM FullGC,但不可控;
新生代分爲:Eden Space、Survivor Space
老年代:Tenured Gen
永久代:Perm Gen(方法區相關數據);
在 JDK 1.8 中, HotSpot 已經沒有 「PermGen space」這個區間了,取而代之是一個叫作 Metaspace(元空間) 的東西。