簡體   English   中英

關於C#協方差的問題

[英]Question about C# covariance

在下面的代碼中:

interface I1 { }
class CI1: I1 { }

List<CI1> listOfCI1 = new List<CI1>();

IEnumerable<I1> enumerableOfI1 = listOfCI1; //this works

IList<I1> listofI1 = listOfCI1; //this does not

我能夠將“listOfCI1”分配給IEnumerable<I1> (由於協方差)

但為什么我無法將其分配給IList<I1> 就此而言,我甚至無法做到以下幾點:

List<I1> listOfI12 = listOfCI1;

協方差不應該允許我將派生類型分配給基類型嗎?

簡單地說, IList<T>不是協變的,而IEnumerable<T>是。 這就是為什么......

假設IList<T> 協變的。 下面的代碼顯然不是類型安全的......但是你想要錯誤在哪里?

IList<Apple> apples = new List<Apple>();
IList<Fruit> fruitBasket = apples;
fruitBasket.Add(new Banana()); // Aargh! Added a Banana to a bunch of Apples!
Apple apple = apples[0]; // This should be okay, but wouldn't be

關於方差的大量細節,請參閱Eric Lippert關於它的博客文章系列 ,或觀看我關於NDC差異的討論視頻

基本上,只有在保證安全的情況下才會允許方差(並且以表示保持的方式,這就是為什么你不能將IEnumerable<int>轉換為IEnumerable<object> - 裝箱轉換不保留表示的原因)。

比較聲明(msdn)

public interface IEnumerable<out T> : IEnumerable

public interface IList<T> : ICollection<T>, IEnumerable<T>, IEnumerable

你看到那個神奇的詞out嗎? 這意味着協方差已經開啟。

沒有。

否則,您可以將I1的不同實現添加到僅包含C1的列表中。

IList<T>接口不是協變的。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM