繁体   English   中英

C#5.0中捕获的闭包(循环变量)

[英]Captured Closure (Loop Variable) in C# 5.0

这在C#5.0中正常工作(按预期方式):

var actions = new List<Action>();
foreach (var i in Enumerable.Range(0, 10))
{
    actions.Add(() => Console.WriteLine(i));
}
foreach (var act in actions) act();

打印0到9.但是这个显示10次10​​次:

var actions = new List<Action>();
for (var i = 0; i < 10; i++)
{
    actions.Add(() => Console.WriteLine(i));
}
foreach (var act in actions) act();

问题:这是我们在5.0之前的C#版本中遇到的问题; 所以我们不得不使用一个循环局部占位符来进行闭包,它现在已经修复了 - 在C#5.0中 - 在“foreach”循环中。 但不是“for”循环!

这背后的原因是什么(也没有解决for循环的问题)?

这背后的原因是什么?

我会假设你的意思是“为什么它也没有改变for循环?”

答案是,对于for循环,现有的行为非常有意义。 如果你打破for循环:

  • 初始化
  • 条件
  • 迭代器
  • 身体

...然后循环大致是:

{
    initializer;
    while (condition)
    {
        body;
        iterator;
    }
}

(当然, iteratorcontinue;语句结束时执行除外。)

初始化部分逻辑上只发生一次,因此只有一个“变量实例化”完全符合逻辑。 此外,在循环的每次迭代中,变量没有自然的“初始”值 - 没有什么可以说for循环必须是在初始化程序中声明变量的形式,在条件中测试它并在其中修改它迭代器。 您期望像这样的循环做什么:

for (int i = 0, j = 10; i < j; i++)
{
    if (someCondition)
    {
        j++;
    }
    actions.Add(() => Console.WriteLine(i, j));
}

将它与foreach循环进行比较, 看起来你正在为每次迭代声明一个单独的变量。 哎呀,变量是只读的,这使得它奇怪地认为它是一个在迭代之间变化的变量。 foreach循环视为在每次迭代中声明一个新的只读变量,其值取自迭代器,这是完全合理的。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM