Are there any non-repeatable IEnumerable classes?

It is possible for implementations of IEnumerable(Of T) to return any items they see fit, for any reason whatsoever. It's pretty well expected that if one calls GetEnumerator twice on the same sequence of items, and then proceeds to cycle through both enumerators, they should either yield the same items in the same order or throw an exception. There are a number of routines that accept an IEnumerable(Of T) and will fail badly if given one that does not abide by such a contract.

If I had my druthers, IEnumerable would have been split into a family of interfaces; the basic IEnumerable's enumerator would lose the Reset method and would convey no particular promise of repeatability. A new IMultiEnumerable would return an enumerator with a Reset method and and a guarantee that multiple passes would yield identical data; the enumerator might also support its own GetEnumerator method (I think that should be practical for any type which could support multi-pass enumeration; the only cost would be a 'start' pointer so the nested enumerator would be reset to the location of its original creation).


File.ReadLines() does return an IEnumerable<T> that only works once.


No, any well behaving class that implements IEnumerable will allow repeated enumerations.

To enumerate collections that aren't repeatable, you don't have a class that implements IEnumerable. Instead you have a method that returns an enumerator. That way the enumerator instead of a class holds the collection, so it's not possible to call GetEnumerator twice for the same collection. To repeat the enumerator you have to call the method to create a new collection.

An example of this is the Enumerable.Range method. It creates the items for a range on the fly, so the range doesn't exist as a collection, which makes it non-repeatable. To enumerate the same range again you call the method to create a new range with the same bounds.


Comments

  1. Ronan

    • 2016/3/12

    To enumerate collections that aren't repeatable, you don't have a class that implements IEnumerable . Instead you have a method that returns an 

  2. Cruz

    • 2018/2/6

    No, any well behaving class that implements IEnumerable will allow repeated enumerations. To enumerate collections that aren't repeatable, you don't have a class that implements IEnumerable. Instead you have a method that returns an enumerator.

  3. Monti

    • 2015/4/14

    I need to clarify that I'm looking for a solution that preserves the lazy nature of the IEnumerable - converting it to a list or an array can be an answer in 

  4. Battaglia

    • 2019/10/7

    If DoSomethingX is an iterator method, then C# creates an object of an anonymous class implementing IEnumerable<int> as a state machine. This object is assigned to values. Therefore there is no difference in usage of these two IEnumerable<int>. It does not matter whether it is based on a collection or on a iterator method.

  5. Aaron

    • 2020/5/31

    Generates a sequence that contains one repeated value. Collections.Generic. The number of times to repeat the value in the generated sequence.

  6. Cox

    • 2019/3/15

    Return values should, unless you have a specific use case in mind already, be returning an IEnumerable<T> which is not mutable. If the underlying type is still a List (or Array or any of a myriad of other types that implement IEnumerable<T>) you can still cast it. Also, some LINQ expressions will self optimise if the underlying type is one

  7. Skyler

    • 2019/12/16

    Methods that are used in a query that returns a sequence of values do not consume the target data until the query object is enumerated. This is known as 

  8. Robert

    • 2020/8/20

    IEnumerable and IEnumerator are both interfaces. IEnumerable has just one method called GetEnumerator. This method returns another type which is an interface that interface is IEnumerator. If we want to implement enumerator logic in any collection class, it needs to implement IEnumerable interface (either generic or non-generic).

  9. Samuel

    • 2015/4/19

    There are times when it's helpful to check a non-repeatable IEnumerable public static class MyEnumerableExtensions { public static IEnumerable<TFirst> 

  10. Brown

    • 2020/8/24

    If enumerating is expensive, non-repeatable and yields a lot of data (like up writing aggregator classes into which I could push items in a foreach loop 

  11. Rayan

    • 2018/4/7

    Creating a copy of the sequence means it needs to be sufficiently small to fit in memory, of course. That may not be ideal. This will only create a copy when 

  12. Pablo

    • 2020/12/5

    Inheritance and generics Basic rules A non-generic class can inherit from a generic class. In this case, all parameter types must be resolved: class B<T> {.

  13. Lance

    • 2021/5/11

    InsertAfter method XmlNode class, 584 writing XmlNodes in DOM trees, 221 nesting of tags, 223 non repeatable tags, 224 providing formatting to tags, 

  14. Malakhi

    • 2015/9/8

    Or better: avoid having to read it twice, since not all data is repeatable. The IEnumerable and IEnumerator should generally be separate classes, and except in 

Comments are closed.

Recent Posts