.net很容易把值型別轉換為引用型別,所以可以在需要物件的任意地方使用值型別。例如int可以賦予乙個物件,從值型別轉換為引用型別稱為裝箱。如果方法需要把乙個物件作為引數,同時傳遞乙個值型別,裝箱操作就會自動進行。另一方面,裝箱的值型別可以使用拆箱操作轉換為值型別。
定義乙個一般的、非泛型的簡化鍊錶類,它可以包含任意型別的物件,在鍊錶中,乙個元素引用下乙個元素。所以必須建立乙個類,它將物件封裝在鍊錶中,並引用下乙個物件。類linkedlistnode包含乙個屬性value,該屬性用建構函式初始化。另外linkedlistnode類包含對鍊錶中下乙個元素和上乙個元素的引用,這些元素都可以從屬性中訪問。
先定義linkedlistnode類
public再定義乙個非泛型的簡化鍊錶類,實現非泛型介面class
linkedlistnode
public
object value
public linkedlistnode next
public linkedlistnode prev
}
public用ilspy檢視il**class
linkedlist : ienumerable
public linkedlistnode last
public linkedlistnode addlast(object
node)
else
return
newnode;
}public
ienumerator getenumerator()}}
il_0000: nop分析il**可知上述過程發生了兩次裝箱和兩次拆箱,在foreach語句中,鍊錶中的元素被強制轉換為整形,裝箱和拆箱操作很容易使用,但效能損失比較大,泛型能很好的避免拆裝箱,從而提供效能。il_0001: newobj instance
void
praticecharter01.linkedlist::.ctor()
il_0006: stloc.
0il_0007: ldloc.
0il_0008: ldc.i4.
3il_0009: box [mscorlib]system.int32
il_000e: callvirt instance
class praticecharter01.linkedlistnode praticecharter01.linkedlist::addlast(object
) il_0013: pop
il_0014: ldloc.
0il_0015: ldc.i4.
4il_0016: box [mscorlib]system.int32
il_001b: callvirt instance
class praticecharter01.linkedlistnode praticecharter01.linkedlist::addlast(object
) il_0020: pop
il_0021: nop
il_0022: ldloc.
0il_0023: callvirt instance
class
[mscorlib]system.collections.ienumerator praticecharter01.linkedlist::getenumerator()
il_0028: stloc.1.
try
//end .try
再定義乙個泛型版本,該泛型集合實現泛型介面ienumerator
publicclass linkedlistnode
public t value
public linkedlistnodenext
public linkedlistnodeprev
}public
class linkedlist: ienumerable
public linkedlistnodelast
public linkedlistnodeaddlast(t node)
else
return
newnode;
}public ienumeratorgetenumerator()
}ienumerator ienumerable.getenumerator()
}
static檢視il**void main(string
args)
il_0000: nopil codeil_0001: newobj instance
void
class praticecharter01.linkedlist`1
::.ctor()
il_0006: stloc.
0il_0007: ldloc.
0il_0008: ldc.i4.
3il_0009: callvirt instance
class praticecharter01.linkedlistnode`1
0> class praticecharter01.linkedlist`1
::addlast(!0
) il_000e: pop
il_000f: ldloc.
0il_0010: ldc.i4.
4il_0011: callvirt instance
class praticecharter01.linkedlistnode`1
0> class praticecharter01.linkedlist`1
::addlast(!0
) il_0016: pop
il_0017: nop
il_0018: ldloc.
0il_0019: callvirt instance
class [mscorlib]system.collections.generic.ienumerator`1
0> class praticecharter01.linkedlist`1
::getenumerator()
il_001e: stloc.1.
try
//end .try
發現並沒拆裝箱過程,說明泛型能提供型別安全的類並能提**用程式的效能,基於以上幾點在訪問資料層經常使用泛型以期提高**的重用性,在資料訪問泛型類通常需要呼叫泛型型別中的方法,所以必須給泛型類新增約束,泛型支援幾種約束如下:
(1)where t:struct 對於結構約束,型別t必須是值型別
(2)where t:class 類約束指定型別t必須是引用型別
(3)where t:ifoo指定型別t必須實現介面ifoo
(4)where t:new()這是乙個建構函式約束,指定型別t必須有乙個預設建構函式
(5)where t1:t2這個約束也可以指定,型別t1派生自泛型型別t2、該約束稱為裸約束
定義乙個實現icomparable泛型介面的實體
public定義泛型類,該泛型有兩個約束class employemodel:icomparable
public
string lastname
public
int age
public
intcompareto(employemodel other)
}
publicclass basedalwhere t : class,icomparable
class總結泛型類可以建立獨立於型別的類,泛型方法是獨立於型別的方法,介面結構和委託也可以用泛型的方式建立。program
}public
struct
nullablestruct
public
class
student
public
string lastname
public
int age
}
C 裝箱 拆箱 泛型
1 裝箱 值型別轉引用型別。開闢一塊記憶體空間進行存放資料。2 拆箱 引用型別轉值型別。值型別存放在棧上,引用型別存放在堆上。裝箱需要消耗記憶體,所以引出了泛型。泛型 1.使用非泛型集合時引發的裝箱和拆箱操作 看下面的一段 1 2 3 4 5 6 7 8 vararray newarraylist ...
java學習 裝箱與拆箱 泛型
把基本資料型別賦給對應的包裝類。比如 把int賦值給integer,對他的操作就需要用它的方法了。是值型別轉換為引用型別的過程。把乙個包裝類賦給基本資料型別。由引用型別轉換為值型別的過程。integer i 1 裝箱 int j i 拆箱 典型應用 list list new arraylist l...
C 委託 泛型 事件 裝箱拆箱
一 委託 我感覺的委託就是指乙個函式指標,指向被委託的方法,在定義的時候把返回值型別與引數全部定義好,建立的例項相當於乙個指向被委託函式的指標,然後將需要的資料通過委託傳進去 是先呼叫委託例項,然後委託例項再呼叫方法 簡寫的那種方式更能體現它像乙個函式指標 注意 多播委託就是用 與 進行操作 當多播...