2011-07-10 57 views
6

可能重複:
Difference between Covariance & Contra-variance.NET:協變和逆變

我想了解協變和逆變的,以及兩者之間的區別。我已經看過this link,到目前爲止我已經理解了以下內容:

協變是您將派生成員分配給基礎成員的過程。如:

IEnumerable<Derived> d = new List<Derived>(); 
IEnumerable<Base> b = d; 

我甚至不確定我是否在上面......猜對。基本上,我正在尋找一個人,以最簡單的方式爲我貶低它,以便我能理解這兩者之間的區別以及它們之間的差異。

我也明白這裏有類似的討論話題,但大多數答案都不是我正在尋找的那種描述。

回答

0

對於我們的內部培訓,我已經與精彩的書「Smalltalk,Objects and Design(Chamond Liu)」合作,並且我轉述了以下示例。 - 希望這有助於...

「一致性」是什麼意思? 這個想法是設計具有高度可替換類型的類型安全類型層次結構。獲得這種一致性的關鍵是基於子類型的一致性。 (我們將在一個較高的水平在這裏討論了里氏替換原則(LSP)。)

協方差: 讓我們假設下蛋「始終堅持」與靜態類型的小鳥: 如果類型鳥生一個蛋,止跌鳥的亞型是蛋的亞型嗎? 例如類型鴨奠定鴨蛋,然後一致性給出。 爲什麼這是一致的?因爲在這樣一個表達式中:引用aBird可以由Bird或Duck實例合法替換。 我們說返回類型與定義Lay()的類型是協變的。 子類型的覆蓋可能會返回更專門的類型。 =>

逆變「他們提供更多的。」: 假設鋼琴是鋼琴家可以玩「始終堅持」與靜態類型: 如果一個鋼琴演奏鋼琴,她將能夠發揮GrandPiano? 難道寧願Virtuoso玩GrandPiano? (被警告;有一個扭曲!)這是不一致的!因爲在這樣一個表達式中: aPiano.Play(aPianist); aPiano無法通過鋼琴或GrandPiano實例合法取代!一個GrandPiano只能由Virtuoso演奏,鋼琴家太籠統了! GrandPianos必須使用更普通的類型才能播放,然後播放是一致的。 我們說參數類型與定義Play()的類型是不相容的。 子類型的覆蓋可能會接受更通用的類型。 =>「他們需要更少。」