![](/img/trans.png)
[英]Is a struct wrapping a primitive value type a zero cost abstraction in C#?
[英]Definitions of “primitive”, “value type”, “struct”, “class”, “wrap” in Java and C#
我一直試圖理解在Java和C#中使用“原語”以及它們之間的區別(如果有的話)。 我已經提出了一系列關於SO的問題,一些答案似乎混淆了問題而不是澄清它。 一些答案(和一些MS文檔)似乎提供了相互矛盾的陳述。 來自SO
並從MS: http : //msdn.microsoft.com/en-us/library/ms228360%28VS.80,lightweight%29.aspx - “結構與類非常相似” - “ Int32
類包裝int
數據類型“ - ”另一方面,C#中的所有原始數據類型都是System命名空間中的對象。對於每種數據類型,都提供了一個簡短的名稱或別名。例如, int
是System.Int32的簡稱“。
我的困惑很大程度上與C#(我已經編程java一段時間)有關。
編輯以下段落已被@Jon Skeet確認為正確
編輯 @Jon已經對C#做了非常明確的陳述,所以我將刪除我建議的真相並參考他的答案。
進一步的問題:對這些術語的實際用途應該有什么共識? 如果達成共識,我將非常感謝它明確闡述。 否則我認為術語混亂,因此使用有限。
總結感謝您非常明確的答案。 在那些真正了解這一點並且MS文檔是一致的人之間存在共識(參見@Jon接受的答案)(盡管他們在某些地方引用了Java而我誤解了這些用於C#)
我沒有看到MS文檔與此相矛盾(MSDN有時是錯誤的,但在這個具體問題上,我總是看到它是正確的)。 您發布的MSDN鏈接說:
對於Java中的每個原始數據類型 ,核心類庫提供了一個包裝類,將其表示為Java對象。 例如,Int32類包裝int數據類型,Double類包裝double數據類型。
另一方面 ,C#中的所有原始數據類型都是System命名空間中的對象。 對於每種數據類型,都提供了短名稱或別名。 例如,int是System.Int32的短名稱,double是System.Double的縮寫形式。
基本上,它說的是正確的。 在Java中, Integer
類是int
基本類型的包裝器。 在C#中, int
是System.Int32
結構的別名。 第一段是關於Java的, 不適用於C#。
在.NET中,術語如下:
基本類型是將IsPrimitive
屬性設置為true的類型。 原始類型是:
基元類型是布爾,字節,SByte,Int16,UInt16,Int32,UInt32,Int64,UInt64,IntPtr,UIntPtr,Char,Double和Single。
所有原始類型都是值類型,但反之亦然 。
值類型是具有值語義的類型,而不是引用語義 。 通過值(而不是其引用)傳遞時復制整個值。 值類型的局部變量存儲在堆棧中。 struct
s和enum
是值類型。
如上所述,所有原始類型都是值類型。 它們是System
命名空間中的struct
。 在C#, int
, double
等中,關鍵字基本上是這些struct
的別名。
第一個要點是正確的。
第二個不是:.NET中的原始類型是Boolean,Byte,SByte,Int16,UInt16,Int32,UInt32,Int64,UInt64,IntPtr,UIntPtr,Char,Double和Single。 結構通常不能設置為null
,但也有可為空的值類型( Nullable<T>
)。 這些仍然是值類型,但C#中的語法糖將“null”等同於“類型的空值”,對於可空值類型, HasValue
返回false的實例。
int
和System.Int32
是 C# 中的完全同義詞。 前者只是后者的別名。 他們編譯成完全相同的代碼。
在C#中,類和接口始終是引用類型。 結構和枚舉是值類型 - 但是每個結構都有一個盒裝的等價物( Nullable<T>
除外,CLR在裝箱方面有不同的處理方式)。 盒裝類型沒有單獨的名稱,並且不能在C#中顯式引用(盡管它們可以在C ++ / CLI中)。 沒有單獨的包裝類,如.NET中的java.lang.Integer
; 引入這樣的類是有問題的,因為您可以在.NET中創建自己的值類型,這與Java不同。
有關引用類型和值類型的更多信息,請參閱我的文章 。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.