JVM 第三章垃圾回收部分摘抄

我們要怎麼理解這裏說的引用呢?
  1. 強引用:new Object() ,只要強引用還在,就不能GC
  2. 軟引用:系統將要內存溢出異常,這之前將對象列入回收範圍,二次回收。
  3. 弱引用:只能生存到下次GC之前,無論內存是否充足。
  4. 虛引用:相同虛設、對象與之關聯的目的是:在本對象被GC時收到一個系統通知。
Be or Die ???可達性分析中:“一定非死不可麼?,有沒有可能逃脫死亡?”
  1. 可達性分析出不可達之後,只是死緩,並不是一定不可逃脫。
  2. 兩次標記:1,發現沒有與引用鏈相連,第一次被標記,並進行刪選(對象是否有必要執行finalize()方法,對象沒有覆蓋finalize()方法OR已經被JVM調用過,均視爲沒有必要執行)  2.有必要時,進入F-Queue隊列,稍後被低優先級Finalize線程執行(觸發finalize()方法)它。但是並不會承若等待其運行結束,否則一旦某個對象在finalize()中緩慢或死循環,將導致F-Queue其他對象永久等待,會導致GC內存回收系統崩潰。
  3. “逃脫死亡”:在finalize()中拯救自己【不推薦用,畢竟throws等那麼多方法】,重新與引用鏈建立連接,在第二次標記時候會被移除“即將回收”集合,否則就被回收了。不夠注意,任一個對象的finalize()方法.只能被調用一次。對象下次面臨回收,無法在從相同的finalize()方法中逃脫。
方法區GC(eg:在HotSpot虛擬機的永久代)的垃圾回收性價比不高、效率相比堆中新生代(70-95%),但是主要有:
     廢棄常量、無用的類
     對象
是不使用的時候就可以被回收。
    “廢棄常量”判斷常量是否廢棄: “abc”字符串存在常量池中,但是系統沒有對該字符串的引用,(沒有任何String對象引用“abc”,也沒有其他地方引用這個字面量,如果此時發生內存回收,那麼這“abc”會被系統請出常量池。) 常量池中其他類(接口)、方法、字段的符號引用與此類似。
     “無用的類”判斷稍微苛刻《判斷條件》
           1.類的所有勢力都已被回收,Java堆中不存在該類的任何實例。
          2.類對應的java.lang.Class 對象沒有被引用,拒絕一切可能的反射訪問到該類的方法。
          3.該類的 ClassLoader已經被回收。
垃圾回收算法:
  1. Mark-Sweeping 最基礎-效率不高、空間不連續會有大量內存碎片,無法找到足夠的連續內存不得不觸發一次GC
  2. Coping -安容量均分爲兩塊A,B,只用一塊A,用完了A將還存活的複製到另一塊B,清除A.但可用內存會變小。由於很多“朝生夕死”所以設置Eden:Survivor=8:1:1,新生代可用容量會提高到90%。但如果Survivor內存不足以承載那邊copying過來的話,就要藉助老年代進行擔保分配。
  3. Mark-Compact:標記-整理:類似MarkSweeping,但後續不是標記就直接清除,而是讓所有存活對象都向一端移動,直接清除邊界外內存。避免了大量的資源碎片。
  4. Generational Collection:分代收集:根據存活週期不同分成老年代、新生代,新生代多用Copying;老年代多用1.3標記-**方法。
   垃圾回收器:7種,分別在新生代、老年代。有連線,即可以搭配使用(多是新生代+老年代各一款)。重點分析CMS、GI兩款相對複雜的收集器。
     新生代:copying算法的天下
  1. Serial : 單線程-JVM在client模式下默認的新生代收集方式,相比其他的單線程簡單高效,因爲專心所以高效。在GC時,必須暫停其他所有工作線程,直到其GC結束。用戶未知情況下線程就被停了,尷尬!用戶線程停頓時間可能久哦,一般控制在幾十ms-100ms不頻繁的話還是可以被client JVM接受的。【媽媽打掃房間時,我只能出去等着】
  2. ParNew :Serial的多線程版本【媽媽打掃房間,我可以邊扔紙屑】,除了多線程,甚至Serial的所有控制參數、回收算法、策略等是一樣。只有Serial和ParNew能和CMS搭檔呢。單線程工作環境下不會優於1.serial(專業),因爲線程交互等開銷。默認的開始的收集多線程數,於CPU數量一樣。
  3. Parallel Scavenge : 特點:目標是達到可控的吞吐量(=運行用戶代碼時間A/(A+垃圾回收時間))。其他eg CMS:減少停頓時間;而這個吞吐率則可以高效利用CPU時間。設置參數:GC停頓時間、直接設置吞吐量。
     老年代:
  1. Serial Old:Serial 的老年代版本。只不過是用Mark-Sweeping算法。給Client模式下的JVM使用。
  2. Parallel Old:Parallel Scavenge的老年版本,多線程+Mark-compact算法。一對一,新生代選那個,老年代必須選這個。
  3. CMS(Concurrent Mark Sweep): 併發收集+低停頓。目的:獲取最短停頓時間。常見於:網站  or B/S(Browser/Server)系統的服務端上。他們的特點是:重視系統停頓時間,以爲用戶提供最好的體驗。<4步驟> 
    初始標記(標記GCRoots能關聯到的對象,最短)---併發標記(GC Roots Tracing過程,時間最最長)---重新標記(修正併發標記過程program運行導致的一些變動,稍長)---併發清除(最最長)  最最長的2個階段,回收線程可與用戶線程同時工作->可認爲CMS回收內存過程與用戶線程併發進行的。
    對CPU很敏感(面向併發的特性決定了);CMS無法處理浮動垃圾(併發清理時運行的程序生成的新垃圾,當次GC無法清理,只能留給下次),可能“Concurrent Mode Failure”失敗導致另一次FullGC;基於M-S算法,回收會有大量碎片,找不到足夠連續內存又會觸發Full-GC。
  4. G1(Garbage-First)最前沿,面向服務端的---並行與併發+分代收集+空間整合+可預測的停頓。                                                                      初始標記---併發標記---最終標記---篩選回收

如何能看懂GC日誌&常見的垃圾收集器參數

  


發佈了47 篇原創文章 · 獲贊 16 · 訪問量 4萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章