Disclaimer: I understand the difference between IEnumerable<T>
and IEnumerator<T>
and how to use both. This is not a duplicate of this or this.
This is more of a design question - since IEnumerator<T>
already encapsulates all the necessary information (.Current
, .MoveNext()
) about something that can be enumerated, then what's the point of introducing a type (IEnumerable<T>
) whose sole purpose is to return an instance of the former?
To be specific:
Why can't foreach
be designed to iterate directly through an IEnumerator<T>
, like so:
// foreach (var e in anEnumerator) { //... }
while (anEnumerator.MoveNext())
{
doSomething(anEnumerator.Current);
}
Why can't Linq be built based directly off of IEnumerator<T>
?
An IEnumerator is a thing that can enumerate: it has the Current property and the MoveNext and Reset methods (which in . NET code you probably won't call explicitly, though you could). An IEnumerable is a thing that can be enumerated...which simply means that it has a GetEnumerator method that returns an IEnumerator .
IEnumerable in C# is an interface that defines one method, GetEnumerator which returns an IEnumerator interface. This allows readonly access to a collection then a collection that implements IEnumerable can be used with a for-each statement.
IEnumerator is the actual object used to perform the iterations. It controls moving from one object to the next in the list. Most of the time, IEnumerable & IEnumerator are used transparently as part of a foreach loop.
IEnumerable- It is an Interface and Exposes the enumerator, which supports a simple iteration over a collection of a specified type. Enumerable- It is a class and Provides a set of static methods for querying objects that implement IEnumerable.
The two interfaces each represent very different concepts. IEnumerable<T>
is something that "allows enumeration", where IEnumerator<T>
is the representation of the enumeration itself.
If you were to merge these together, it would be impossible to enumerate a single collection more than once at the same time (without some other mechanism in place). For example, two threads doing a foreach
over an array would no longer work, where that is perfectly acceptable in the current design.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With