Search code examples
c#linqienumerableenumerable

Performance of IEnumerable


I have this code

List<int> items = new List<int>() { 1, 2, 3, 4, 5, 6, 7, 8, 9, 0 };
//calculation is not being executed until "even" is used
IEnumerable<int> even = items.Where(x => x % 2 == 0);   

DoStuff1(even);
DoStuff2(even);
DoStuff3(even);

I've read this answer https://stackoverflow.com/a/3628705/6887468 and it says

When you use IEnumerable, you give the compiler a chance to defer work until later, possibly optimizing along the way. If you use ToList() you force the compiler to reify the results right away.

Now is this calculation (in my example x % 2 == 0) being executed for each call of DoStuff() or is this somehow hold in the Memory?


Solution

  • executed for each call of DoStuff() or is this somehow hold in the Memory?

    It is not by itself held in memory so the following is sometimes a worthwhile optimization:

    IEnumerable<int> even = items.Where(x => x % 2 == 0);   
    even = even.ToList();  // now it is held in memory
    DoStuff1(even);
    DoStuff2(even);
    DoStuff3(even);
    

    Whether you want the ToList() depends on what DoStuff() does, how big the source list is vs the filtered list, how expensive the enumeration, etc.

    Note that when items was a little longer and all the DoStuff methods had a main loop like foreach(var item in items.Take(3)) then the ToList() in the main method would be an expensive de-optimization.