簡體   English   中英

采用實時堆轉儲執行System.gc()和死對象回收之間的區別?

[英]Difference between System.gc() and dead object reclamation performed by taking a live-only heap dump?

至少有兩種方式,直接或間接地建議JVM花費精力收集垃圾:

  • System.gc()
  • 進行堆轉儲並僅請求活動對象

在后者中,我可以通過編程方式獲取堆轉儲,例如通過

hotspotMBean = ManagementFactory.newPlatformMXBeanProxy(ManagementFactory.getPlatformMBeanServer(), "com.sun.management:type=HotSpotDiagnostic", HotSpotDiagnosticMXBean.class);
hotspotMBean.dumpHeap(filename, live);

這兩個操作在收集非強可達對象方面會有什么區別(如果有的話)?

我相信我有證據表明堆存儲方法比System.gc()更具攻擊性,存在弱引用的一些組合,RMI分布式垃圾收集和可從堆棧強烈訪問的不可見對象 特別是那些本地只能很弱地訪問並且相對於RMI變為Unreferenced對象似乎只是由堆轉儲收集的。 我還沒有將它提煉成一個小的測試用例,但它是可重現的。

(在我被警告不要依賴prod代碼中的特定GC行為之前,我不是。我在調查潛在的內存泄漏時發現了這一點,並注意到結果因我何時進行堆轉儲而有所不同。我只是好奇。)

這是在Windows 7上使用HotSpot 64位服務器VM 1.6.0_22。

System.gc()可能不那么激進,因為它只是表明它應該運行GC的JVM。 然后GC可以自由決定它應該收集(查找和釋放所有)死對象,其中一些,等等。它可以決定最近發生的偉大收集,並且現在不是再次收集所有對象的時間。

我相信轉儲堆並明確只詢問生命對象將導致GC精確計算每個對象是否仍然存活。 這部分收集工作正在完成,釋放死對象所使用的內存也不會花費太多。

唉,我沒有這種行為的有力證據,這是一個瘋狂的猜測,而不是一個真正的解釋。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM