天天看點

C# 泛型程式設計之泛型類、泛型方法、泛型限制泛型方法泛型類泛型委托.net泛型限制  

  

  所謂泛型,即通過參數化類型來實作在同一份代碼上操作多種資料類型。

  泛型程式設計是一種程式設計範式,它利用“參數化類型”将類型抽象化,進而實作更為靈活的複用。在定義泛型類時,在對用戶端代碼能夠在執行個體化類時,可以用類型參數的類型種類施加限制。

在C# 2.0中,方法可以定義特定于其執行範圍的泛型參數,如下所示:

<a></a>

即使包含類不适用泛型參數,你也可以定義方法特定的泛型參數,如下所示:

注意:屬性和索引器不能指定自己的泛型參數,它們隻能使用所屬類中定義的泛型參數進行操作。

在調用泛型方法的時候,你可以提供要在調用場所使用的類型,如下所示:

//調用泛型方法

MyClass myClass = new MyClass();

myClass.MyMethod&lt;int&gt;(3);

泛型推理:

在調用泛型方法時,C#編譯器足夠聰明,基于傳入的參數類型來推斷出正确的類型,并且它允許完全省略類型規範,如下所示:

//泛型推理機制調用泛型方法

myClass.MyMethod(3);

注意:泛型方法無法隻根據傳回值的類型推斷出類型,代碼如下:

泛型方法中泛型參數的限制,如下:

無法為類級别的泛型參數提供方法級别的限制。類級别泛型參數的所有限制都必須在類作用範圍中定義,代碼如下所示

而下面的代碼是正确的:

泛型參數虛方法的重寫:子類方法必須重新定義該方法特定的泛型參數,代碼如下

同時子類中的泛型方法不能重複基類泛型方法的限制,這一點和泛型類中的虛方法重寫是有差別的,代碼如下

子類方法調用虛拟方法的基類實作:它必須指定要代替泛型基礎方法類型所使用的類型實參。你可以自己顯式的指定它,也可以依靠類型推理(如果可能的話)代碼如下:

在某個類中定義的委托可以使用該類的泛型參數,代碼如下

委托推理:C#2.0使你可以将方法引用的直接配置設定轉變為委托變量。将上面的代碼改造如下

泛型委托的限制:

委托級别的限制隻在聲明委托變量和執行個體化委托時使用,類似于在類型和方法的作用範圍中實施的其他任何限制。

泛型和反射

在Net2.0當中,擴充了反射以支援泛型參數。類型Type現在可以表示帶有特定類型的實參(或綁定類型)或未指定類型的泛型(或稱未綁定類型)。像C#1.1中那樣,您可以通過使用typeof運算符或通過調用每個類型支援的GetType()來獲得任何類型的Type。代碼如下:

typeof還可以對未綁定的泛型進行操作,代碼如下

請注意"&lt;&gt;"的用法。要對帶有多個類型參數的未綁定泛型類進行操作,請在"&lt;&gt;"中使用","

Type類中添加了新的方法和屬性,用于提供有關該類型的泛型方面的反射資訊,見MSDN。

  如果用戶端代碼嘗試使用某個限制所不允許的類型來執行個體化類,則會産生編譯時錯誤。這些限制稱為限制。限制是使用 where 上下文關鍵字指定的。

  下表列出了五種類型的限制:

限制

說明

T:struct

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

T:class

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

T:new()

類型參數必須具有無參數的公共構造函數。當與其他限制一起使用時,new() 限制必須最後指定。

T:&lt;基類名&gt;

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

T:&lt;接口名稱&gt;

類型參數必須是指定的接口或實作指定的接口。可以指定多個接口限制。限制接口也可以是泛型的。

T:U

為 T 提供的類型參數必須是為 U 提供的參數或派生自為 U 提供的參數。這稱為裸類型限制.

1.常見的

public class MyClass5&lt;T&gt; where T :IComparable { }

2.限制放在類的實際派生之後

public class B { }

public class MyClass6&lt;T&gt; : B where T : IComparable { }

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

public class MyClass7&lt;T&gt; where T : B, IComparable, ICloneable { }

public class MyClass8&lt;T&gt; where T :  new() { }

2.可以将構造函數限制和派生限制組合起來,前提是構造函數限制出現在限制清單的最後

public class MyClass8&lt;T&gt; where T : IComparable, new() { }

public class MyClass9&lt;T&gt; where T : struct { }

2.與接口限制同時使用,在最前面(不能與基類限制,構造函數限制一起使用)

public class MyClass11&lt;T&gt; where T : struct, IComparable { }

常見的

public class MyClass10&lt;T&gt; where T : class { }

 public class MyClass12&lt;T, U&gt; where T : IComparable  where U : class { }

public class B&lt;T&gt;{ }

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

    public class SubClass11 : B&lt;int&gt;

    { }

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

    public class SubClass12&lt;R&gt; : B&lt;R&gt;

3.在子類重複基類的限制(在使用子類泛型參數時,必須在子類級别重複在基類級别規定的任何限制)

    public class B&lt;T&gt; where T : ISomeInterface { }

    public class SubClass2&lt;T&gt; : B&lt;T&gt; where T : ISomeInterface { }

4.構造函數限制

    public class B&lt;T&gt; where T : new()

    {

        public T SomeMethod()

        {

            return new T();

        }

    }

    public class SubClass3&lt;T&gt; : B&lt;T&gt; where T : new(){ }

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

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

public class MyClass5

        public void MyMethod&lt;T&gt;(T t){ }

2.泛型方法的聲明與調用

3.泛型方法的重載

4.泛型方法的覆寫

(1)public class MyBaseClass1

        public virtual void MyMothed&lt;T&gt;(T t) where T : new() { }

    public class MySubClass1:MyBaseClass1

        public override void MyMothed&lt;T&gt;(T t) //不能重複任何限制

        { }

(2)public class MyBaseClass2

        public virtual void MyMothed&lt;T&gt;(T t)

    public class MySubClass2 : MyBaseClass2

        public override void MyMothed&lt;T&gt;(T t) //重新定義泛型參數T

編譯器隻允許将泛型參數隐式強制轉換到 Object 或限制指定的類型。

變通方法:使用臨時的 Object 變量,将泛型參數強制轉換到其他任何類型

1

2

3

4

5

6

7

8

<code>class</code> <code>MyClass2&lt;T&gt;</code>

<code>{</code>

<code>    </code><code>void</code> <code>SomeMethod(T t)</code>

<code>    </code><code>{</code>

<code>        </code><code>object</code> <code>temp = t;</code>

<code>        </code><code>BaseClass obj = (BaseClass)temp;</code>

<code>    </code><code>}</code>

<code>}</code>

編譯器允許您将泛型參數顯式強制轉換到其它任何接口,但不能将其轉換到類

使用臨時的 Object 變量,将泛型參數強制轉換到其他任何類型

沒有整理與歸納的知識,一文不值!高度概括與梳理的知識,才是自己真正的知識與技能。 永遠不要讓自己的自由、好奇、充滿創造力的想法被現實的架構所束縛,讓創造力自由成長吧! 多花時間,關心他(她)人,正如别人所關心你的。理想的騰飛與實作,沒有别人的支援與幫助,是萬萬不能的。

   本文轉自wenglabs部落格園部落格,原文連結:http://www.cnblogs.com/arxive/p/6179972.html,如需轉載請自行聯系原作者

繼續閱讀