Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/.net/24.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 这还是个了结吗?_C#_.net_Function_Closures_Anonymous Methods - Fatal编程技术网

C# 这还是个了结吗?

C# 这还是个了结吗?,c#,.net,function,closures,anonymous-methods,C#,.net,Function,Closures,Anonymous Methods,testit()方法是一个闭包。aString已超出范围,但testit()仍可以在其上执行。testit2()使用的变量没有超出范围(mystring),但也没有传递到testit2()。testit2()是否被视为一个闭包 string mystring = "hello world"; Action testit = new Action(delegate { string aString = "in anon method"; Debug.WriteLine(aString); });

testit()方法是一个闭包。aString已超出范围,但testit()仍可以在其上执行。testit2()使用的变量没有超出范围(mystring),但也没有传递到testit2()。testit2()是否被视为一个闭包

string mystring = "hello world";
Action testit = new Action(delegate { string aString = "in anon method"; Debug.WriteLine(aString); });
testit();

//capture mystring.  Is this still a closure?
Action testit2 = new Action(delegate { Debug.WriteLine(mystring); });
//mystring is still in scope
testit2();

在第二个示例中,mystring可以在方法之外更新,这些更改将反映在testt2()中。这与普通方法不同,普通方法只能将mystring作为参数捕获。

这两个示例都是匿名函数。第二种方法使用闭包来捕获局部变量。变量相对于匿名函数的作用域生存期不影响是否创建闭包来使用它。只要变量在匿名函数外部定义并在内部使用,就会创建一个闭包

第一个匿名函数不使用本地状态,因此不需要闭包。它应该编译成一个静态方法


这是必要的,因为匿名函数可以超过当前函数的生存期。因此,必须捕获匿名函数中使用的所有局部变量,以便在以后执行委托。

闭包不捕获作用域中的值,而是捕获作用域的实际定义。因此,引用同一范围的任何其他代码段都可以修改其中的变量。

testit
并不像
testit2
那样是一个闭包——它只使用一个本地定义的变量,而不是“父”环境中的变量(例如
mystring


然而,我认为这两种方法都是闭包,因为它们能够从封闭的环境中捕获变量,这是由于匿名方法。

它们是匿名方法,而不是lambda表达式(无论如何,在C#术语中)。然而,lambda表达式和匿名方法都算作匿名函数。我觉得用软词挑剔术语很糟糕:)@Jon,挑剔是受欢迎的。又一次学习新事物的机会。我不知道匿名函数是这两种不同场景的通用术语。我已经习惯于到处叫他们lambda's了。但匿名函数更难键入;)这种闭包被称为“词汇闭包”——它捕获了词汇范围。谢谢。我在这里查看了您的示例:。计数器的定义与testit()定义aString一样。我相信这意味着你给出的例子不是闭包最有力的例子,这似乎是你为testit()所说的。@4thspace:不,再看一遍这个例子。计数器是在匿名方法之外定义的,更像mystring。