官方文档

注释(Comments)

和Java一样,支持单行(使用//)、多行(/* */)和文档注释(使用/** */)。

Shebang line

UNIX系统支持一种特殊的单行注释叫作Shebang line,用于指明脚本的运行环境,这样就可以直接在终端中使用./xxx.groovy运行(当然,前提是文件得有可运行的权限),而不用像groovy xxx.groovy这样运行:

#!/usr/bin/env groovy
println "Hello from the shebang line"

#号必须是文件的第一个字符。

标识符(Identifiers)

普通标识符

以字母、美元符号$或下划线_开始,不能以数字开始。以下是可用的标识符:

def name
def item3
def with_underscore
def $dollarStart

以下是不可用的标识符:

def 3tier // 不能以数字开始
def a+b // "+"号是非法字符
def a#b // #号也不是可用的字符

注意:在点号后,是可以使用关键字作为标识符的:

foo.as
foo.assert
foo.break
foo.case
foo.catch

引号标识符(Quoted identifiers)

Groovy在点表达式(dotted expression)后面可以使用引号标识符,比如persion.name可以表示为persion.'name'persion."name"。而引号中可以包含普通标识符中不支持的字符,比如空格、中档线-这些:

def map = [:]

map."an identifier with a space and double quotes" = "ALLOWED"
map.'with-dash-signs-and-single-quotes' = "ALLOWED" assert map."an identifier with a space and double quotes" == "ALLOWED"
assert map.'with-dash-signs-and-single-quotes' == "ALLOWED"

其实,Groovy支持多种字符串的字面量表达形式,这些都是可以出现在点号后面的:

map.'single quote'
map."double quote"
map.'''triple single quote'''
map."""triple double quote"""
map./slashy string/
map.$/dollar slashy string/$

更方便的是,Groovy中的GString支持插值,也可以用在点号后面的:

def firstname = "Homer"
map."Simson-${firstname}" = "Homer Simson" // 会被插值成map."Simson-Homer" assert map.'Simson-Homer' == "Homer Simson"

字符串

在Groovy中字符串有两种类型,一种是Java原生的java.lang.String;另一种是groovy.lang.GString,又叫插值字符串(interpolated strings)。

单引号字符串(Single quoted string)

在Groovy中,使用单引号括住的字符串就是java.lang.String,不支持插值:

def name = 'yjiyjgie'
println name.class // class java.lang.String

三单引号字符串(Triple single quoted string)

使用三单引号括住字符串支持多行,也是java.lang.String实例,在第一个’‘’起始处加一个反斜杠\可以在新一行开始文本:

def strippedFirstNewline = '''line one
line two
line three
'''
// 可以写成下面这种形式,可读性更好
def strippedFirstNewline = '''\
line one
line two
line three
'''

双引号字符串(Double quoted string)

如果双引号括住的字符串中没有插值表达式(interpolated expression),那它就是java.lang.String;如是有插值表达式,那它就是groovy.lang.GString

def normalStr = "yjiyjige" // 这是一个java.lang.String
def interpolatedStr = "my name is ${normalStr}" // 这是一个groovy.lang.GString

字符串插值(String interpolation)

在Groovy所有的字符串字面量表示中,除了单引号字符串和三单引号字符串,其他形式都支持字符串插值。字符串插值,也即将占位表达式中的结果最终替换到字符串相应的位置中:

def name = 'Guillaume' // a plain string
def greeting = "Hello ${name}" // name变量的值会被替换进去 assert greeting.toString() == 'Hello Guillaume'

当使用点号表达式时,可以只用$代替${}

def person = [name: 'Guillaume', age: 36]
println "$person.name is $person.age years old" // 注意
def number = 3.14
println "$number.toString()" // 这里会报异常,因为相当于"${number.toString}()"
println "${number.toString()}" // 这样就正常了

插值占位符中还支持闭包,而闭包的一个好处是惰性求值(lazy evaluation):

def number = 1
def eagerGString = "value == ${number}" // 普通形式
def lazyGString = "value == ${-> number}" // 这是一个闭包 println eagerGString == "value == 1"
println lazyGString == "value == 1" number = 2
println eagerGString == "value == 1" // eagerGString已经被固定下来了
println lazyGString == "value == 2" // lazyGString的值会被重新计算

当一个方法的需要一个java.lang.String变量,而我们传递的是一个groovy.lang.GString实例时,GStringtoString方法会被自动调用,看起来像我们可以直接将一个GString赋值给一个String变量一样。

注意:GStringString的hashCode是不一样的,即使他们最终结果一样。所以,在Map中,不应该用GString去做元素的Key,而又使用普通的String去取值:

def key = "a"
def m = ["${key}": "letter ${key}"] // key类型是一个GString
assert m["a"] == null // 用一个普通String类型的key去取值

三双引号字符串(Triple double quoted string)

类似于三单引号字符串,但支持字符串插值。

斜线字符串(Slashy string)

除了使用引号来括住字符串,还可以使用/。它一般用来定义正则表达式:

def fooPattern = /.*foo.*/
assert fooPattern == '.*foo.*' def foo = /"yjiyjige"/ // 可以在斜线表达式中,直接使用引号
println foo // 结果是“yjiyjige”

美元斜线字符串(Dollar slashy string)

这种字符串使用$/开始,使用/$结束,其中的转义字符为$

def name = "Guillaume"
def date = "April, 1st" def dollarSlashy = $/
Hello $name,
today we're ${date}. $ dollar sign
$$ escaped dollar sign
\ backslash
/ forward slash
$/ escaped forward slash
$/$ escaped dollar slashy string delimiter
/$ assert [
'Guillaume',
'April, 1st',
'$ dollar sign',
'$ escaped dollar sign',
'\\ backslash',
'/ forward slash',
'$/ escaped forward slash',
'/$ escaped dollar slashy string delimiter'
].each { dollarSlashy.contains(it) }

字符串小结

 
 

字符(Characters)

在Groovy中并没有明确的字符字面量表示形式,我们必须明确指明:

char c1 = 'A' // 明确指定给一个字符变量
assert c1 instanceof Character def c2 = 'B' as char // 用as关键字
assert c2 instanceof Character def c3 = (char) 'C' // 强制类型转换
assert c3 instanceof Character

数字(Numbers)

当使用def指明整数字面量时,变量的类型会根据数字的大小自动调整:

def a = 1
assert a instanceof Integer // Integer.MAX_VALUE
def b = 2147483647
assert b instanceof Integer // Integer.MAX_VALUE + 1
def c = 2147483648
assert c instanceof Long // Long.MAX_VALUE
def d = 9223372036854775807
assert d instanceof Long // Long.MAX_VALUE + 1
def e = 9223372036854775808
assert e instanceof BigInteger

为了精确地计算小数,在Groovy中使用def声明的小数是BigDecimal类型的:

def decimal = 123.456
println decimal.getClass() // class java.math.BigDecimal

如果要强制指明一个数字的字面量类型,可以给字面量加上类型后缀:

  • BigInteger 使用Gg
  • Long 使用Ll
  • Integer 使用Ii
  • BigDecimal 使用Gg
  • Double 使用Dd
  • Float 使用Ff

列表(List)

默认情况下Groovy的列表使用的是java.util.ArrayList,用中括号[]括住,使用逗号分隔:

def numbers = [1, 2, 3]
println numbers.getClass() // class java.util.ArrayList

如果要使用其它类型的列表(如:LinkedList)可以使用as操作符或显式分配给一个指定类型的变量:

def arrayList = [1, 2, 3] // 默认类型
assert arrayList instanceof java.util.ArrayList def linkedList = [2, 3, 4] as LinkedList // 使用as操作符
assert linkedList instanceof java.util.LinkedList LinkedList otherLinked = [3, 4, 5] // 显式指明类型
assert otherLinked instanceof java.util.LinkedList

Groovy重载了列表的[]<<操作符,可以通过List[index]访问指定位置元素,也可以通过List << element往列表末尾添加元素:

def letters = ['a', 'b', 'c', 'd']

assert letters[0] == 'a'
assert letters[1] == 'b' assert letters[-1] == 'd' // 从后面访问
assert letters[-2] == 'c' letters[2] = 'C' // 直接修改
assert letters[2] == 'C' letters << 'e' // 往最后面添加元素
assert letters[4] == 'e'
assert letters[-1] == 'e' assert letters[1, 3] == ['b', 'd'] // 提取指定元素
assert letters[2..4] == ['C', 'd', 'e'] // 支持范围(ranges)操作 // 二维列表
def multi = [[0, 1], [2, 3]]
assert multi[1][0] == 2

数组(Arrays)

在Groovy中,没有数组的字面量定义方式。和特定类型列表的定义方式一样,我们需要使用as操作符或显式地分配给一个数组类型的变量:

String[] arrStr = ['Ananas', 'Banana', 'Kiwi'] // 显式指明类型
assert arrStr instanceof String[]
assert !(arrStr instanceof List) def numArr = [1, 2, 3] as int[] // 使用as操作符
assert numArr instanceof int[]
assert numArr.size() == 3

映射(Maps)

Groovy使用中括号[]来定义映射,元素需要包含key和value使用冒号分隔,元素与元素之间用逗号分隔:

// key部分其实是字符串
def colors = [red: '#FF0000', green: '#00FF00', blue: '#0000FF'] assert colors['red'] == '#FF0000' // 使用中括号访问
assert colors.green == '#00FF00' // 使用点表达式访问 colors['pink'] = '#FF00FF'
colors.yellow = '#FFFF00'
assert colors.pink == '#FF00FF'
assert colors['yellow'] == '#FFFF00' assert colors instanceof java.util.LinkedHashMap // 默认使用LinkedHashMap类型

在上边的例子中,虽然没有明确的使用字符串’red‘’green‘,但Groovy会自动把那些key转化为字符串。并且,在默认情况下,初始化映射时,key也不会去使用已经存在的变量:

def keyVal = 'name'
def persons = [keyVal: 'Guillaume'] // 此处的key是字符串keyVal而不是name assert !persons.containsKey('name')
assert persons.containsKey('keyVal')

如果要使用一个变量作为key,需要用括号括住:

def keyVal = 'name'
def persons = [(keyVal): 'Guillaume'] // 相当于[ 'name' : 'Guillaume' ] assert persons.containsKey('name')
assert !persons.containsKey('keyVal')

Groovy基本语法的更多相关文章

  1. Gradle Groovy 基础语法 MD

    Markdown版本笔记 我的GitHub首页 我的博客 我的微信 我的邮箱 MyAndroidBlogs baiqiantao baiqiantao bqt20094 baiqiantao@sina ...

  2. groovy常用语法及实战

    groovy语言简介 一种基于JVM的敏捷开发语言,作为编程语言可编译成java字节码,也可以作为脚本语言解释执行. 结合了Python.Ruby和Smalltalk的许多强大的特性 支持面向对象编程 ...

  3. Groovy系列(3)- Groovy基础语法

    Groovy基础语法 动态类型 Groovy定义变量时:可以用Groovy风格的def声明,不指定类型:也可以兼容Java风格,指定变量类型:甚至还可以省略def或类型 def t1 = 't1' S ...

  4. Groovy基础语法

    Groovy 基础语法 变量定义 1.支持动态类型,使用def关键字定义变量 // Java中定义变量的方式 int age = 18; String name = "张三"; / ...

  5. Groovy常见语法汇总

    一.groovy是什么 简单地说,Groovy 是下一代的java语言,跟java一样,它也运行在 JVM 中. 作为跑在JVM中的另一种语言,groovy语法与 Java 语言的语法很相似.同时,G ...

  6. Groovy常用语法汇总

    基本语法 1.Grovvy的注释分为//和/**/和java的一样. 2.Grovvy语法可以不已分号结尾. 3.单引号,里面的内容严格的对应java中的String,不对$符号进行转义. def s ...

  7. GROOVY简单语法实习

    慢慢的看<GROOVY IN ACTION>的一个中文节译本,根据上面的东东慢慢练习. 中文看起来确实比英文快好多...:) Book gina = new Book('Groovy in ...

  8. groovy基本语法--JSON

    1.groovy提供了对JSON解析的方法       ①JsonSlurper   JsonSlurper是一个将JSON文本或阅读器内容解析为Groovy数据的类结构,例如map,列表和原始类型, ...

  9. Groovy学习--基本语法了解

    x项目用到gradle,学习gradle之前准备先过一遍Groovy的语法.这里参考:Groovy入门. 该博客没有系统的讲解Groovy的语法和原理,仅仅只是罗列了使用Groovy的常规方法.我照着 ...

随机推荐

  1. Comet OJ - Contest #6 D. 另一道树题 并查集 + 思维 + 计数

    Code: #include <cstdio> #include <algorithm> #include <cstring> #include <vecto ...

  2. UE4中显示AI Debug信息

    运行时,按下引号键('),就会出现AI的Debug信息,包含 AI Behavior Tree EQS Perception 四个大的分类,可以通过键盘上的1234键来显示和关闭相应的选项. 另外在E ...

  3. Spring Cloud教程(十)自定义引导配置属性源

    可以通过在org.springframework.cloud.bootstrap.BootstrapConfiguration键下添加条目/META-INF/spring.factories来训练引导 ...

  4. C/C++头文件的编写

    在C语言的学习过程中,我们一般把所有的代码写在一个文件中.随着自身水平的提高,我们发现代码越写越长,代码行数越来越多,把一个工程的所有代码写在一个文件中让人看起开非常吃力.于是我们开始想把代码中的函数 ...

  5. yum命令查询详解

    一.列举包文件列出资源库中所有可以安装或更新的rpm包# yum list列出资源库中特定的可以安装或更新以及已经安装的rpm包# yum list perl           //列出名为perl ...

  6. Day3 01 枚举

    枚举:关键字 enum  主要为了限定了选择范围,声明了一组相关的值类型的集合. 1.枚举类型,实质上是整整 2.如果不进行赋值操作,枚举类型从0开始递增. 3.枚举不能定义字段 属性  方法. 例如 ...

  7. MySQL5.6transportable tablespace

    https://blog.csdn.net/xiaoyi23000/article/details/53150776

  8. java valueOf

    valueOf 方法可以将原生数值类型转化为对应的Number类型,java.lang.Number 基类包括ouble.Float.Byte.Short.Integer 以及 Long派生类, 也可 ...

  9. SynchronousQueue 源码分析

    SynchronousQueue SynchronousQueue 能解决什么问题?什么时候使用 SynchronousQueue? 1)SynchronousQueue 没有任何内部容量. 2)Sy ...

  10. LongAdder 源码分析

    LongAdder LongAdder 能解决什么问题?什么时候使用 LongAdder? 1)LongAdder 内部包含一个基础值[base]和一个单元[Cell]数组. 没有竞争的情况下,要累加 ...