日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程语言 > C# >内容正文

C#

【转】C#泛型约束

發(fā)布時間:2025/4/5 C# 37 豆豆
生活随笔 收集整理的這篇文章主要介紹了 【转】C#泛型约束 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

轉(zhuǎn)自:http://www.cnblogs.com/kk888/archive/2011/09/01/2161647.html

所謂泛型,即通過參數(shù)化類型來實現(xiàn)在同一份代碼上操作多種數(shù)據(jù)類型。泛型編程是一種編程范式,它利用“參數(shù)化類型”將類型抽象化,從而實現(xiàn)更為靈活的復(fù)用。

在定義泛型類時,可以對客戶端代碼能夠在實例化類時用于類型參數(shù)的類型種類施加限制。如果客戶端代碼嘗試使用某個約束所不允許的類型來實例化類,則會產(chǎn)生編譯時錯誤。這些限制稱為約束。約束是使用 where 上下文關(guān)鍵字指定的。

下表列出了五種類型的約束:

?

約束說明

T:struct

類型參數(shù)必須是值類型。可以指定除 Nullable 以外的任何值類型。

T:class

類型參數(shù)必須是引用類型,包括任何類、接口、委托或數(shù)組類型。

T:new()

類型參數(shù)必須具有無參數(shù)的公共構(gòu)造函數(shù)。當(dāng)與其他約束一起使用時,new() 約束必須最后指定。

T:<基類名>

類型參數(shù)必須是指定的基類或派生自指定的基類。

T:<接口名稱>

類型參數(shù)必須是指定的接口或?qū)崿F(xiàn)指定的接口。可以指定多個接口約束。約束接口也可以是泛型的。

T:U

為 T 提供的類型參數(shù)必須是為 U 提供的參數(shù)或派生自為 U 提供的參數(shù)。這稱為裸類型約束.

?---------------------------------------

一.派生約束

1.常見的

public class MyClass5<T> where T :IComparable { }

2.約束放在類的實際派生之后

public class B { }

public class MyClass6<T> : B where T : IComparable { }

3.可以繼承一個基類和多個接口,且基類在接口前面

public class B { }

public class MyClass7<T> where T : B, IComparable, ICloneable { }

二.構(gòu)造函數(shù)約束

1.常見的

public class MyClass8<T> where T :? new() { }

2.可以將構(gòu)造函數(shù)約束和派生約束組合起來,前提是構(gòu)造函數(shù)約束出現(xiàn)在約束列表的最后

public class MyClass8<T> where T : IComparable, new() { }

三.值約束

1.常見的

public class MyClass9<T> where T : struct { }

2.與接口約束同時使用,在最前面(不能與基類約束,構(gòu)造函數(shù)約束一起使用)

public class MyClass11<T> where T : struct, IComparable { }

四.引用約束

1.常見的

public class MyClass10<T> where T : class { }

五.多個泛型參數(shù)

?public class MyClass12<T, U> where T : IComparable? where U : class { }

六.繼承和泛型

public class B<T>{ }

1. 在從泛型基類派生時,可以提供類型實參,而不是基類泛型參數(shù)

??? public class SubClass11 : B<int>
??? { }

2.如果子類是泛型,而非具體的類型實參,則可以使用子類泛型參數(shù)作為泛型基類的指定類型

??? public class SubClass12<R> : B<R>
??? { }

3.在子類重復(fù)基類的約束(在使用子類泛型參數(shù)時,必須在子類級別重復(fù)在基類級別規(guī)定的任何約束)
??? public class B<T> where T : ISomeInterface { }
??? public class SubClass2<T> : B<T>
where T : ISomeInterface { }

4.構(gòu)造函數(shù)約束
??? public class B<T> where T : new()
??? {
??????? public T SomeMethod()
??????? {
??????????? return new T();
??????? }
??? }
??? public class SubClass3<T> : B<T> where T : new(){ }

七.泛型方法(C#2.0泛型機制支持在"方法聲名上包含類型參數(shù)",這就是泛型方法)

1.泛型方法既可以包含在泛型類型中,又可以包含在非泛型類型中

public class MyClass5
??? {

??????? public void MyMethod<T>(T t){ }
??? }

2.泛型方法的聲明與調(diào)用

public class MyClass5
??? {
??????? public void MyMethod<T>(T t){ }
??? }
??? public class App5
??? {
??????? public void CallMethod()
??????? {
??????????? MyClass5 myclass5 = new MyClass5();
??????????? myclass5.MyMethod<int>(3);
??????? }
??? }

3.泛型方法的重載

?

//第一組重載
?void MyMethod2<T>(int i){ }
?void MyMethod2(int i){ }

?

//第二組重載

public class MyClass8<T,U>
??? {
??????? public T MyMothed(T a, U b)
??????? {
??????????? return a;
??????? }
??????? public T MyMothed(U a, T b)
??????? {
??????????? return b;
??????? }
??????? public int MyMothed(int a, int b)
??????? {
??????????? return a + b;
??????? }
??? }

以下重載是錯誤的:

?//第一組重載
?void MyMethod1<T>(T t, int i){ }

?void MyMethod1<U>(U u, int i){ }

//第二組重載,假設(shè)有兩個泛型參數(shù)
?void MyMethod3<T>(T t) where T : A { }
void MyMethod3<U>(U t) where T : B { }

?

4.泛型方法的覆寫

(1)public class MyBaseClass1
??? {
??????? public virtual void MyMothed<T>(T t) where T : new() { }
??? }
??? public class MySubClass1:MyBaseClass1
??? {
??????? public override void MyMothed<T>(T t) //不能重復(fù)任何約束
??????? { }
??? }

(2)public class MyBaseClass2
??? {
??????? public virtual void MyMothed<T>(T t)
??????? { }
??? }
??? public class MySubClass2 : MyBaseClass2
??? {
??????? public override void MyMothed<T>(T t) //重新定義泛型參數(shù)T
??????? { }
??? }

八.虛擬方法

public class BaseClass4<T>
??? {
??????? public virtual T SomeMethod()
??????? {
??????????? return default(T);
??????? }
??? }
??? public class SubClass4 : BaseClass4<int> //使用實參繼承的時候方法要使用實參的類型
??? {
??????? public override int SomeMethod()
??????? {
??????????? return 0;
??????? }
??? }

??? public class SubClass5<T> : BaseClass4<T> //使用泛型繼承時,方法也是泛型
??? {
??????? public override T SomeMethod()
??????? {
??????????? return default(T);
??????? }
??? }

九.編譯器只允許將泛型參數(shù)隱式強制轉(zhuǎn)換到 Object 或約束指定的類型

class MyClass<T> where T : BaseClass, ISomeInterface
??? {
??????? void SomeMethod(T t)
??????? {
??????????? ISomeInterface obj1 = t;
??????????? BaseClass obj2 = t;
??????????? object obj3 = t;
??????? }
??? }

變通方法:使用臨時的 Object 變量,將泛型參數(shù)強制轉(zhuǎn)換到其他任何類型

class MyClass2<T>
??? {
??????? void SomeMethod(T t)
??????? {
??????????? object temp = t;
??????????? BaseClass obj = (BaseClass)temp;
??????? }
??? }

十.編譯器允許您將泛型參數(shù)顯式強制轉(zhuǎn)換到其他任何接口,但不能將其轉(zhuǎn)換到類

class MyClass1<T>
??? {
??????? void SomeMethod(T t)
??????? {
??????????? ISomeInterface obj1 = (ISomeInterface)t;?
??????????? //BaseClass obj2 = (BaseClass)t;?????????? //不能通過編譯
??????? }
??? }

?

十一.使用臨時的 Object 變量,將泛型參數(shù)強制轉(zhuǎn)換到其他任何類型

class MyClass2<T>
??? {
??????? void SomeMethod(T t)
??????? {
??????????? object temp = t;
??????????? BaseClass obj = (BaseClass)temp;
??????? }
??? }

十二.使用is和as運算符

public class MyClass3<T>
??? {
??????? public void SomeMethod(T t)
??????? {
??????????? if (t is int) { }
??????????? if (t is LinkedList<int>) { }
??????????? string str = t as string;
??????????? if (str != null) { }
??????????? LinkedList<int> list = t as LinkedList<int>;
??????????? if (list != null) { }
??????? }
??? }

轉(zhuǎn)載于:https://www.cnblogs.com/h20064528/archive/2012/04/23/2466632.html

《新程序員》:云原生和全面數(shù)字化實踐50位技術(shù)專家共同創(chuàng)作,文字、視頻、音頻交互閱讀

總結(jié)

以上是生活随笔為你收集整理的【转】C#泛型约束的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。