以下计划
static IEnumerable<Action> Create()
{
foreach (var i in Enumerable.Range(0, 2))
{
yield return () => { Console.Write(i); };
}
}
static void Main(string[] args)
{
foreach (var func in Create())
{
func();
}
Console.ReadLine();
}
OUPUTS
01
这个程序
static event Action SomethingHappened;
static void Register()
{
foreach (var i in Enumerable.Range(0, 2))
{
SomethingHappened += () => { Console.Write(i); };
}
}
static void Main(string[] args)
{
Register();
SomethingHappened();
Console.ReadLine();
}
输出
11
为什么会这样?如何使程序2输出01
?
答案 0 :(得分:3)
您正在捕获lambda表达式中的循环变量。这意味着当委托最终被调用时,它将使用变量的最新值...它将始终为1.试试这个:
foreach (var i in Enumerable.Range(0, 2))
{
int copy = i;
SomethingHappened += () => { Console.Write(copy); };
}
...然后阅读Eric Lippert's blog post。
答案 1 :(得分:1)
在第二个程序中,变量i
由lambda捕获。要获得正确的行为,请在lambda中使用它之前制作本地副本。例如。
foreach (var i in Enumerable.Range(0, 2))
{
var local = i;
SomethingHappened += () => { Console.Write(local); };
}