Groovy for 循环

估计for循环是使用得最广泛的循环类型了,在java中for循环比较难用,虽然使用过具有相似结构的开发语言的人们逐渐发现for循环容易使用,但是常常使用的for循环确没有好好 的设计,虽然传统的for循环语句是强大的,但它很少用来表述像集合这样的数据结构,groovy 具有这个简单性,这可能是groovy和java之间的最大不同吧。

Groovy允许这样的for循环:for (variable in iterable) { body }这里variable的类型是可选的,groovy的for循环遍历iterable,常常用到的iterable有 range/collections/map/array/iterator/enumeration,事实上,任何对象都可以是一个iterable, groovy为对象的遍历应用相同的逻辑,这在第八章进行描述。

如果循环体只有一句,那么花括号是可选的,列表6.9显示了一些例子。

例子(1)为i使用了现实的类型并且由于循环体只有一句话,所以没有花括号,这个循环用来生成一个字符串。

当使用集合类型时通常出现的for循环如(2)所示,再次感谢自动装箱,这种方式也适用于数组。

一个半排除的整数范围的循环如(3)显示,它与java相当的结构如下:[code]for (int i=0; i < exclusiveUpperBound; i++) { // Java !

//这里放置使用i的代码

}[/code]这是一个经典的for循环,在当前版本的groovy中不支持,以后的版本也许会支持(译者

注:在最新的1.6版本中已经支持了)。

例子(4)使例子(3)更加清晰,例子(3)不是groovy典型字符串处理风格,更多时 候groovy把字符串作为字符的集合进行处理
在一般对象上使用for循环将在9.1.3节进行描述,这节提供了一些非常强大的例子。

你可以使用for循环一行一行的输出一个文件的内容:[code]def file = new File(‘myFileName.t xt’)

for (line in file) println line[/code]或者打印匹配正则表达式的所有数字:[code]def matcher = ‘12xy3’=~/\d/

for (match in matcher) println match[/code]如果容器对象为null,那么将没有结果输出:for (x in null) println 'This will not be printed!'如果groovy通过任何方法都不能确定一个容器对象是iterab le,那么最好的解决方法是仅仅使用容器对象本身进行一次遍历:for (x in new Object()) println "Printed once for object $x"对象遍历使groovy的for循环成为一个优雅的控制结构,一个有效的对应方式是以闭包为参数调用对象上的遍历方法,比如使用Collection的each方法。

这两者的主要不同之处是for循环不是一个闭包!这意味做方法体是代码块:for (x in 0..9) { println x }但是这样用的循环体就是一个闭包了:code.each { println it }[/code]即使它们看起来相似,但它们在结构上时很不相同的。

一个闭包是一个对象,并且有你在第五章看到的所有特性,它可以在不同的地方就行构建然后传递给each方法。

for循环的循环体,相应的,它直接在它出现的地方生成字节码,没有特别的范围规则。

当从循环体中退出来时这种区别十分重要,在下节将显示为什么会这样。