C# 變體
變體(variance)是協(xié)變(covariance)和抗變(contravariance)的統(tǒng)稱,這兩個概念在.NET4中引入。實(shí)際上,它們己經(jīng)存在了較長時間了(在.NET 2.0中就可以使用),但在.NET 4之前很難實(shí)現(xiàn)它們,因?yàn)樗鼈冃枰ㄖ频木幾g過程。
要掌握這些術(shù)語的含義,最簡單的方式是把它們與多態(tài)性進(jìn)行比較。多態(tài)性允許把派生類型的對象放在基類型的變量中,例如:
Cow myCow = new Cow("BenM>
Animal myAnimal = myCow;
其中把Cow類型的對象放在Animal類型的變量中,這是可行的,因?yàn)镃ow派生自Animal。
但這不適用于接口,也就是說,下面的代碼不能工作:
IMethaneProducer<Cow> cowMethaneProducer = myCow;
IMethaneProducer<Animal> animalMethaneProducer = cowMethaneProducer;
假定Cow支持IMethaneProducer<Cow>接口,第一行代碼就沒有問題。但是,第二行代碼預(yù)先假定兩個接口類型有某種關(guān)系,但實(shí)際上這種關(guān)系不存在,所以無法把一種類型轉(zhuǎn)換為另一種類型??梢栽诜盒徒涌诤头盒臀猩隙x變體類型參數(shù),以適合上述代碼演示的情形。
為使上述代碼工作,IMethaneProducer<T>接口的類型參數(shù)T必須是協(xié)變的。有了協(xié)變的類型參數(shù),就可以在IMethaneProducer<Cow>和IMethaneProducer<Animal>之間建立繼承關(guān)系,這樣一種類型的變量就可以包含另一種類型的值,這與多態(tài)性類似(但稍復(fù)雜些)。
為了完成對變體的介紹,需要看看變體的另一面:抗變??棺兒蛥f(xié)變是類似的,但方向相反。抗變不能像協(xié)變那樣,把泛型接口值放在使用基類型的變量中,但可以把該接口放在使用派生類型的變量中,例如:
IGrassMuncher<Cow> cowGrassMuncher = myCow;
IGrassMuncher<SuperCow> superCowGrassMuncher = cowGrassMuncher;
初看起來似乎有點(diǎn)古怪,因?yàn)椴荒芡ㄟ^多態(tài)性完成相同的功能。但是這在一些情況下是一項(xiàng)有效的技術(shù)。
點(diǎn)擊加載更多評論>>