另外return关键字在方法的最后是可选的;同样,返回类型也是可选(缺省是Object)。
二、动态类型
//Groovy 动态类型
myStr = "Hello World"
由于使用了动态类型,不需要继承就可以得到多态的全部功能:
class Song{
Property length
Property name
}
class Book{
def public name
def public author
}
def doSomething(thing){
println "going to do something with a thing named = " + thing.name
}
这里定义了两个Groovy 类,Song 和 Book。这两个类都包含一个 name 属性。函数 doSomething,它以一个 thing 为参数,并试图打印这个对象的 name 属性,但doSomething 函数没有定义其输入参数的类型,所以只要对象包含一个 name 属性,那么它就可以工作。可见, Song 和 Book 的实例都可以作为 doSomething 的输入参数。
mySong = new Song(length:90, name:"Burning Down the House")
myBook = new Book(name:"One Duck Stuck", author:"Phyllis Root")
doSomething(mySong) //prints Burning Down the House
doSomething(myBook) //prints One Duck Stuck
def doSth=this.&doSomething
doSth(mySong)
doSth(myBook)
在例子的最后,我们还创建了doSomething的一个函数指针 doSth,最后的执行结果与调用doSoemthing是一样的。
值得注意的是:与Groovy Beta不同,在使用新的JSR Groovy类时,类里面的所有的变量都必须加上 def 关键字或者 private、protected 或 public 这样的修饰符。当然,也可以用 @Property 关键字声明成员变量。在Script中则不必。
三、字符串
Groovy中的字符串允许使用双引号和单引号。当使用双引号时,可以在字符串内嵌入一些运算式,Groovy允许您使用 与 bash 类似的 ${expression} 语法进行替换。可以在字符串中包含任意的Groovy表达式。
name="James"
println "My name is ${name},'00${6+1}'" //prints My name is James,'007'
Groovy还支持"uXXXX" 引用(其中X是16进制数),用来表示特殊字符,例如 "u0040" 与"@"字符相同。
1、大块文本
如果有一大块文本(例如 HTML 和 XML)不想编码,你可以使用Here-docs. here-docs 是创建格式化字符串的一种便利机制。它需要类似 Python 的三重引号(""")开头,并以三重引号结尾。
name = "James"
text = ""“ hello there ${name} how are you today? ”""
assert text != null
println(text)
在Groovy-JSR中,不再支持下面这种多行字符串,个人觉得似乎与Here-docs功能重叠:
foo = “hello there how are things?”
println(foo)
2、对字符串的操作
(1)contains 字符串中是否包含子字符串,'groovy'.contains('oo')将返回true;
(2)count 返回字符串中子字符串出现的次数,'groooovy'.count('oo')将返回3;
(3)tokenize 根据分隔符将字符串分解成子串,'apple^banana^grap'.tokenize('^')返回['apple','banana','grape'];
(4)减操作 'groovy'-'oo',结果是'grvy';
(5)乘操作 'oo'*3,结果是'oooooo'。
四、Groovy主要结构
Groovy主要结构包括逻辑分支、类、闭包等等。
1、逻辑分支
(1)if-else语句:
Groovy提供Java相同的if-else语句。
x = false
y = false
if ( !x ) {
x = true
}
assert x == true
if ( x ) {
x = false
} else{
y = true
}
assert x == y
Groovy也支持三元操作符。
y = 5
x = (y > 1) ? "worked" : "failed"
assert x == "worked"
(2)switch语句
Groovy的switch语句兼容Java代码,但是更灵活,Groovy的switch语句能够处理各种类型的switch值,可以做各种类型的匹配:
a、case值为类名,匹配switch值为类实例
b、case值为正则表达式,匹配switch值的字符串匹配该正则表达式
c、case值为集合,匹配switch值包含在集合中,包括ranges
除了上面的,case值与switch值相等才匹配。
x = 1.23
result = ""
switch ( x ) {
case "foo":
result = "found foo" // lets fall through
case "bar":
result += "bar"
case [4, 5, 6, ‘inList‘]:
result = "list"
break
case 12..30:
result = "range"
break
case Integer:
result = "integer"
break
case Number:
result = "number"
break
default:
result ="default"
}
assert result == "number"
Switch语句的工作原理:switch语句在做case值匹配时,会调用isCase(switchValue)方法,Groovy提供了各种类型,如类,正则表达式、集合等等的重载。可以创建自定义的匹配类,增加isCase(switchValue)方法来提供自定义的匹配类型。
五、循环
1、while循环:
Groovy支持Java相同的while循环,但目前暂不支持do循环。
x = 0
y = 5
while ( y-- > 0 ){
x++
}
assert x == 5
2、for循环:
Groovy的for循环更简单,而且能够和各种类型的数组、集合、Map、范围等一起工作,我们稍候会详细介绍这些内容。
// iterate over a range
x = 0
for ( i in 0..9 ) {
x += i
}
assert x == 45
// iterate over a list
x = 0
for ( i in [0, 1, 2, 3, 4] ) {
x += i
}
assert x == 10
// iterate over an array
array = (0..4).toArray()
x = 0
for ( i in array ) {
x += i
}
assert x == 10
// iterate over a map
map = [‘abc‘:1, ‘def‘:2, ‘xyz‘:3]
x = 0
for ( e in map ) {
x += e.value
}
assert x == 6
// iterate over values in a map
x = 0
for ( v in map.values() ) {
x += v
}
assert x == 6
// iterate over the characters in a string
text = "abc"
list = []
for (c in text) {
list.add©
}
assert list == ["a", "b", "c"]
六、运行Groovy脚本
编写Groovy脚本,不需要class,不需要Main入口点,也不需要声明变量;此外,可以用def语句来定义自己的函数,并在脚本中使用它。
像许多脚本语言一样,Groovy是在运行时解释的,无编译的代码在构建-运行周期中可以提供很多好处。运行时编译使Groovy成为快速原型设计、构建不同的实用程序和测试框架的理想平台。通过以下代码可以很简单的运行Groovy:
除了利用解释器来运行Groovy脚本外,Groovy提供了两种不同的解释器Shell,使所有有效的Groovy表达式可以交互地执行:
- 运行groovysh启动命令Shell,可以输入Groovy语句直接执行
- 运行groovyConsole启动Swing方式的Groovy控制台,这是一个简单的Groovy编辑器
Groovy 脚本实际上是字节码级别的Java类。因此,还可以用groovyc编译Groovy脚本。可以通过命令行或者 Ant 使用groovyc以生成脚本的类文件。这些类可以用普通java命令运行,只要classpath包groovy.jar和asm.jar。(wang_wang)