泛型應用、原理、協變逆變、泛型快取
object(最初的封裝各個型別引數做法)
1,任何父類的地方都可以使用之類來代替
2,object是一切型別的父類
public static void ShowObject(object oParameter)
{
Console.WriteLine("我是{0} 類,型別為:{1},引數值為: {2}",
typeof(CommonMethod).Name,oParameter.GetType().Name,oParameter);
}
3,object型別存在倆個問題;
3.1:裝箱拆箱的問題
解答:object在堆裡面,如果把一個int型別傳遞進來的值從棧裡面複製到堆裡面(這是裝箱)
使用的時候,有需要使用物件值,又會複製到棧裡面(這就是拆箱)
3.2:型別不安全問題
解答: 可能會有,應為傳遞物件的時候沒有限制
在.netformwork2.0是推出來泛型方法,
1.什麼是泛型方法:
方法名後面加上尖括號,裡面是引數型別,
型別引數實際上就是一個型別T宣告,方法就可以用 這個T型別了
2,泛型的使用:
CommonMethod.Show<int>(iValues); //指定好了泛型型別,就必須使用該泛型類的引數值, 呼叫泛型,需要指定好型別引數,
CommonMethod.Show<string>(sValues); 如果可以從型別中推斷,可以省略型別引數(俗稱語法糖---編譯器提供的功能)
CommonMethod.Show<int>("sssss"); 型別不能衝突,比如指定好了泛型型別,你就不能寫別的型別引數的值
3,泛型為什麼也可以支援多種不同型別的引數?
因為泛型方法在宣告是時並沒有寫死型別,泛型T是什麼不知道,T要等著呼叫時才指定,正因為沒寫死,才擁有無限的可能。
泛型設計思想:延遲申明,推遲一切可以推遲的,一切能晚點再晚點做的事
泛型不是一個簡單的語法糖是靠框架升級支援的
4,泛型方法的效能和普通方法,object方法對比區別:
泛型方法和普通方法效能做好,而且泛型方法有可以一個方法支援多種不同型別的的方法呼叫,是因為框架升級支援的
/// ShowGenric<T> 類 與 ShowObj(object oParter) 的對比總結
/// 泛型類可以約束,那些型別不能呼叫,在呼叫時會直接報錯,而不是在編譯用過,執行時才報錯
///
/// 而 obj 類的方法所能什麼型別都能呼叫不會編譯報錯,可以在執行時會報錯,
/// 應為在該方法中做了一次型別強制轉換,有些類沒有繼承該類所以在執行時型別轉換出錯
/// 這就是泛型約束的=好處
5:泛型快取
每個不同的T,都會生成一份不同的副本適合不同型別,需要快取一份資料 的場景,效率高,
第一次進來都會讀取建構函式中建立值,而第二次進來就不會傳進入建構函式中建立值,,因為已經快取好了資料
/// <summary>
/// 一個泛型快取方法
/// </summary>
/// <typeparam name="T"></typeparam>
public static class GetCache<T>
{
//第一次使用快取的時候,都會先到建構函式裡面執行,
//第二次該引數快取有值得時候就不會再進入建構函式中進行讀取值
private static string _TypeTime = "";
static GetCache()
{
_TypeTime = DateTime.Now.ToString("yyyyMMdd");
}
public static string Get()
{
return _TypeTime;
}
}
6:泛型方法/類:
泛型方法:為了一個方法滿足不同型別的需求
泛型類:一個類滿足不同類的需求
泛型介面:一個介面為了滿足所有型別的介面
泛型委託: 一個委託滿足所有型別需求
泛型引數:一個泛型可以使用多個泛型引數 public void Get<T,S,W>(){}
泛型類繼承:需要明確指定泛型型別 public void Get:A<int>{}
不明確指定泛型型別可以這樣寫: public void Get<T,S>:A<T>,B<S>{}
7:泛型約束:
沒有約束,很受極限性,密封類不能進行約束,應為密封類沒意義,密封類沒有子類或父類,以下幾種約束可以放在一起使用
如果一個泛型裡面有多個引數可以直接寫 where T:class where S:class
基類約束:where T:BaseModel,
1,可以吧T當成基類 2,T必須是T:後面的BaseModel類 和 BaseModel 子類 為什麼要約束?因為有了約束才有權利
介面約束: where T:IWorke
引用型別約束: where T:class 返回return null
值型別約束:where T:Struct 返回 return default(T)
無引數建構函式: where T:new() 返回 return new T()