ienumerable vs list <t> </t>

时间:2012-12-21 15:19:14

标签: c# .net ienumerable

据说IEnumerable用于自定义集合。其中一个用途是用于遍历自定义集合的foreach循环。

但是我的问题是,不是制作首先实现IEnumerable的自定义集合,而是构建另一个类来实现IEnumerator来存储一组自定义对象,为什么我们不能只使用{ {1}}。

提前感谢您的帮助。

9 个答案:

答案 0 :(得分:3)

因为您可能希望实现不同的数据结构。 IEnumerable抽象了序列的概念,而List具有索引的概念,添加/删除项及其自己的数据结构。

作为不同结构的一个例子,这里有一个允许你输入无限foreach循环的类。

public class InfiniteSequence : IEnumerable<int>
{
    public IEnumerator<int> GetEnumerator()
    {
        return new InfiniteEnumerator();
    }

    IEnumerator IEnumerable.GetEnumerator()
    {
        return GetEnumerator();
    }

    class InfiniteEnumerator : IEnumerator<int>
    {
        public void Dispose()
        {
            throw new NotImplementedException();
        }

        public bool MoveNext()
        {
            Current++;
            return true;
        }

        public void Reset()
        {
            Current = 0;
        }

        public int Current { get; private set; }

        object IEnumerator.Current
        {
            get { return Current; }
        }
    }
}

答案 1 :(得分:1)

当然,您可以使用List<T>

如果List<T>符合您的需求,请使用它,不要创建一个继承自IEnumerable<T>的新类。

答案 2 :(得分:1)

IEnumerable<T>不适合您的需求时,您会提供自己的List<T>实施。这个典型的例子是当你想支持对集合进行延迟评估时,可能使用yield return的方法。

答案 3 :(得分:1)

正如@ ken2k所说,你可以List<T>,你将得到一个T类型的通用版本。但是,如果要隐藏此实现并自定义List<T>或包含新功能的某些操作,则可以从List继承并实现自己的方法。样本:

public class CustomerCollection : List<Customer> // at this time, you have all methods from List such as Add, Remove, [index] etc...
{
   public double AverageAge()
   {
       return this.Average(customer => customer.Age)
   }

   // other methods...
}

IEnumeralbe是.Net Framework中最集合的集合,你可以只是在这个抽象中进行交互。

答案 4 :(得分:0)

您可以使用List<T>或任何其他通用集合类型。毕竟List<T>实现了IEnumerable<T>

你是否有一个特殊的边缘案例需要用定制的集合来覆盖?

答案 5 :(得分:0)

当然,您可以将您的成员定义为List<T>,然而将您的类的客户绑定到特定的实现。如果将成员定义为IEnumerable<T>(假设消费者只想枚举您的集合),则可以将实现更改为实现接口的不同集合类型,而不会破坏合同。如果您将其从List<T>更改为SortedSet<T>以实施订单,则您的消费者不会受到影响。

这基本上是对接口而不是具体类型进行编码的优势。

您可以使用其他界面,即。 ICollection<T>如果您的消费者想要的不仅仅是枚举。

答案 6 :(得分:0)

如果它没有做任何其他事情,请继续。专门收藏品适用于需要做的收藏......特别......。

(例如,ListViewItemCollection更新时必须通知其父ListView,因此需要实施IList(T),因此IEnumerable(T)。自定义集合,它可能会从中继承。仅从IEnumerable(T)继承才有意义,只有当您的集合可以枚举但不能编入索引时。)

答案 7 :(得分:0)

你可以。

public class List<T> : IList<T>, ICollection<T>, 
IList, ICollection, IReadOnlyList<T>, IReadOnlyCollection<T>, IEnumerable<T>, 
IEnumerable 

答案 8 :(得分:0)

我认为这里混淆的根源是“自定义集合”和“自定义类实例集合”之间的区别。在这两个中,您的List<CustomObject>是后一种情况 - 您只是重复使用其他人创建的集合并利用泛型来保存项目类型信息,这就是全部。真正的自定义集合可能会实现IEnumerable<T>,但您很少(如果有的话)需要它。

所以在这种情况下你不仅可以 使用List<CustomObject>