.Net Discovery系列之十-深刻理解平臺機制與性能影響(上)

轉眼間《.Net Discovery》系列文章已經推出1年了,本文爲該系列的第10-13篇文章,在本文中將對之前所講的.Net平臺知識作一個小小的總結與機制分析,引出並重點介紹這些機制對程序性能的影響與改進建議。
    本文將分爲四部分,分別講述了:垃圾回收機制、即時編譯機制、異常處理機制、字符串駐駐留機制的原理與性能改進建議。《.Net Discovery》系列的每篇文章撰寫耗時都在2天以上,轉載時麻煩著名做者Aicken(李鳴),而且未經做者贊成,禁止一切商業用途!
    一.關於垃圾回收機制
    ● 機制分析
    垃圾收集器是.Net平臺的一個特性,它自動回收託管堆上再也不使用的對象,及時清理內存,這一切都是對開發人員透明的,固然你也能夠手動把它召喚出來,它的本質就是跟蹤全部被引用到的對象,整理對象再也不被引用的對象,回收相應的內存。垃圾收集機制採用「標記與清除(Mark Sweep)」算法來完成上述任務,整個過程分爲兩步:
    Step 1.Mark-Sweep :從應用程序的root出發,利用相互引用關係,遍歷其在Heap上動態分配的全部對象,指明須要回收的對象,標記出那些存活的對象,予以標記。
    Step 2.Compact: 對內存中存活的對象進行移動,修改它們的指針,使之在內存中連續,這樣空閒的內存也就連續了,即完成了內存釋放工做,也解決了內存碎片問題,這個過程也能夠成爲指針的壓縮。
    垃圾收集器通常將託管堆中的對象分爲3代,這能夠經過調用GC.MaxGeneration得知,對象按照存在時間長短進行分代,最短的分在第0代,最長的分在第2代,第2代中的對象每每是比較大的,第二代空間被稱做Large Object Heap,對於2代對象的回收,與第0、1代回收方式相比最大的不一樣在於,沒有了指針移動的壓縮過程。
    以下圖,第一次GC時,左邊第一列A-F表示內存中的對象,位於淺藍色 區域,通過Mark後,ACDF標記爲可用,Sweep過程清除了BE,Compact過程移動了ACDF,使之位於連續存儲區域中;第二次使用綠色作標記;第三次GC使用藍色表示標記;能夠看出第三次GC過程沒有了指針移動的壓縮過程。html

圖1 對象的回收

    ●性能影響分析
    這個過程看起來有點複雜,的確垃圾收集器的啓動是會佔用一些CPU時間,從而影響系統的性能,但這種影響頗有限,而且這些損失是有所值的。
    1.垃圾收集器並非沒有規律的啓動,而是當代齡達到必定觸發條件時啓動,並且垃圾收集器只是移動代齡較低的一、2代的資源,並不會移動LOH中的對象。這就在必定程度上避免了GC長時間鎖定線程致使的性能損失。
    2.GC有三種不一樣的工做模式,適用於不一樣環境的狀況,並非全部環境都是「使用掛起->查找與標記->壓縮->恢復」 的流程。「Workstation GC with Concurrent」模式能夠第0、1代的收集仍然是要暫時掛起應用程序,在收集第2代時,會並行處理,具體原理是將Full GC過程切分紅多個短暫子過程對線程進行凍結,在線程凍結時間以外,應用程序仍然能夠正常運行。這主要經過將0代空間設置的很大,使Full GC時,CLR仍然可以在0代中進行內存分配,若是Full GC時0代內存也已用盡,那麼應用程序將被掛起,等待Full GC的完成。
    在多CPU的狀況下,可使用和「Server GC」模式。這種GC模式有着很高的性能和效率。這種模式下,CLR爲每一個CPU建立一個專用的GC線程,每一個CPU能夠獨立的爲相應的heap執行GC操做,這些GC線程是以非併發的形式工做的,收集工做與線程正常工做不能同時進行,這就是說第0、一、2代的收集都會掛起應用線程。
    在.Net 4.0中,有一種新的垃圾收集機制,叫作後臺收集。這種機制以concurrent GC爲基礎的,如上文所講,Workstation GC with Concurrent模式中,在Full GC過程時,CLR仍然可以在0代中進行內存分配,若是Full GC時0代內存也已用盡,那麼應用程序將被掛起,等待Full GC的完成。
    3.垃圾收集器是配合策略引擎工做的。策略引擎能夠喚醒GC,它會根據GC啓動的次數、頻率、代齡狀況等自發的啓動GC,使GC工做。特別要注意的是,由程序人員手動的調用GC收集的代碼,一樣會影響策略引擎的工做,這樣會給策略引擎錯誤的信號,從而致使GC的錯誤啓動,因此在沒有必要的狀況下,通常不建議使用GC.Collect();手動回收。
    ● 綜述
    比起垃圾收集器帶來的微乎的性能損失,咱們應該把精力放在程序的優化上,非託管資源的及時釋放、字符串拼接、循環內的業務代碼都是須要注意的地方。垃圾收集機制不是.Net也不是Java的專利,它已經有一段進化的歷史,愈來愈多的案例也證實垃圾收集機制的優勢,Exchange 2010的大部分模塊就是基於託管環境的。
    二.關於實時編譯機制
    JIT(Just In Time簡稱JIT)是.Net邊運行邊編譯的一種機制,這種機制的命名來源於豐田汽車在20世紀60年代實行的一種生產方式,中文譯爲「準時制」。
    .Net 的JIT編譯器在設計初衷和運行方式來上講,都與豐田汽車的這種「準時生產」思想體系有着很大的類似之處,因此讓咱們先來透過「準時生產」方式來理解.Net的JIT機制吧。
    「準時生產」的基本思想可歸納爲「在須要的時候,按須要的量生產所需的產品」,這正是.Net JIT編譯器的設計初衷,即在須要的時候編譯須要的代碼。

未完算法

 

轉自:http://www.cnblogs.com/isline/archive/2010/04/06/1705131.html併發

相關文章
相關標籤/搜索