大對象堆及.NET垃圾回收器的改進
當 .NET 開發者編寫內存密集型(memory intensive)應用程序的時候,即便總體內存看起來非常充足,也經常會在大對象堆的分配上遇到問題,產生 out-of-memory 異常。微軟 承諾會在 .NET Framework 4.5 中對此做出改進,其中會有更好的 LOH 管理,產生的內存碎片會更少。
CLR 會管理兩種獨立的堆并對其進行分配,小對象堆(small object heap,SOH)和大對象堆(large object heap,LOH)。所有大于85,000 byte 的內存分配都會在 LOH 上進行。你可以閱讀這些文章,以進一步了解這兩種堆之間的區別。 為了在 LOH 中換取性能,需要消耗大量內存的應用程序——像繁重的圖像處理程序——會面臨內存碎片的問題,并且可能在使用到最大限制的內存之前就發生 OutOfMemory 異常。
.NET 在從 3.5 向4.0升級的時候,已經在總體內存分配方面做出了一些改進。負責 .NET Framework 的垃圾回收器的資深項目經理 Brandon Bay 對上述問題做出評論,他說:
基于所提供的示例,執行了從3.5到4.0的升級之后,在耗盡大對象堆上的內存之前,我們可分配的內存增加了22倍。
而現在 .NET 4.5 看起來是在此基礎之上構建的:
在 .NET 4.5 中,我們對大對象堆做出了兩項改進。首先,我們顯著改進了運行時管理空閑列表的方式,從而能夠更有效地利用碎片。現在,內存分配器可以重新訪問到之前版本中的分配器無法使用的內存碎片。其次,當處于服務器垃圾回收(server GC)模式時,運行時會在每個堆之間平衡 LOH 的分配。而在 .NET 4.5 之前,我們只能針對 SOH 做出平衡。在 LOH 分配評測中,我們發現這兩種改變讓結果有了實質上的改善。
你可以閱讀 Brandon 的完整文章以獲得更多細節。想要了解更多關于 .NET Framework 垃圾回收器的工作原理,你可以參考 MSDN 文檔以及 Andrew Hunter 的這篇文章。
查看英文原文:Large Object Heap And .NET GC Improvements