歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
您现在的位置: Linux教程網 >> UnixLinux >  >> Linux編程 >> Linux編程

Java和.NET中的垃圾回收機制比較

Java和.NET中的垃圾回收機制相同點:

都采用了分代的機制。

都支持並發GC。

都沒有采用引用計數方式,而是采用了追蹤技術。

.NET中,可以通過代碼GC.Collect() 強制要求CLR進行垃圾回收(由於垃圾回收是異步的,CLR有一個專用的線程負責垃圾回收,因此,即使調用GC.Collect,也並不是實時的調用了Finalize,因此要保證確實調用了析構方法,可以使用語句GC.WaitForPendingFinalizers()來確保析構方法真的被運行了,參考http://www.linuxidc.com/Linux/2017-02/140121.htm)

Java中也可以通過System.gc() 強制要求進行垃圾回收。(事實上也僅僅是建議JVM執行垃圾回收,JVM並不一定立即做回收行為。)

不同點:

CLR預留了一塊大空間,稱作large object heap (LOH),目的是當有大對象(超過85000字節的)需要分配空間時,就可以放在這裡。

這塊地方和分代機制的不同之處在於,這個地方只有當發生full GC的時候,才會回收,而且這塊地方不會被壓縮。

Java中可以通過配置參數,使得大對象(大於設定的阈值)直接進入老年代(避免在年輕代上做大量的復制操作)。

JVM回收的內存的,僅僅在某些條件下才返回給操作系統。(詳見:http://stackoverflow.com/questions/366658/java-6-excessive-memory-usage#367933)

.NET回收的內存,直接給返還給操作系統。

JVM在的垃圾回收機制,提供了大量的可配置參數。

而CLR的垃圾回收機制幾乎沒什麼可以配置的(僅有的配置似乎就是工作站模式(Workstation)和服務器模式(Server))。

都支持並發GC。JAVA是在老年代上支持並發GC,采用的CMS收集器。

.NET的並發GC只在第2代上,並且在工作站模式下才會有。

Java分成年輕代,老年代,永久代。

.NET分第0代,第1代,第2代。

.NET中采用了標記,壓縮的方式。

JAVA由於收集器很多,因此不限於一種算法。

 

年輕代

老年代

方式

Serial收集器

復制算法

             

單線程,stop the world

SerialOld收集器                  

             

標記整理算法

單線程,stop the world                  

ParNew收集器

復制算法

標記整理算法

多線程,stop the world

Parallel Scavenge收集器

復制算法                
           
多線程,stop the world               

CMS收集器

             

標記清除

單線程

G1收集器

復制

標記整理

             

Java垃圾回收的幾篇文章
http://www.linuxidc.com/Linux/2017-02/140122.htm
http://www.linuxidc.com/Linux/2017-02/140123.htm

.NET垃圾回收的幾篇文章
https://msdn.microsoft.com/zh-cn/library/ee787088(v=vs.110).aspx
http://www.mincoder.com/article/4284.shtml

Copyright © Linux教程網 All Rights Reserved