有人能向我解释一下为什么我想在c#中使用IList而不是List吗?

相关问题:为什么公开List<T>被认为是不好的


当前回答

List<T>是IList<T>的特定实现,它是一个容器,可以像线性数组T[]一样使用整数索引寻址。当您指定IList<T>作为方法参数的类型时,您只是指定了您需要容器的某些功能。

例如,接口规范并不强制使用特定的数据结构。List<T>的实现在访问、删除和添加元素方面与线性数组具有相同的性能。但是,您可以想象一个由链表支持的实现,其中在末尾添加元素更便宜(常量时间),但随机访问要昂贵得多。(注意。net LinkedList<T>没有实现IList<T>。)

这个例子还告诉您,在某些情况下,您可能需要在参数列表中指定实现,而不是接口:在这个例子中,当您需要特定的访问性能特征时。这通常是容器的特定实现所保证的(List<T>文档:“它使用一个数组实现IList<T>泛型接口,该数组的大小根据需要动态增加。”)。

此外,您可能需要考虑公开最少需要的功能。为例。如果你不需要改变列表的内容,你可能应该考虑使用IEnumerable<T>,它是IList<T>扩展的。

其他回答

因为定义IList或ICollection将为接口的其他实现打开空间。

您可能希望有一个IOrderRepository,它在IList或ICollection中定义一个订单集合。然后,您可以使用不同类型的实现来提供订单列表,只要它们符合IList或ICollection定义的“规则”。

令人惊讶的是,这些List和IList的问题(或答案)都没有提到签名差异。(这就是为什么我在SO上搜索这个问题!)

下面是List中包含的在IList中找不到的方法,至少在。net 4.5(大约2015年)

AddRange AsReadOnly BinarySearch 能力 ConvertAll 存在 找到 FindAll FindIndex FindLast FindLastIndex ForEach GetRange InsertRange LastIndexOf RemoveAll RemoveRange 反向 排序 ToArray TrimExcess TrueForAll

IList<T>是一个接口,所以你可以继承另一个类,仍然实现IList<T>,而继承List<T>阻止你这样做。

例如,如果有一个类a,你的类B继承了它,那么你不能使用List<T>

class A : B, IList<T> { ... }

如果。net 5.0取代了System.Collections.Generic。List<T>到system . collection . generic . linearlist <T>. . net总是拥有List<T>这个名称,但是他们保证IList<T>是一个契约。所以恕我直言,我们(至少我)不应该使用别人的名字(尽管在这种情况下是。net),之后会遇到麻烦。

在使用IList<T>的情况下,调用者总是保证事情正常工作,而实现者可以自由地将底层集合更改为任何可供选择的IList具体实现

所有的概念基本上都在上面关于为什么使用接口而不是具体实现的回答中说明了。

IList<T> defines those methods (not including extension methods)

IList<T> MSDN link

添加 清晰的 包含 CopyTo GetEnumerator IndexOf 插入 删除 RemoveAt

List<T>实现了这9个方法(不包括扩展方法),除此之外,它还有大约41个公共方法,这将影响您在应用程序中使用哪个方法。

List<T> MSDN link