簡體   English   中英

對引用類型變量進行裝箱和拆箱的技術性能如何?

[英]Performance of boxing and unboxing like technique for reference type variable?

裝箱和拆箱僅針對值類型定義。 資料來源

裝箱是將值類型轉換為類型對象或該值類型實現的任何接口類型的過程。 當CLR裝箱值類型時,它將值包裝在System.Object中,並將其存儲在托管堆中。 取消裝箱從對象中提取值類型。 裝箱是隱式的。 拆箱是明確的。 裝箱和拆箱的概念是類型系統的C#統一視圖的基礎,在該視圖中,任何類型的值都可以視為對象。

裝箱和拆箱的性能是一個昂貴的過程, 來源

裝箱和拆箱是計算上昂貴的過程。 裝箱值類型時,必須創建一個全新的對象。 這可能比簡單的參考分配花費多達20倍的時間。 拆箱時,鑄造過程可能需要花費四倍的時間。

現在,如果我使用stringstring[] ,它們是引用類型 ,我將執行以下操作:

string A;
return (string)(object)A;
// IMP: Here first casting is similar to boxing (though for a reference type), and second casting is similar to unboxing.

同樣的,

string[] A;
return (string[])(object)A;
// IMP: Here first casting is similar to boxing (though for a reference type), and second casting is similar to unboxing.

不同於在計算上很昂貴的值類型,我們使用引用類型。 對引用類型使用類似裝箱/拆箱的技術是否會對性能產生類似的影響?

它看起來類似於以下內容,但沒有討論性能影響(如果有):

您可能想知道C#編譯器完全刪除object強制轉換1 最終的結果是(假設該方法從一個常量為A分配一個值,然后得到您顯示的代碼):

.method private hidebysig static string Thing() cil managed
{
    .maxstack 8
    L_0000: ldstr "fred"
    L_0005: castclass string
    L_000a: ret 
}

您可能會在此處對引用類型進行運行時檢查,但是如果JIT無法靜態證明由於ldstr而導致堆棧上的引用已經是string ,因此我可以不感到驚訝,因此可以刪除任何代碼它可能已經考慮為castclass操作生成。

參考強制轉換是斷言 (我知道我要處理的類型比編譯器要好)。 它們不像裝箱和拆箱。


1通常,將在參考類型之間進行任何上行轉換

由於字符串已經是引用類型,因此不會對性能產生重大影響。

暫無
暫無

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

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