Java需要闭包吗?
我最近一直在阅读很多关于可能支持闭包的Java的下一个版本。我觉得我对什么是闭包有了相当坚定的把握,但是我想不出一个坚实的例子来说明它们如何使面向对象语言“更好”。任何人都可以给我一个特定的用例,其中需要一个闭包(甚至首选)?
我最近一直在阅读很多关于可能支持闭包的Java的下一个版本。我觉得我对什么是闭包有了相当坚定的把握,但是我想不出一个坚实的例子来说明它们如何使面向对象语言“更好”。任何人都可以给我一个特定的用例,其中需要一个闭包(甚至首选)?
作为一名Lisp程序员,我希望Java社区能够理解以下区别:作为对象的函数与作为闭包的函数。
a) 函数可以是命名的,也可以是匿名的。但它们也可以成为自己的对象。这允许函数作为参数传递,从函数返回或存储在数据结构中。这意味着函数是编程语言中的第一类对象。
匿名函数不会给语言增加太多,它们只是允许您以更短的方式编写函数。
b) 闭包是函数加上绑定环境。闭包可以向下传递(作为参数)或向上返回(作为返回值)。这允许函数引用其环境的变量,即使周围的代码不再处于活动状态。
如果你有某种语言的a),那么问题就来了,该如何处理b)?有些语言有a),但没有b)。在函数式编程世界中,a)(函数)和b(作为闭包的函数)现在是常态。Smalltalk在很长一段时间内都有a)(块是匿名函数),但后来Smalltalk的一些方言增加了对b)(块作为闭包)的支持。
你可以想象,如果你在语言中添加函数和闭包,你会得到一个稍微不同的编程模型。
从实用的角度来看,匿名函数添加了一些简短的表示法,您可以在其中传递或调用函数。这可能是一件好事。
例如,闭包(函数加绑定)允许您创建一个可以访问某些变量(例如计数器值)的函数。现在,您可以将该函数存储在对象中,访问它并调用它。函数对象的上下文现在不仅是它有权访问的对象,而且是它通过绑定可以访问的变量。这也很有用,但你可以看到变量绑定与对象变量的访问现在是一个问题:什么时候应该是词法变量(可以在闭包中访问),什么时候应该是某个对象(插槽)的变量。什么时候某物应该是闭包还是对象?您可以通过类似的方式同时使用两者。对于学习 Scheme(Lisp 方言)的学生来说,一个常见的编程练习是使用闭包编写一个简单的对象系统。
结果是更复杂的编程语言和更复杂的运行时模型。太复杂了?
它们不会使面向对象的语言变得更好。它们使实用语言更加实用。
如果你正在用OO锤子来解决问题 - 将所有内容表示为对象之间的交互 - 那么闭包就没有意义。在基于类的OO语言中,封闭是烟雾弥漫的后室,在那里完成工作,但之后没有人谈论它。从概念上讲,这是令人憎恶的。
在实践中,它非常方便。我真的不想定义一种新型的对象来保存上下文,为它建立“do stuff”方法,实例化它,并填充上下文......我只想告诉编译器,“看,看看我现在可以访问什么?这就是我想要的上下文,这是我想使用它的代码 - 为我坚持这个“直到我需要它”。
很棒的东西。