groovy开发环境搭建怎么开发一个Filter

7287人阅读
Groovy(3)
& & & 虽然一直在做C和C++,但只要涉及到能用Java或者.net开发的部分,还是很愿意用这两者进行开发的。虽然相比于C/C++,Java或.net的灵活性小了一些,但后者开发的效率真的是相当高,而且写起来也不会像C/C++那样让人郁闷。
& & & 这两年C#的发展可谓是精彩,Microsoft真不愧是最牛X的拿来主义公司,C#结合了多种语言的优点,写代码相当流畅,特别是C#描述中间件和API时可选的表现方法更多,对于类库使用者的要求更低,真的很不错。
& & & 当然,相比Phyton、Ruby或者Javascript这类脚本,任何强类型语言都显得不那么灵活,就好比PHP能提供比C语言更多的语言特性,包括闭包这样强大的功能。C#能以一种强类型语言做到相当多的动态语言特性,真是很了不起。对应Java,这两年发展的真的很慢,最新版本的JDK 7,也不过是增加了.net framework 2.0中几个常用功能,和.net framework 4相比依然相差很远。Java上有Spring等如此强大的API,语言本身却简单的近乎粗陋,真是不好说。
& & & 有人说Java就应该是这样的,就应该用getter/setter而不用=运算符,就应该不停的throws,就应该用一大票的interface,就应该不能自定义值类型……但我总觉得,开发人员喜欢什么样的设计模式都不能成为语言本身不提供该功能的理由。
& & & 否则,Groovy为什么会出现呢?
& & & 不吐槽了,既然Java上诞生了Groovy,这门语法甜的发腻的语言就肯定会让很多人喜欢它!虽然Groovy目前还存在效率方面的问题,它甚至比Javascript更慢,但Groovy毕竟是依赖于Java的,毕竟是和Java无缝挂接的,毕竟具备Java, Javascript, Phython, Ruby等等语言的优点,所以我估计谁也不能阻止Groovy的前进了!
&1、配置Groovy开发环境
& & & 由于Groovy是基于JDK的,所以安装Groovy之前肯定要安装JDK了,从可以下载到最新的JDK,写这篇文章时,JDK已经更新到JDK
7u2了,下载安装包安装即可。
& & & Groovy的安装挺简单的,基本上和JDK的安装差不多,从下载Groovy的GDK环境的安装包Windows-Installer(应该是1.8版本了),直接安装就可以了;如果下载的是zip版本,则按照如下步骤设置即可:
将zip包解压到随便那个目录中,如d:\devtools\groovy1.8.4设置环境变量GROOVY_HOME,值为放置解压文件的目录,如d:\devtools\groovy1.8.4增加环境变量path,指向%GROOVY_HOME%\bin
& & & 接下来就可以在Groovy控制台中编写脚本了,在Windows控制台(cmd)下输入groovyconsole命令进入groovy控制台,在里面输入代码 println &HelloWorld&回车,按组合键CTRL+R就可以看到运行结果了。
& & & 当然,这是Groovy自带的最基本的开发工具,很不实用,对于Groovy,NetBeans,IntelliJ IDEA等开发环境都提供了完善的支持,eclipse也提供了对应的插件。这里主要说一下eclipse中安装插件的办法。
到上下载最新版本的eclipse,目前是3.7.1版本,下载后解压到任意目录即可运行;
打开eclipse,选择菜单项“Help-&Install New Software”,再打开的对话框中按下Add按钮,在其中输入网址后确定;
& & & & & & & & & & 等上一会儿,直到eclipse从网上找到找到要安装的包,此时把要安装的包前面的复选框选中(全选即可),点击Finish按钮即可开始安装
& & & & & & 其实我试了几次在线安装,都是安装到一半的时候由于神奇的未知网络原因,安装中断,所以最终我使用的是离线安装的办法:
从下载离线安装包,注意,直接下载速度不会超过1kbps,请各位同学自行寻找访问伟大祖国以外神奇网站的具体方法,我使用GoAgent,可以在10Mbps的带宽上达到200多bps的下载;
注意下载的这个安装包不能使用eclipse传统的插件安装方式(内含Groovy编译器),无论覆盖方式、Link文件方式还是dropins目录方式都玩不转,还得使用eclipse的”Help-&nstall New Software“方式安装;当打开上述图2的对话框后,不要填写网址,按下Achieve按钮,在出现的对话框中填写下载文件的路径和文件名
点击OK,继续安装即可
& & & 插件安装后重启eclipse,在新建项目中应该包含了Groovy Project和Groovy Class,这就表示Groovy插件安装成功,可以利用eclipse开发Groovy应用程序了!
参考知识库
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
访问:230187次
积分:2947
积分:2947
排名:第8085名
原创:51篇
评论:92条
(2)(4)(1)(1)(1)(1)(1)(2)(3)(1)(1)(4)(1)(1)(1)(3)(1)(13)(8)(1)(9)微信公众号
Groovy元编程为您提供常见问题的简单解决方案
Java 下一代语言扩展现有的类和其他构件的方法有很多,前两期 Java 下一代 文章探讨了其中的一些方法。在本期文章中,我将继续该探索,仔细查看在多种上下文中实现扩展的 Groovy 元编程技术。
在 &没有继承性的扩展,第 1 部分& 中,在讨论使用类别类 和 ExpandoMetaClass 作为将新行为 &应用于& 现有类的机制时,我偶然接触了一些 Groovy 元编程特性。Groovy 中的元编程特性更深入一些:它们使得集成 Java 代码变得更容易,而且可以帮助您采用比 Java 语言更简洁的方式来执行常见任务。
接口强制转换(Interface coercion)
接口是 Java 语言中常​​见的语义重用机制。尝试以简洁的方式集成 Java 代码的其他语言应该提供简单的方法来具体化接口。在 Groovy 中,类可以通过传统的 Java 方式来扩展接口。但是,Groovy 还使得在方便时轻松地将闭包和映射强制转换成接口实例变得很容易。
单一方法强制转换
清单 1 中的 Java 代码示例使用 FilenameFilter 接口来定位文件:
清单 1. 在 Java 中使用 FilenameFilter 接口列出文件
import java.io.F
import java.io.FilenameF
public class ListDirectories {
public String[] listDirectoryNames(String root) {
return new File(root).list(new FilenameFilter() {
public boolean accept(File dir, String name) {
return new File(name).isDirectory();
在 清单 1 中,我创建了一个新的匿名内部类,它覆盖了指定过滤条件的 accept() 方法。在 Groovy 中,我可以跳过创建一个新类的步骤,只将一个闭包强制转换成接口,如清单 2 所示:
清单 2. 在 Groovy 中通过使用闭包强制转换来模拟 FilenameFilter 接口
new File('.').list(
{ File dir, String name -& new File(name).isDirectory() }
as FilenameFilter).each { println it }
在 清单 2 中,list() 方法想使用一个 FilenameFilter 实例作为参数。但我却创建了一个与接口的 accept() 签名相匹配的闭包,并在闭包的正文中实现接口的功能。在定义了闭包之后,我通过调用 as FilenameFilter 将闭包强制转换成适当的 FilenameFilter 实例。Groovy 的 as 运算符将闭包具体化为一个实现接口的类。该技术对于单一方法接口非常适用,因为方法和闭包之间存在一个自然映射。
对于指定多个方法的接口,被具体化的类为每个方法都调用了相同的闭包块。但只在极少数情况下,用相同代码来处理所有方法调用才是合理的。当您需要使用多个方法时,可以使用包含方法名称/闭包对的 Map,而不是使用单一的闭包。
在 Groovy 中,还可以使用映射来表示接口。映射的键是代表方法名称的字符串,键值是实现方法行为的代码块。清单 3 中的示例将一个映射具体化为一个 Iterator 实例:
清单 3. 在 Groovy 中使用映射来具体化接口
h = [hasNext:{ h.i & 0 }, next:{h.i--}]
def iterator = h as Iterator
while (iterator.hasNext())
print iterator.next() + &, &
// 10, 9, 8, 7, 6, 5, 4, 3, 2, 1,
在 清单 3 中,我创建了一个映射 (h),它包括 hasNext 和 next 键,以及它们各自的代码块。Groovy 假设映射键是字符串,所以我不需要用引号来包围该键。在每个代码块中,我用点符号 (h.i) 引用 h 映射的第三个键 (i)。这个点符号借鉴自人们所熟悉的对象语法,它是 Groovy 中的另一个语法糖示例。在使用 h 作为一个迭代器之前,不会执行代码块,我必须首先确保 i 有一个值,然后再使用 h 作为一个迭代器。我用 h.i = 10 设置 i 的值。然后,我将 h 选作一个 Iterator,并使用从 10 开始的整数集合。
通过使得映射能够动态地作为接口实例,Groovy 极大地减少了 Java 语言有时导致的一些语法问题。此特性很好地说明了 Java 下一代语言如何改进开发人员的体验。
ExpandoMetaClass
正如我在 &没有继承性的扩展,第 1 部分& 中所述,您可以使用 ExpandoMetaClass 将新方法添加到类 & 包括核心类,比如 Object 和 String。ExpandoMetaClass 对于其他一些用途也是有用的,比如将方法添加到对象实例,以及改善异常处理。
将方法添加到对象和从对象中删除方法
从将行为附加到类的那一刻起,使用 ExpandoMetaClass 对类执行的更改就会在全局生效。普遍性是这种方法的优势 & 这并不奇怪,因为这种扩张机制源自 Grails Web 框架(请参阅 参考资料)的创建。Grails 依赖于对核心类的全局变更。但有时您需要在不影响所有实例的情况下,采用有限的方式为一个类添加语义。对于这些情况,Groovy 提供了可以与对象的元类实例 交互的方式。例如,您可以将方法只添加到某个特定的对象实例,如清单 4 所示:
清单 4. 将行为附加到一个对象实例
def list = new ArrayList()
list.metaClass.randomize = { -&
Collections.shuffle(delegate)
list && 1 && 2 && 3 && 4
println list.randomize() // [2, 1, 4, 3]
println list
// [2, 1, 4, 3]
在 清单 4 中,我创建了 ArrayList 的一个实例 (list)。然后我访问了该实例以懒惰方式实例化的 metaClass 属性。我添加了一个方法 (randomize()),该方法返回执行 shuffle 之后的集合。在元类的方法声明中,delegate 代表对象实例。
不过,我的 randomize() 方法改变了底层集合,因为 shuffle() 是一个变异调用。在 清单 4 的第二行输出中,请注意,该集合被永久性地更改为新的随机顺序。令人高兴的是,通过解决这些问题,可以轻松地改变 Collections.shuffle() 等内置方法的默认行为。例如,清单 5 中的 random 属性是对 清单 4 的 randomize() 方法的改进:
清单 5. 改进不良语义
def list2 = new ArrayList()
list2.metaClass.getRandom = { -&
def l = new ArrayList(delegate)
Collections.shuffle(l)
list2 && 1 && 2 && 3 && 4
println list2.random // [4, 1, 3, 2]
println list2
// [1, 2, 3, 4]
在 清单 5 中,我让 getRandom() 方法的正文先复制列表,然后再改变它,这样就可以让原始列表保持不变。通过使用 Groovy 的命名约定,将属性自动映射到 get 和 set 方法,我让 random 也成为一个属性,而不是一个方法。
使用属性技术来减少额外的括号干扰,导致了最近在 Groovy 中将方法链接在一起的方式的改变。该语言的版本 1.8 引入了命令链 的概念,支持创建更流畅的域特定语言(DSL)。DSL 通常扩充现有的类或对象实例来添加特殊的行为。
Ruby 和类似语言中的一个流行特性是混合。混合让您能够不使用继承,而是将新的方法和字段添加到现有的层次结构中。Groovy 支持混合特性,如清单 6 所示:
清单 6. 使用混合特性来附加行为
class ListUtils {
static randomize(List list) {
def l = new ArrayList(delegate)
Collections.shuffle(l)
List.metaClass.mixin ListUtils
在 清单 6 中,我创建了一个辅助类 (ListUtils) 并为其添加了一个 randomize() 方法。在最后一行中,我将 ListUtils 类与 java.util.List 混合在一起,让我的 randomize() 方法对 java.util.List 可用。也可以在对象实例中使用 mixin。这种技术通过将变更限制到某个单独的代码构件来帮助执行调试和跟踪,所以,对于将行为附加到类而言,这是最好的方式。
其他类似的新闻
其他相关的新闻
大家感兴趣的内容
小伙伴最爱的新闻
小伙伴还关注了以下信息
小伙伴关注的焦点
小伙伴都在关注的热门词
Copyright (C) 2006- Inc. All Rights Reserved
孝感风信信息技术有限公司 ● 版权所有IBM Bluemix
点击按钮,开始云上的开发!
developerWorks 社区
凭借 Groovy,元编程 (metaprogramming) 和函数式编程形成了一个强有力的组合。了解元编程如何支持您为 Integer 数据类型添加方法,从而使您能够利用 Groovy 的内置函数式特性。学习如何使用元编程将 Functional Java™ 框架的丰富函数式特性集无缝地整合到 Groovy 中。
, 软件架构师, ThoughtWorks Inc.
Neal Ford 是一家全球性 IT 咨询公司 ThoughtWorks 的软件架构师和 Meme Wrangler。他的工作还包括设计和开发应用程序、教材、杂志文章、课件和视频/DVD 演示,而且他是各种技术书籍的作者或编辑,包括最近的新书 。他主要的工作重心是设计和构建大型企业应用程序。他还是全球开发人员会议上的国际知名演说家。请访问他的 。
中,我介绍了 Groovy 中一些已有的函数式特性,以及如何使用 Groovy 的原语来构建无限列表 (infinite list)。在这一部分中,我会继续探讨函数式编程和 Groovy 的交集。
Groovy 是一种多范式语言:它支持面向对象、元编程和函数式编程风格,这些风格几乎都是彼此正交的(参见侧边栏上的 )。元编程支持您为语言及其核心库添加特性。通过将元编程与函数式编程结合在一起,您可以将自己的代码变得更加函数化,或者在 Groovy 中增加第三方函数库,让它们发挥更大的作用。我将首先介绍 Groovy 的 ExpandoMetaClass 添加类的方式,然后介绍如何使用这一机制将 Functional Java 库(参见 )整合到 Groovy 中。
通过 ExpandoMetaClass 使用开放类
Groovy 的一个更加强大的功能是开放类(open class),即重新打开现有类来增加或是删除其功能的能力。这与子类化不同,子类化是从一个现有类中派生出新的类。开放类允许您重新打开一个类(比如 String)并为它添加新的方法。测试库大量使用这一功能来为 Object 添加验证方法,这样,应用程序中的所有类现在都有了验证方法。
Groovy 有两种开放类技术:categories 和 ExpandoMetaClass(参阅 )。这两种技术都适用于本示例;我选择 ExpandoMetaClass 是因为它的语法更简单一些。如果您一直在关注本系列的话,那么您可能熟悉我一直在使用的数字分类示例。使用 Groovy 编写的完整的 Classifier,如清单 1 所示,使用了 Groovy 自己的函数式构造:
清单 1. 使用 Groovy 编写的完整的 Classifierclass Classifier {
def static isFactor(number, potential) {
number % potential == 0;
def static factorsOf(number) {
(1..number).findAll { i -& isFactor(number, i) }
def static sumOfFactors(number) {
factorsOf(number).inject(0, {i, j -& i + j})
def static isPerfect(number) {
sumOfFactors(number) == 2 * number
def static isAbundant(number) {
sumOfFactors(number) & 2 * number
def static isDeficient(number) {
sumOfFactors(number) & 2 * number
static def nextPerfectNumberFrom(n) {
while (!isPerfect(++n));
如果有任何关于在这一版本中如何实现方法的问题,请参考之前的文章(具体地讲,是 "" 和 "")。要使用此类的方法,我可以按照 “正常的” 的函数式方法来调用这些方法:Classifier.isPerfect(7)。但是,在使用元编程时,我可以直接将这些方法 “捆绑” 到 Integer 类中,并允许 “询问” 某个数字是属于哪个类别的。
要将这些方法添加到 Integer 类,我访问该类的 metaClass 属性,该属性是 Groovy 为每个类预定义好的,如清单 2 所示:
清单 2. 为 Integer 添加分类Integer.metaClass.isPerfect = {-&
Classifier.isPerfect(delegate)
Integer.metaClass.isAbundant = {-&
Classifier.isAbundant(delegate)
Integer.metaClass.isDeficient = {-&
Classifier.isDeficient(delegate)
中,我为 Integer 添加了三个 Classifier 方法。现在,Groovy 中的所有整数都有三个方法。(Groovy 没有原始数据类型的概念;甚至 Groovy 中的常数都是使用 Integer 作为基础数据类型。)在定义每个方法的代码块中,我访问了预定义的 delegate 参数,该参数代表了调用类方法的对象的值。
在初始化了我的元编程方法之后(参阅侧边栏上的 ),就可以 “询问” 数字的类别了,如清单 3 所示:
清单 3. 使用元编程对数字进行分类@Test
void metaclass_classifiers() {
def num = 28
assertTrue num.isPerfect()
assertTrue 7.isDeficient()
assertTrue 6.isPerfect()
assertTrue 12.isAbundant()
} 说明了新添加的方法在变量和常量上都能够正常工作。现在为 Integer 添加一个返回特定数字的分类的方法已经不是什么难事了,也许和枚举一样简单。
为现有类添加新方法本身并不是特别的 “函数化”,尽管它们调用的代码有着强烈的函数式风格。但是,无缝添加方法的能力使整合到第三方库(比如 Functional Java 库)中变得非常简单,并添加了一些重要的函数式特性。我曾在
中使用 Functional Java 库实现了数字分类器,我会在这里使用它来创建一个无限的完全数字流。
使用元编程映射数据类型
Groovy 本质上是 Java 的一个特殊化版本,所以引入 Functional Java 等第三方库并非难事。但是,我可以通过在数据类型之间执行一些元编程映射来深入整合这些库,从而使接缝变得不那么明显。Groovy 有一种原生的闭包类型(使用 Closure 类)。Functional Java 还没有奢侈到使用闭包的地步(它依赖于 Java 5 的语法),这就迫使作者使用泛型和包含了一个 f() 方法的泛类 F。利用 Groovy 的 ExpandoMetaClass,我可以通过在方法和闭包之间创建映射方法来解决这两者的类型差异问题。
我打算添加的类是 Functional Java 的 Stream 类,该类提供了无限列表的一个抽象。我希望传递 Groovy 的闭包来代替 Functional Java 的 F 实例,因此为 Stream 类添加了许多的方法,以便将闭包映射到 F 的 f() 方法,如清单 4 所示:
清单 4. 使用 ExpandoMetaClass 映射数据类型Stream.metaClass.filter = { c -& delegate.filter(c as fj.F) }
Stream.metaClass.filter = { Closure c -& delegate.filter(c as fj.F) }
Stream.metaClass.getAt = { n -& delegate.index(n) }
Stream.metaClass.getAt = { Range r -& r.collect { delegate.index(it) } }
第一行在 Stream 上创建了一个接受闭包(代码块的 c 参数)的 filter() 方法。(注释的)第二行与第一行相同,但是添加了 Closure 的类型声明;这不会影响 Groovy 的代码执行方式,但用作文档的说明倒是不错的。代码块的主体内容调用 Stream 预先就存在的 filter() 方法,将 Groovy 闭包映射到 Functional Java 的 fj.F 类。我使用 Groovy 的神奇的 as 运算符来执行映射。
Groovy 的 as 运算符将闭包强制加入到接口定义中,允许闭包方法映射到接口所需的方法。请考虑一下清单 5 中的代码:
清单 5. 使用 as 来创建轻量级的迭代器def h = [hasNext : { println "hasNext called"; return true},
next : {println "next called"}] as Iterator
h.hasNext()
println "h instanceof Iterator? " + (h instanceof Iterator)
中的示例中,我创建了一个有着两个 “名称-值” 对的哈希表。每个名称都是一个字符串(Groovy 不要求使用双引号来分隔哈希键,因为它们默认就是字符串),值则是代码块。as 运算符将这一哈希表映射到 Iterator 接口,该接口要求必须要有 hasNext() 和 next() 方法。一旦执行了映射,就可以将哈希表作为一个迭代器来使用;清单中的最后一行输出 true。在有单一方法的接口的情况下,或是在希望接口中的所有方法都映射成单个闭包的情况下,我可以省去哈希表,直接使用 as 将闭包映射到某个函数上。回过头来看一下
中的第一行,我将传递进来的闭包映射到只有一个方法的 F 类。
中,我必须映射两个 getAt 方法(一个接受数字而另一个接受一个 Range),因为 filter 需要用到这些方法来进行操作。使用这一新添加的 Stream,我可以使用一个无限序列来进行相关操作,如清单 6 所示:
清单 6. 在 Groovy 中使用无限的 Functional Java 流@Test
void adding_methods_to_fj_classes() {
def evens = Stream.range(0).filter { it % 2 == 0 }
assertTrue(evens.take(5).asList() == [0, 2, 4, 6, 8])
assertTrue(evens[3..6] == [6, 8, 10, 12])
中,我创建了偶数的一个无限列表,从 0 开始,使用一个闭包块来过滤它们。您不能一下子取得无限序列中的所有元素,因此必须要使用 take() 获取所需数目的元素。 的余下部分内容给出了测试断言,这些断言说明了该流的工作方式。
Groovy 中的无限流
中,我介绍了如何在 Groovy 中实现一个无限的惰性列表。与其手动创建该列表,为什么不依靠 Functional Java 的无限序列来实现此操作呢?
为了创建一个由完全数构成的无限 Stream,我需要其他两种 Stream 方法映射来了解 Groovy 闭包,如清单 7 所示:清单 7. 完全数字流的其他两种方法映射Stream.metaClass.asList = { delegate.toCollection().asList() }
Stream.metaClass.static.cons = { head, closure -& delegate.cons(head, closure as fj.P1) }
// Stream.metaClass.static.cons =
{ head, Closure c -& delegate.cons(head, ['_1':c] as fj.P1)}
中,我创建了一个 asList() 转换方法,使将 Functional Java 流转换为列表变得非常简单。我实现的另一种方法是重载 cons(),该方法是构建新列表的 Stream 上的方法。当创建无限列表时,数据结构通常包含首个元素和一个作为列表尾部的闭包块,该闭包块在调用时生成下一个元素。就我的 Groovy 完全数字流而言,我需要 Functional Java 知道 cons() 可以接受一个 Groovy 闭包。
如果我使用 as 来将单个闭包映射到有着多个方法的接口上的话,则在我调用接口中的任何方法时,都会执行该闭包。对于 Functional Java 类来说,这种简单映射类型在大多数情况下都是可行的。但是,少数几个方法要求使用 fj.P1 方法而不是 fj.F 方法。在其中的某些情况下,我仍然能够使用一个简单的映射来逃脱这种限制,因为下游的方法并不依赖 P1 的其他任何方法。在有着更高精确性要求的情况下,我可能不得不使用
的注释行中给出的更复杂的映射,该做法必须使用 _1() 方法来创建一个映射到闭包上的哈希表。尽管该方法看起来有些奇怪,但它是 fj.P1 类的一个标准方法,返回首个元素。
一旦在 Stream 上拥有了元编程方式映射的方法,我就可以使用
中的 Classifier 来创建一个无限的完全数字流,如清单 8 所示:
清单 8. 使用 Functional Java 和 Groovy 实现的完全数的无限流import static fj.data.Stream.cons
import static com.nealford.ft.metafunctionaljava.Classifier.nextPerfectNumberFrom
def perfectNumbers(num) {
cons(nextPerfectNumberFrom(num), { perfectNumbers(nextPerfectNumberFrom(num))})
void infinite_stream_of_perfect_nums_using_functional_java() {
assertEquals([6, 28, 496], perfectNumbers(1).take(3).asList())
我使用静态导入的方式导入了 Functional Java 的 cons() 和我自己的 nextPerfectNumberFrom() 方法,从而让代码变得更简洁一些。perfectNumbers() 方法返回一个无限的完全数序列,其做法是预先附加(没错,cons 是一个动词)初始数字之后的首个完全数字,然后加入一个闭包块来作为第二个元素。该闭包块返回的无限序列以下一个数字作为头部,以计算另一个完全数字的闭包作为尾部。在测试代码中,我从 1 开始生成一个完全数字串,获取接下来的三个完全数字,并断言它们和列表中列出的数字相吻合。
当开发人员在考虑使用元编程时,他们通常只会考虑自己的代码,而不会想到往其他人的代码中添加内容。Groovy 不仅允许我往诸如 Integer 一类的内置类中添加新的方法,而且允许我往 Functional Java 一类的第三方库中添加新方法。将元编程和函数式编程组合起来,只需非常少的代码就可以实现非常强大的功能,这种组合创造出了一种无缝的链接。
尽管我可以在 Groovy 中直接调用 Functional Java 类,但相比于真正的闭包,许多库构建块都显得过于蠢笨。在使用元编程时,我可以通过映射 Functional Java 方法,让它们理解便利的 Groovy 数据结构,从而使双方都获得了最好的效用。在 Java 定义原生闭包类型之前,开发人员常常需要在一些语言类型之间执行这样的多语言映射:在字节码级别上,Groovy 闭包和 Scala 闭包并不是一回事。在 Java 中建立一个标准会将这些对话向下推至运行时中,并会消除我在本文中展示的这一类映射的需要。但是,在此之前,这一功能会创建简洁却强大的代码。
在下一部分中,我会谈到一些优化措施:函数式编程允许运行时使用记忆式 (memoization) 的 Groovy 创建和运行示例。
参考资料 (Neal Ford,O'Reilly Media,2008 年):Neal Ford 的新书讨论了帮助您提升编程效率的工具和实践。:Functional Java 框架为 Java 增添了许多函数式的语言构造。
""(Scott Davis,developerWorks,2009 年 6 月):在
系列的相关部分中了解有关 Groovy 元编程的更多信息。"" (Brian Goetz,developerWorks,2011 年 7 月):了解 lambda 表达式(闭包)背后的设计考虑因素,适用于 Java SE 8 中的新语言功能。
浏览 ,阅读有关这些主题和其他技术主题的图书。
:这里有数百篇关于 Java 编程各个方面的文章。
:下载 Functional Java 框架。以最适合您的方式
:下载产品试用版,在线试用产品,在云环境中使用产品,或者在
中花一些时间来学习如何高效地实现面向服务的架构。加入 。查看开发人员推动的博客、论坛、组和 wikis,并与其他 developerWorks 用户交流。
developerWorks: 登录
标有星(*)号的字段是必填字段。
保持登录。
单击提交则表示您同意developerWorks 的条款和条件。 查看条款和条件。
在您首次登录 developerWorks 时,会为您创建一份个人概要。您的个人概要中的信息(您的姓名、国家/地区,以及公司名称)是公开显示的,而且会随着您发布的任何内容一起显示,除非您选择隐藏您的公司名称。您可以随时更新您的 IBM 帐户。
所有提交的信息确保安全。
选择您的昵称
当您初次登录到 developerWorks 时,将会为您创建一份概要信息,您需要指定一个昵称。您的昵称将和您在 developerWorks 发布的内容显示在一起。昵称长度在 3 至 31 个字符之间。
您的昵称在 developerWorks 社区中必须是唯一的,并且出于隐私保护的原因,不能是您的电子邮件地址。
标有星(*)号的字段是必填字段。
(昵称长度在 3 至 31 个字符之间)
单击提交则表示您同意developerWorks 的条款和条件。 .
所有提交的信息确保安全。
文章、教程、演示,帮助您构建、部署和管理云应用。
立即加入来自 IBM 的专业 IT 社交网络。
为灾难恢复构建应用,赢取现金大奖。
static.content.url=/developerworks/js/artrating/SITE_ID=10Zone=Java technologyArticleID=793216ArticleTitle=函数式思维: Groovy 中的函数式特性,第 2 部分publish-date=

我要回帖

更多关于 groovy filter 的文章

 

随机推荐