1.對象已死?
1.引用計數算法
2.可達性分析算法
2.引用
1.強引用
2.軟引用
3.弱引用
4.虛引用
作用:在這個對象被回收時,收到一個系統通知
3.Finalize
一個對象死亡的過程
發現沒有和GC Roots相連接配接->被标記一個,并檢測,是否有必要執行Finalize方法->Yes的話被放入F-Queue中
->稍後GC對 F-Queue隊列進行标記->對象如果在finalize中拯救了自己,他将被移出即将回收隊列
這個方法不同于C++析構函數,不建議使用
4.垃圾收集算法
1.标記-清除算法
兩個不足:效率問題,标記與清除兩個功能效率都不高;空間問題,會産生大量碎片
2.複制算法
簡單,高效,代價是犧牲一半的記憶體
适合新生代
3.标記-整理算法
先進行标記,然後讓存活下來的向一邊移動,然後清理掉邊界外的記憶體
4.分代收集算法
根據對象存活周期不同,将記憶體劃分為幾塊,新生代使用2複制算法。老年代使用标記清除或标記整理算法
5.HotSpot算法實作-虛拟機如何發起記憶體回收
1.枚舉根節點
枚舉根節點時必須保證分析過程中對象的引用關系沒有變化。枚舉根節點時,虛拟機一定會停頓。
主流虛拟機使用精确式GC,HotSpot中使用OopMap的資料結構來定位對象引用。
2.安全點
Hotspot會在特定位置記錄了對象引用到OopMap,這個位置就是安全點。
安全點標明問題:
如何讓所有線程都跑到“安全點停下來那?
1.搶占式中斷
先把所有線程都中斷,然後讓沒有在安全點的,恢複線程,讓他跑到安全點(這種方法幾乎沒有人使用了)
2.主動式中斷”
不直接操作線程,僅設定一個标志,這個标志與安全點重合,執行到安全點就完成線程中斷
3.安全區域
安全區域:是引用關系不會發生變化的一段代碼片段,這個區域裡面任何地方GC都是安全的。
6.HotSpot算法實作-垃圾收集器
前面三個都是新生代收集器,使用的都是複制算法
1.Serial收集器
單線程收集器,運作在Client模式下面的預設新生代收集器。 特點:簡單且高效;對于單個CPU的情況下,沒有線程直接的互動,效率更高。
2.PerNew收集器
PeriNew 是Serial的多線程版本,一個并行的多線程收集器。是很多在Server下面首選的新生代收集器,與性能無關的原因是:目前隻有他能與CMS收集器配合工作。
3.Parallel Scavenge收集器
特點:
1,吞吐量優先收集器 2,于PeiNew差別是,這個收集器采用自适應調節政策 這個收集器的目的是達到一個可控制的吞吐量。吞吐量=運作使用者代碼時間/(運作使用者代碼時間+垃圾收集時間) 參數詳解: 1,-XX:MaxGCPauseMillis
設定記憶體回收不超過的時間,GC停頓時間縮短是以犧牲性能和新生代空間來保證的。
2,-XX:GCTimeRadtio
設定垃圾收集時間所占比重。(0<n<100)
3.-XX:UserAdaptiveSizePolicy
隻需設定好基本的記憶體資料,然後剩下的交給虛拟機自動完成
4,Serial Old收集器
标記整理算法 單線程收集器,和Serial一樣用于Client模式下老年代收集。 兩大用途: 在jdk1.5以及之前與Parallel Old收集器搭配使用 CMS收集器後備方案
5,Parallel Old收集器
标記整理算法
Parallel Scavenge老年化版本,
在注重吞吐量和CPU資源敏感的地方使用 Parallel Scavenge 和Parallel Old 組合
6,CMS收集器
并發低停頓收集器 标記-清除算法 CMS收集器的目的是擷取最短回收停頓時間。CMS适合 網際網路站和B/S系統伺服器端,這種要求響應時間的 步驟: 1.初始标記 需要stop the world,标記GC Root能關聯到的對象 2,并發标記 從GC Roots 對對象進行可到達性分析,找出存活的對象 3,重新标記 需要stop the world,修正并發期間變動的那部分對象的标記記錄 4,并發清除 花費時間最長的并發标記與并發清除是可以并行的, CMS的缺點: 1.對CPU資源比較敏感,CPU不足4個時,CMS對客戶程式影響較大 2.無法處理浮動垃圾,就是在并發清除過程中産生的垃圾,CMS無法再當次進行中收集他們 而且,由于CMS是并發的收集器是以不能等到老年代幾乎快滿了再收集,預設68%, -XX:CMSInitiatingOccupancyFraction 用來提高觸發百分比 如果運作期間,預留的記憶體空間無法滿足CMS收集垃圾,就會啟動備用方案,Serial Old收集器.是以-XX:CMSInitiatingOccupancyFraction設定太高反而性能降低 3.基于标記-清除,會有大量碎片産生 -XX:UseCMSCompactAtFullCollection 開關參數,模式是開啟,用于開啟記憶體碎片這個能力過程 -XX:CMSFUllGCsBeforeCompaction 多少次不執行壓縮的FullGC後,來一次帶壓縮的
7,G1收集器
面向伺服器端應用的垃圾收集器 特點: 1.并行與并發 2.分代收集 3.空間整合,使用标記整理算法,不會産生記憶體碎片 4.可預測的停頓,不僅追求地停頓,還建立了可預測時間的模型
步驟: 1.初始标記 需要stop the world,标記GC Root能關聯到的對象 2,并發标記 從GC Roots 對對象進行可到達性分析,找出存活的對象 3,最終标記 修正并發期間變動的那部分對象的标記記錄 4,篩選回收
JVM 參數
XX:+<option> 啟用選項 -XX:-<option> 不啟用選項 -XX:<option>=<number> -XX:<option>=<string>
附錄:參數 描述
-XX:+UseSerialGC | Jvm運作在Client模式下的預設值,打開此開關後,使用Serial + Serial Old的收集器組合進行記憶體回收 |
-XX:+UseParNewGC | 打開此開關後,使用ParNew + Serial Old的收集器進行垃圾回收 |
-XX:+UseConcMarkSweepGC | 使用ParNew + CMS + Serial Old的收集器組合進行記憶體回收,Serial Old作為CMS出現“Concurrent Mode Failure”失敗後的後備收集器使用。 |
-XX:+UseParallelGC | Jvm運作在Server模式下的預設值,打開此開關後,使用Parallel Scavenge + Serial Old的收集器組合進行回收 |
-XX:+UseParallelOldGC | 使用Parallel Scavenge + Parallel Old的收集器組合進行回收 |
-XX:SurvivorRatio | 新生代中Eden區域與Survivor區域的容量比值,預設為8,代表Eden:Subrvivor = 8:1 |
-XX:PretenureSizeThreshold | 直接晉升到老年代對象的大小,設定這個參數後,大于這個參數的對象将直接在老年代配置設定 |
-XX:MaxTenuringThreshold | 晉升到老年代的對象年齡,每次Minor GC之後,年齡就加1,當超過這個參數的值時進入老年代 |
-XX:UseAdaptiveSizePolicy | 動态調整java堆中各個區域的大小以及進入老年代的年齡 |
-XX:+HandlePromotionFailure | 是否允許新生代收集擔保,進行一次minor gc後, 另一塊Survivor空間不足時,将直接會在老年代中保留 |
-XX:ParallelGCThreads | 設定并行GC進行記憶體回收的線程數 |
-XX:GCTimeRatio | GC時間占總時間的比列,預設值為99,即允許1%的GC時間,僅在使用Parallel Scavenge 收集器時有效 |
-XX:MaxGCPauseMillis | 設定GC的最大停頓時間,在Parallel Scavenge 收集器下有效 |
-XX:CMSInitiatingOccupancyFraction | 設定CMS收集器在老年代空間被使用多少後出發垃圾收集,預設值為68%,僅在CMS收集器時有效,-XX:CMSInitiatingOccupancyFraction=70 |
-XX:+UseCMSCompactAtFullCollection | 由于CMS收集器會産生碎片,此參數設定在垃圾收集器後是否需要一次記憶體碎片整理過程,僅在CMS收集器時有效 |
-XX:+CMSFullGCBeforeCompaction | 設定CMS收集器在進行若幹次垃圾收集後再進行一次記憶體碎片整理過程,通常與UseCMSCompactAtFullCollection參數一起使用 |
-XX:+UseFastAccessorMethods | 原始類型優化 |
-XX:+DisableExplicitGC | 是否關閉手動System.gc |
-XX:+CMSParallelRemarkEnabled | 降低标記停頓 |
-XX:LargePageSizeInBytes | 記憶體頁的大小不可設定過大,會影響Perm的大小,-XX:LargePageSizeInBytes=128m |
Client、Server模式預設GC
新生代GC方式老年代和持久 代GC方式
Client | Serial 串行GC | Serial Old 串行GC |
Server | Parallel Scavenge 并行回收GC | Parallel Old 并行GC |
Sun/oracle JDK GC組合方式
新生代GC方式老年代和持久 代GC方式
-XX:+UseSerialGC | Serial 串行GC | Serial Old 串行GC |
-XX:+UseParallelGC | Parallel Scavenge 并行回收GC | Parallel Old 并行GC |
-XX:+UseConcMarkSweepGC | ParNew 并行GC | CMS 并發GC 當出現“Concurrent Mode Failure”時 采用Serial Old 串行GC |
-XX:+UseParNewGC | ParNew 并行GC | Serial Old 串行GC |
-XX:+UseParallelOldGC | Parallel Scavenge 并行回收GC | Parallel Old 并行GC |
-XX:+UseConcMarkSweepGC -XX:+UseParNewGC | Serial 串行GC | CMS 并發GC 當出現“Concurrent Mode Failure”時 采用Serial Old 串行GC |
參數部分參考自:http://blog.csdn.net/huxian1234/article/details/17163023