今天在编程中遇到了C#的匿名函数捕获局部变量的一些有趣的机制 …
先来看实例 d是一个委托(类似于C++的函数指针)
using System;
delegate void D(); // 声明一个委托: 用来存匿名函数
class Test
{
static D[] F()
{
D[] result = new D[3];
int x;
for (int i = 0; i < 3; i++)
{
x = i * 2 + 1;
result[i] = () => { Console.WriteLine(x); };
}
return result;
}
static void Main()
{
foreach (D d in F()) d();
}
}
其输出结果:
嗯? 为什么是5 5 5 不应该是 1 3 5吗?
… 我们再改进一下
再这个for循环中, 如果我们将x的声明放入for循环内部 . … 我们再看一下
using System;
delegate void D();// 声明一个委托: 用来存匿名函数
class Test
{
static D[] F()
{
D[] result = new D[3];
for (int i = 0; i < 3; i++)
{
int x = i * 2 + 1;
result[i] = () => { Console.WriteLine(x); };
}
return result;
}
static void Main()
{
foreach (D d in F()) d();
}
}
运行结果:
小结:
我们可以这样理解: 在实例一中匿名函数 捕获的是变量x , 而在实例一中’只有一个x’ ,而匿名函数其实是是捕获了x变量的内存地址 . 其经过三次循环后终值是 5 所以 匿名函数放回 5 其结果也就能解释了, 同理可得 : 在实例二中实例化了’三个x’ 所以匿名函数捕获了三块内存地址 , 所以其结果是 1, 3, 5