1. 程式人生 > >泛型的學習筆記

泛型的學習筆記

技術 類型 假設 http 需求 ons 接口 是把 vat

我們在日常的開發任務中,經常遇到對不同的數據結構執行相同的操作,例如有一個方法傳入的參數可能是字符串也可能是數字,這樣的情況下,一般我們是直接傳入一個object類型的參數,以便於可以實現這樣的功能。例如以下代碼。

private static void Show(object a)

{

Console.WriteLine(a.ToString());

}

這樣的代碼可是實現我們需要的功能,但是確定也很明顯:1、只是傳入一個object類型的參數,對於調用方來說,根本不知道應該傳入一個什麽類型的參數,很有可能以為參入參數的問題造成代碼運行失敗。2.object是一個引用類型,如果我們要處理的是一個值類型,那麽就會產生裝箱和拆箱的操作,頻繁的裝箱拆箱會對程序的性能造成極大的影響。在這樣的需求下,C#2.0引入了泛型的概念,用於提供通用的功能以及編譯時的類型安全。

一、泛型的定義

泛型的定義非常簡單,<T>即可<>尖括號不能省略,T代表需要操作的具體類型,T不是固定的你可以使用任何有意義的符號代替。例如以下定義

private static void Show<TValue>(TValue a)

{

Console.WriteLine(a.ToString());//TValue代表需要操作的類型,需要註意的是TValue是類型而不是實例

}

泛型的定義可以放在方法上面,也可以放在整個類上面,放在方法上面那麽只有當前方法是泛型方法,而直接放在類上面,則是把整個類全部定義為了泛型類,類內部的任何方法再使用此泛型的時候都可以不用再定義,如果需要定義多個泛型參數,則使用逗號隔開所有的參數,例如

private static void Show<TKey,TValue>(TValue a)

{

Console.WriteLine(a.ToString());

}

二、泛型方法的使用

定義了泛型方法就要去使用它,假設定義了如下的泛型方法

private static TValue Show<TValue>(TValue a)

{

Console.WriteLine(a.ToString());

return a;

}

那麽應該怎麽調用他呢?

Show<string>("此坑已滿");

Show<int>(123);

在<>中使用需要操作的類型代替TValue這個符號

技術分享圖片

上面就是調用泛型方法的結果。

三、泛型約束

有時候我們需要我們的泛型參數滿足一定的條件,例如我們需要T繼承自IComparable接口,或者我們要求T不能是值類型,只能是引用類型這樣的需求,該怎樣滿足呢?很簡單,使用where即可,例如以下定義

//以下定義要求TValue必須是一個引用類型

private static TValue Show<TValue>(TValue a) where TValue:class

{

Console.WriteLine(a.ToString());

return a;

}

有了這樣的定義,如果我們在調用泛型方法的時候把TValue定義為了一個值類型,那麽VS的智能提示就會在編譯時報錯,這樣就提供了編譯時的類型安全。例如

如果是要求TValue要滿足多個要求的話,則使用逗號分開即可

private static TValue Show<TValue>(TValue a) where TValue:class,IComparable,new ()

{

Console.WriteLine(a.ToString());

return a;

}

下面是常用的一些約束規則

  1. 要求必須是引用類型,where T:class
  2. 要求必須是值類型,where T:struct
  3. 約束中可以有多個接口,但只能有一個基類,因為類型繼承要求單基類繼承
  4. new ()要求T必須有一個無參構造函數,同時new()必須放在約束的最後,同時C#不支持約束帶參數的構造函數

其他更加詳細的規則請參考MSDN

四、C#中常見的泛型

泛型可以用在方法,類型,接口,委托等等對象上面,在C#中有很多已經定義好的泛型供我們直接使用,例如List<T>,Dictionary<TKey,TValue>,Func<T1,T2>,Action<T>等等。他們的使用方法,請參考MSDN或者自行百度,謝謝!

泛型的學習筆記