C#中的Lambdaexpression式是否closures?
lambdaexpression式(以及一定程度的匿名函数)是否被closures?
我对闭包的理解是,它们是被视为对象的函数,它似乎是匿名函数和Lambdaexpression式的精确表示。
把它们叫做闭包是正确的吗? 据我所知,由于口语方言,closures(或stream行),但它也是一个一般的编程术语?
感谢您的澄清,您可以提供!
lambda可以使用闭包实现,但它本身不一定是闭包。
闭包是“一个函数,以及该函数的非局部variables的引用环境”。
当你使用在方法外部定义的variables的lambdaexpression式时,lambda必须使用闭包来实现。 例如:
int i = 42; Action lambda = () => { Console.WriteLine(i); };
在这种情况下,编译器生成的方法必须能够访问在完全不同的作用域中定义的variables( i
)。 为了这个工作,它产生的方法是一个“函数与引用环境” – 基本上,它创build一个“闭包”来检索variables的访问。
不过,这个lambda:
Action lambda2 = () => { Console.WriteLine("Foo"); }
不依赖任何“引用环境”,因为它是一个完全包含的方法。 在这种情况下,编译器会生成一个正常的静态方法,并且根本不存在任何closures。
在这两种情况下,lambda创build一个delegate
(“函数对象”),但它只是在第一种情况下创build闭包,因为在所有情况下,lambda不一定需要“捕获”引用环境。
里德的回答是正确的。 我只是添加一些额外的细节:
-
lambdaexpression式和匿名方法都有闭包语义; 也就是说,他们“捕捉”了外部variables,延长了这些variables的生命周期。
-
匿名函数是我们使用的术语,指的是lambdaexpression式或匿名方法 。 是的,这是令人困惑的。 抱歉。 这是最好的,我们可以拿出来。
-
一个可以被当作对象的函数只是一个委托。 什么使一个lambda 闭包是它捕获它的外部variables。
-
转换为expression式树的lambdaexpression式也具有闭包语义,非常有趣。 正确的实施是一个痛苦的脖子,我告诉你!
-
即使“this”不是variables,“this”被认为是创build闭包的“外部variables”。
这是“封闭”而不是“clojure”。
这不是封闭的。 闭包基本上是一个函数的表示,以及该函数消耗的任何非局部variables。
从这个意义上说,lambdas并不是闭包,但是如果closures了任何variables,它们确实会导致编译器生成闭包。
如果在包含closures某些variables的lambda的程序集上使用ILDASM,则会在该程序集中看到一个编译器生成的类,它表示该函数以及已closures的那些variables。 这是closures。
当你说
被视为对象的函数,
这通常只是“函数对象”(在C#中我们会说“委托”),并且在函数式编程中很常见。
是。 闭包通常从外部范围捕获variables。 兰巴达斯可以做到这一点。 但是,如果你的lambda没有捕获任何东西,它不是一个闭包。