我們都知道,c#的兩大資料型別分別為值型別和引用型別。很多人或許閉著眼睛都能說出值型別包括簡單型別、結構體型別和列舉型別,引用型別包括自定義類、陣列、介面、委託等,但是當被問及到二者之間的聯絡和區別,什麼時候用struct什麼時候用class時,就常常混淆不清了。為此,了解值型別和引用型別的本質差異就變的很有必要了。
1.值型別直接儲存其值,變數本身就包含了其實例資料,而引用型別儲存的只是例項資料的記憶體引用。因此,乙個值型別變數就永遠不會影響到其他的值型別變數,而兩個引用型別變數則很有可能指向同一位址,從而發生相互影響。
3.值型別均隱式派生自system.valuetype,而system.valuetype又直接派生於system.object,每種值型別均有乙個隱式的預設建構函式來初始化該型別的預設值,注意所有的值型別都是密封(sealed)的,所以無法派生出新的值型別。而且system.valuetype本身是乙個類型別,而不是值型別,因為它重寫了object的equals()方法,所以對值型別將按照例項的值來比較,而不是比較引用位址。
4.c# 的統一型別系統,使得值型別可以轉化為物件來處理,這就是常說的裝箱和拆箱。由於裝拆箱需要裝建全新物件或做強制型別轉換,這些操作所需時間和運算要遠遠大於賦值操作,因此不提倡使用它,同時也要盡量避免隱式裝拆箱的發生。
注:棧是作業系統分配的乙個連續的記憶體區域,用於快速訪問資料。因為值型別的容量是已知的,因此它可儲存在棧上。而託管堆是clr在應用程式啟動時為應用程式預留的一塊連續記憶體區,是用於動態記憶體分配的記憶體區,引用型別的容量只有到執行時才能確定,所有用堆來儲存引用型別。
c#的兩種資料型別延伸之一--巢狀型別的記憶體分配
對於引用型別巢狀值型別,以及值型別巢狀引用型別的情況下,記憶體分配可以根據以下兩條規律來判斷:
• 引用型別始終部署在託管堆上;
• 值型別總是分配在它宣告的地方:作為欄位時,跟隨其所屬的物件儲存;作為區域性變數時,儲存在棧上。
c#的兩種資料型別延伸之二--string型別
string是乙個很有意思的引用型別,為什麼說它很有意思呢?因為它表現了很多值型別的特點。請看一下**示例:
示例1stringstr1 = "abc";
stringstr2 = str1;
str1= "123";
console.writeline(str2);
示例2(msdn上的例子)
stringa = "hello";
stringb = "h";
b +="ello";
console.writeline(a== b);
示例1的輸出結果是abc,改變str1的值對str2沒有影響。
示例2的輸出結果是true。
這樣的結果會使我們誤以為string就是值型別。其實不然,示例1中str1= "123"語句編譯器私底下建立了乙個新的字串物件來儲存新的字串行"123",也就是此str1已非彼str1了,「此」str1的值的改變也就不能影響「彼」str1的值了,當然str2的值也就不會改變了。實質上str1= "123"是str1=newstring("123")的簡寫,它的每一次賦值都會拋掉原來的物件而生成乙個新的字串物件,分配新的記憶體空間,因此string是不可改變的。如果要建立可修改的字串,可使用stringbuilder以獲得更好的效能。至於示例2是因為為了方便比較字串的值重定義了string的運算子==和!=。
c#的兩種資料型別延伸之三--struct和class
class和struct的語法基本相同,從宣告到使用,都很相似。但是struct的約束要比class多,理論上,struct能做到的class都能做到,但class能做到的stuct卻不一定做的到,也就是說struct都能被class所代替。那麼為什麼還要使用struct呢?存在即是合理的,struct在很多方面有著效能優勢。讓我們看看它們的主要區別在**?
比較struct和class的不同,可以得出以下幾條struct和class的使用原則:
1 在表示諸如點、矩形等主要用來儲存資料的輕量級物件時,首選struct。
2 在表示資料量大、邏輯複雜的大物件時,首選class。
3 在表現抽象和多級別的物件層次時,class是最佳選擇
實際舉例C 引用型別和值型別的區別
我們都知道,c 的兩大資料型別分別為值型別和引用型別。很多人或許閉著眼睛都能說出值型別包括簡單型別 結構體型別和列舉型別,引用型別包括自定義類 陣列 介面 委託等,但是當被問及到二者之間的聯絡和區別,什麼時候用struct什麼時候用class時,就常常混淆不清了。為此,了解值型別和引用型別的本質差異...
C 值型別和引用型別
c 資料型別 值型別,引用型別 概念 值型別直接儲存其值,引用型別儲存對值的引用 這兩種型別儲存在記憶體的不同地方 值型別儲存在堆疊中,引用型別儲存在託管堆上。乙個引用型別的例子,如圖 上圖中,只有乙個user物件,u1和u2都指向包含該物件的記憶體位置 執行結果 在c 中,基本資料型別如bool和...
c 值型別和引用型別
今天我們來學習一下什麼是值型別和引用型別。1.值型別的值存在棧上,引用型別棧上存的是位址,值在堆上 2.將乙個值型別變數賦給另乙個值型別變數時,將複製包含的值。引用型別變數的賦值只複製對物件的引用,而不複製物件本身。3.裝箱是將值型別轉換為引用型別,拆箱是將引用型別轉換為值型別,利用裝箱和拆箱功能,...