【问题标题】:Custom Collection using IEnumerable vs ICollection vs IList使用 IEnumerable、ICollection 和 IList 的自定义集合
【发布时间】:2012-10-20 20:42:10
【问题描述】:

我需要设计自己的自定义GenericCollection 类。现在我有很多选择可以使用IEnumerableICollectionIList 来推导它,稍后会提供一些附加功能。

我有点困惑,如果我使用IEnumerable<T>,我可能需要声明对象以实际保存集合,就像在这种情况下_list一样。

public class GenericCollection<T> : IEnumerable<T>
{
    private List<T> _list;
    //...
}

但是如果我使用ICollection&lt;T&gt;IList&lt;T&gt;,我不需要声明List 对象,因为它是隐式可用的。

public class GenericCollection<T> : IList<T>
{
    // no need for List object
    //private List<T> _list; 
    //...
}

这两种方法在性能方面有什么区别

在哪种情况下,每个人都是首选,尤其是在设计您自己的系列时。我对性能良好的轻量级系列感兴趣。我认为这可以使用IEnumerable&lt;T&gt; 来实现,但究竟有哪些强有力的理由支持它呢?

我已经查看了一些现有的帖子,但没有一个提供所需的信息。

Returning 'IList' vs 'ICollection' vs 'Collection'

【问题讨论】:

  • 在第一个示例中,您不需要拥有 _list 成员。此外,如果从IList继承并实现与IList相关的公共接口,您仍然需要实现一些存储机制
  • 通用集合?对我来说听起来像是一个列表......
  • 可以更改底层实现,Generic Collection 只是一个包装器。

标签: c# ienumerable ilist icollection custom-collection


【解决方案1】:

IEnumerableICollectionIList(通常,任何带有 I 前缀的类型)只是 interfaces。它们让您公开您的类将要做什么,但与 inherit 一个类不同,接口不会为您提供他们说您必须做的任何事情的默认实现。

至于选择哪个界面,这里有一个快速指南:

  • IList 是可以通过索引访问的ICollection
  • ICollection 是一个IEnumerable,可以轻松访问AddRemoveCount 等内容。
  • IEnumerable 是可以枚举的任何内容,即使在您枚举之前这些内容的列表并不存在。

您可能希望为您的集合扩展(或保留为运行大部分逻辑的私有字段)的一些类是List&lt;T&gt;Collection&lt;T&gt;(它实现了IList&lt;T&gt;,但更容易访问覆盖实现,请参阅Collection<T> versus List<T> what should you use on your interfaces? 了解这两者之间的巨大差异)ObservableCollection&lt;T&gt;,或不是列表的集合,如Dictionary&lt;T, U&gt;HashSet&lt;T&gt;。有关任何这些的更多信息,请查看该课程的 MSDN 文档。

【讨论】:

    【解决方案2】:

    首先,您不必在这些接口之间进行实际选择,如果有必要,您可以实现所有这三个接口。其次,实现 IEnumerable 不需要您公开基础列表。您可以只实现使用底层列表的 Enumerator 的方法。

    在性能方面,我怀疑会有很大的影响,请专注于您在功能上需要的东西。唯一确定的方法是测量。

    【讨论】:

    • 我错误地添加了公共列表,但感谢您的指点。实现所有三个接口有什么用?如果我只专注于功能,那么我也可以使用 List 添加并准备好提供功能。但我正在寻找一些强有力的理由来选择 IEnumerable,如果有的话?
    • 既然Ilist实现了IEnumerable,那么实现IList就不需要显式实现了。我只是想说这不是一个非此即彼的问题。
    【解决方案3】:

    性能不太可能取决于实现了哪些接口。这取决于处理器必须运行多少指令才能实现某个目标。如果您实现 IEnumerable 并覆盖 List,您最终可能会编写 Add/Remove/this[] 方法,这些方法只是将调用传播到 List,这会增加性能开销。因此,虽然我没有进行任何测量,但继承方法可能会快一点。

    但是,这些细节通常只对极度需要节省每个可能的 CPU 周期的实时应用程序很重要。 Eric Lippert 有一篇关于关注此类细节的精彩文章:http://blogs.msdn.com/b/ericlippert/archive/2003/10/17/53237.aspx。一般来说,您可能最好使用更适合您的应用程序的业务逻辑和架构的方法,而不是性能细节。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2010-11-12
      • 1970-01-01
      • 2011-02-22
      • 1970-01-01
      • 1970-01-01
      • 2014-12-07
      • 2013-06-24
      • 1970-01-01
      相关资源
      最近更新 更多