【问题标题】:Adding IEnumerable<T> to class derived from CollectionBase将 IEnumerable<T> 添加到从 CollectionBase 派生的类
【发布时间】:2009-09-23 20:29:04
【问题描述】:

假设我有一个类 TestCollection 用于保存 Test 类型的对象,并定义为

public class TestCollection : CollectionBase

这允许我以

的形式遍历集合
foreach(object o in collection)
...

foreach(Test t in collection)

但不允许我使用新的 Linq 查询。

如果我将类的定义更改为

public class TestCollection : CollectionBase, IEnumerable<Test>

并添加一个方法

public new IEnumerator<Test> GetEnumerator()
{
    foreach (Test o in this.List)
        yield return o ;
}

那么 linq 查询可用。

然而,这个新方法不仅在 linq 查询中被调用,而且在遗留代码中也被调用(即在 foreach(object o in collection) 和 foreach(Test in Collection) 期间。

遍历集合的旧方法和假设集合中所有项目都是 Test 类型的新方法之间有什么区别吗?我知道添加 IEnumerator 方法会导致程序在找到除 Test 以外的任何类型时引发异常,但想知道我是否忽略了任何内容。

【问题讨论】:

    标签: c# generics collections


    【解决方案1】:

    既然你在2.0(或以上),也许只是继承自Collection&lt;T&gt;

    public class TestCollection : Collection<Test> {
        // your extra code here
    }
    

    然后您可以免费获得IList&lt;T&gt;ICollection&lt;T&gt;IEnumerable&lt;T&gt;virtual 方法,您可以通过override 为行为打上烙印。

    【讨论】:

    • 更改基本类型是一项重大更改 - 如果该类已经发布,则不应这样做。
    • 如果类还没有发货,这绝对应该做。
    • 目前不想从 Collection 继承,因为我希望免费(或几乎免费)获得一些东西(即需要很少的测试。)更改为继承自Collection 听起来像是一个很大的变化(即需要大量测试)。还。实际情况比我的例子更复杂。会有一些从 Test 派生的类(比如 Test2),它们有自己的集合类,并且从 Collection 或 TestCollection 继承 Test2Collection 不能正常工作。
    【解决方案2】:

    不,您将看到相同的结果,并且只会遇到一个额外的间接级别(因为新的 GetEnumerator 方法只是调用现有的 GetEnumerator 方法并流式传输其输出)。

    【讨论】:

      【解决方案3】:

      从迭代器编译的IEnumerator&lt;T&gt; 没有实现Reset 方法。 编辑:我的意思是它会抛出一个NotImplementedException

      这实际上并没有什么问题,但如果你想要Reset 方法,你必须编写自己的迭代器类,这并不难。

      【讨论】:

      • 否;它实现它——就像抛出一个NotImplementedException。迭代器块很适合这个目的。
      猜你喜欢
      • 1970-01-01
      • 2013-08-22
      • 1970-01-01
      • 2018-01-05
      • 1970-01-01
      • 2020-12-07
      • 1970-01-01
      • 2010-10-22
      • 2015-02-08
      相关资源
      最近更新 更多