Does this linq query run on every iteration of the for-each loop?

自古美人都是妖i 提交于 2019-12-06 01:27:06

问题


In another question on SO I answered with code like the one below and got a comment that the LINQ-query probably was evaluated in every iteration of the for/each. Is that true?

I know that LINQ-querys does not executes before its items is evaluated so it seems possible that this way to iterate the result can make it run on every iteration?

Dim d = New Dictionary(Of String, String)()    
d.Add("Teststring", "Hello")    
d.Add("1TestString1", "World")    
d.Add("2TestString2", "Test")    

For Each i As String In From e In d Where e.Value.StartsWith("W") Select e.Key
    MsgBox("This key has a matching value:" & i)    
Next

回答1:


NO... in a foreach, the "GetEnumerator" is called only once (ever), and that is used going forward.

EDIT: I put a statement here about the result set being stored temporarily... that's only true for some cases... not this one, so I took it out.

EDIT: Please forgive this for being overly verbose... but I wanted to show you what is happening... so here's a Console app :)

using System;
using System.Collections.Generic;
using System.Linq;

namespace ConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            foreach (string item in MyCustomEnumerator()
                .Where(item => item.StartsWith("abc")))
            {
            Console.WriteLine(item);
            }
        }

        static IEnumerable<string> MyCustomEnumerator()
        {
            Console.WriteLine(DateTime.Now);

            yield return "abc1";

            Console.WriteLine(DateTime.Now);

            yield return "abc2";

            Console.WriteLine(DateTime.Now);

            yield return "abc3";

            Console.WriteLine(DateTime.Now);

            yield return "xxx";
        }
    }
}

EDIT: This will result in a DateTime, then abc1, then a DateTime, then abc2, then a DateTime, then abc3, then a DateTime.




回答2:


I believe that it will run the first time it is reached and produce an enumeration that has all the matching values. What you will actually get back is an enumerator for that enumeration.




回答3:


I looked up the FOR EACH...NEXT statement and it seems like Visual Basic evaluates the collection only once, before the loop begins, so it should not run the query on every iteration.

Number of Iterations. Visual Basic evaluates the collection only once, before the loop begins. If your statement block changes element or group, these changes do not affect the iteration of the loop.



来源:https://stackoverflow.com/questions/332864/does-this-linq-query-run-on-every-iteration-of-the-for-each-loop

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!