You have to be aware that there are two kinds of LINQ statements:
- those that return
IEnumerable<...>
(or IQueryable)
- and those that don't.
The first group will only return an object that contains everything that is needed to enumerate the elements: get the first element of the sequence, and once you've got one, you can get the next one, until there are no more left.
Note: by creating this enumerable object, you haven't enumerated it yet.
The second group, the LINQ functions that don't return IEnumerable<...>
are the ones that will actually start enumerating: ToList
, ToDictionary
, FirstOrDefault
, Count
, Max
, Any
.
These function use the input IEnumerable
to call GetEnumerator()
and repeatedly call MoveNext()
until they know the return value. Quite often the complete sequence needs to be enumerated, sometimes only a few of them.
For example:
public static bool Any<TSource>(this IEnumerable<Tsource> source)
{
if (source == null) throw new ArgumentNullException(...);
IEnumerator<TSource> enumrator = source.GetEnumerator();
bool containsAnyElement = enumerator.MoveNext();
// no need to check the rest of the sequence, I already know the result:
return containsAnyElement;
}
Back to your question
Your code creates an IEnumerable<...>
It is similar to:
IEnumerable<RestrictionDto> restrictions = Employer.Restrictions
.Select(restriction => new RescrictionDto(restriction));
In words: make an enumerable object, that, when enumerated, will return one new object RestrictionDto per MoveNext that is called on the enumerator, for every restriction in the enumerable sequence Employer.Restrictions.
So you have created the Enumerable object, but you haven't enumerated over it yet.
Try the following, your debugger will show you that your RestrictionDtos are actally created:
var list = restrictions.ToList();
bool restrictionsAvailable = restrictions.Any();
var firstRestriction = restrictions.FirsOrDefault();
int numberOfRestrictions = restrictions.Count();
foreach (var restiction in restrictions)
{
...
}
They will all internally do something similar to the following:
var enumerator = restrictions.GetEnumerator();
while(enumerator.MoveNext())
{ // there are still restrictions left
RestrictionDto restriction = enumerator.Current;
// do something with this restriction
}