gpt4 book ai didi

c# - 为什么 IEnumerable 不需要强制转换而 List 需要?

转载 作者:太空狗 更新时间:2023-10-29 22:59:49 25 4
gpt4 key购买 nike

给定以下 LinqPad 示例:

void Main()
{
List<DbItem> dbItems = new List<DbItem>
{
new DbItem{Id = 4, SomeValue = "Value For 4", OtherValue = 1},
new DbItem{Id = 19, SomeValue = "Value For 19", OtherValue = 2}
};

ListMethod(dbItems.Cast<IDbItem>().ToList()); <-+
EnumerableMethod(dbItems); <-+
} |
|
// These are the methods are I asking about -------+

public void ListMethod(List<IDbItem> dbItems)
{
Console.WriteLine(dbItems);
}
public void EnumerableMethod(IEnumerable<IDbItem> dbItems)
{
Console.WriteLine(dbItems);
}
public class DbItem : IDbItem
{
public int Id {get; set;}
public string SomeValue {get; set;}
public int OtherValue {get; set;}
}
public interface IDbItem
{
int Id {get; set;}
string SomeValue {get; set;}
}

为什么 EnumerableMethod 可以直接获取列表,而 ListMethod 需要先进行转换?

我知道正在从 DbItem 到 IDbItem 进行强制转换,但是允许它在没有明确请求的情况下进行强制转换的 IEnumerable 有什么不同?

我想答案涉及协方差这个词,但我对此了解不多,无法自己弄清楚。

最佳答案

查看 this post about covariance .他给出了解释和一种无需类型转换即可使代码工作的方法。列表不是协变的,但您可以像这样更改方法:

public void ListMethod<T>(List<T> dbItems) where T : IDbItem
{
Console.WriteLine(dbItems);
}

协变性是将派生程度更高的泛型分配给基本泛型的能力。 List 不是协变的原因是你可以这样做:

class Animal {}
class Dog : Animal {}
class Cat : Animal {}

void someFunction()
{
List<Animal> dogs = new List<Dog>();
dogs.Add(new Cat());
}

dogs 实际上是狗的列表,而不是动物的列表。因此,向其添加 Cat 将是一个问题,特别是会导致编译器错误。

关于c# - 为什么 IEnumerable 不需要强制转换而 List 需要?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18647658/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com