I'm trying to understand the yield keyword better and I think I have a decent enough understanding of it so I ran some tests however I was surpised by the results.
If I run the below code I get the following output which shows that it loops over the whole range not just up to number 4.
public void DoIt()
{
Console.WriteLine("Method Call");
var results = GetData(Enumerable.Range(1, 10));
Console.WriteLine("LINQ");
var filtered = results.Where(x => x == 4);
Console.WriteLine("Start result loop");
foreach (var item in filtered)
{
Console.WriteLine("Item is " + item);
}
}
private IEnumerable<int> GetData(IEnumerable<int> Input)
{
foreach (int item in Input)
{
if (item % 2 == 0)
{
Console.WriteLine("Found " + item);
yield return item;
}
}
}
Output:
Method Call
LINQ
Start result loop
Found 2
Found 4
Item is 4
Found 6
Found 8
Found 10
If I run the below code it shows that it only gets to 4 and then stops.
public void DoIt()
{
Console.WriteLine("Method Call");
var results = GetData(Enumerable.Range(1, 10));
Console.WriteLine("Start result loop");
foreach (var item in results)
{
if (item == 4)
{
Console.WriteLine("Item is " + item);
break;
}
}
}
private IEnumerable<int> GetData(IEnumerable<int> Input)
{
foreach (int item in Input)
{
if (item % 2 == 0)
{
Console.WriteLine("Found " + item);
yield return item;
}
}
}
Output:
Method Call
Start result loop
Found 2
Found 4
Item is 4
I guess I'm not understading something but it looks as if LINQ is doing the opposite of what I expect it to do? I though LINQ used yield and deferred execution as well and I'd expect the results from the second set of code to be the same for the first set of code.
It does use deferred execution. LINQ Where
checks all the elements of the input enumerable, it doesn't stop when it gets to the first element found. That's what First
does.
Your first example would return the same as the second example if you changed Where
to First
, or if you removed the break
from the second example.
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