`
renjie120
  • 浏览: 234720 次
  • 性别: Icon_minigender_1
  • 来自: 上海
博客专栏
D11bba82-ec4a-3d31-a3c0-c51130c62f1c
Java应用集锦
浏览量:22416
社区版块
存档分类
最新评论

Groovy基础总结

阅读更多

最近因为工作需要,接触groovy,很好的语言。以前学习过python,感觉没有用到的地方,现在用groovy有了深入学习的理由,和java的无缝衔接技术。

 

入门很简单,而且做了一个小脚本,比较几个数据库的表结构,将结果保存在excel中,用groovy代码才不到1K行,使用了POI,derby,oralce数据库等。不用创建很罗嗦的pojo,太好了。

 

这里就先整理一下基础的groovy东西。全部来自附件文档,然后自己粘贴出来而已。

 

 

字符串类型的方法:

 

def firstname='Kate'
def surname='Bush'
//打印字符串的连接
println firstname*2

def fullname="$firstname $surname"
println fullname
println fullname-firstname
//凑足15个字符,不够就在左边补充空格
println fullname.padLeft(15)  

//关于字符串的截取
println fullname[0..3]
println fullname[-4..-1]
//下面的方式比较特别,取第5个字符,以及3,2,1位置字符连接起来
assert fullname[5,3..1]=='Beta'

ff='aaaabbccadvbasd'
lines=ff.split('a')
//下面assert在后面表达式为false情况下抛出异常
assert lines.size()==7

//注意字符串中的特殊字符
def plain='\n\r\t\b\\\f\$'
assert plain.size()==7

//关于字符串的闭包(注意下面的括号的使用方法!)
fullname="${-> firstname} $surname"
println fullname
firstname = 'li'
surname='shuiqing'
println fullname

//关于字符串的运算符
fullname = fullname -'qing'-'l'+' hello world'
assert fullname=='i Bush hello world'

//字符串替换
string = 'hippopotamus'
assert string.replace('ppopotam','bisc') == 'hibiscus'

//字符串反转,转换为list
assert'apple'.toList() == ['a', 'p', 'p', 'l', 'e']

//下面把字符串里面去掉重复数字,并排序.
string = "an apple a day"
assert string.toList().unique().sort().join() == ' adelnpy'

//下面方法取出得到字符串里面的各个单词,并进行反转
string = 'Yoda said, "can you see this?"'
revwords= string.split(' ').toList().reverse().join(' ')
assert revwords== 'this?" see you "can said, Yoda'
println revwords

//对数组进行筛选,找出反转之后还等于原来字符串并且长度大于5的字符串
words = ['bob', 'alpha', 'rotator', 'omega', 'reviver']
bigPalindromes= words.findAll{w-> w == w.reverse() && w.size() > 5}
assert bigPalindromes== ['rotator', 'reviver']
println bigPalindromes
 

数字方法:

 

def x=3
def y=4
println x+y
println x.plus(y)                
println x instanceof Integer   //输出true

def a=2/3
//进行小数的取三位小数运算.
def b = a.setScale(3,BigDecimal.ROUND_HALF_UP)
assert b.toString() == '0.667'

//进行不等于的比较
println 4<=>3     //输出1
   4!=3
  
println 4**3      //4的3次方,等于4.power(3)
println 4/3       //输出1.3333333333,等于4.div(3)
println 8.intdiv(3)     //输出1
println 8%3          //取余,等于8.mod(3)
 

 

日期函数:

 

 

import static java.util.Calendar.getInstance as now
import org.codehaus.groovy.runtime.TimeCategory
import java.text.SimpleDateFormat

def date = new Date()+1
println date

input = '1998-06-03'
df1 = new SimpleDateFormat("yyyy-MM-dd")
date = df1.parse(input)
df2 = new SimpleDateFormat("MMM/dd/yyyy")
println 'Date was '+df2.format(date)

println now().time

println  df1.format(now().time)

//进行时间的计算
use(TimeCategory){
    date3 =  new Date()+1.year+3.hours-2.days
    println df1.format(date3)
}

/*
Tue Apr 10 14:59:33 CST 2012
Date was 六月/03/1998
Mon Apr 09 14:59:33 CST 2012
2012-04-09
2013-04-07
*/
 

操作符重载:

 

 

//下面演示对字符串实现了操作符++的重载.++对应的方法名是next
 for ( i='a';i<'d';i++)
   print i +", "
 
 println ''
   
 for( i in 'a'..'d')
  print i+", "
  
  //下面演示的对于集合,重载了操作符<<,对应的方法名是leftShift()
  lst = ['hello']
  lst << 'there'
  println lst
  
  //下面演示对一个自定义类实现的+的重载。
  class ComplexNumber{
      def real,imaginary
      
      def plus(other){
          new ComplexNumber(real:real+other.real,
               imaginary:imaginary+other.imaginary)
      }
      
      String toString(){
          "$real ${imaginary>0 ? '+':''}${imaginary}i"
      }
  }
  
  c1 = new ComplexNumber(real:1,imaginary:2)
  c2 = new ComplexNumber(real:4,imaginary:-31)
  
  println c1+c2
 
操作数据库
import groovy.sql.Sql
def testYear = '2011'
//下面的Driver类找不到!修改配置文件就可以了。
def sql = Sql.newInstance("jdbc:mysql://localhost:3306/dwz","root","123456"
    ,"com.mysql.jdbc.Driver")
println '数据库名:'+sql.connection.catalog

   
sql.execute("delete from testtable where name like ? or name like ? or name like ?",['ls%','lish%','%dataSet%']) 

println '插入我的数据之前,数据库:'
sql.eachRow("select * from testtable"){
    println "id = ${it.id}   year = ${it.name}  "+it.name
}
println '--------------------------------------'
wid = 123
wname = 'lishuiqing'
//下面必须使用双引号!
sql.execute("insert into testtable(id,name) values (${wid},${wname})") 

sql.execute("update testtable set name =? where name = ?",['lsq','lishuiqing'])

//下面使用预定义参数的查询语句
sql.eachRow("select * from testtable where name like ?",["%a%"]){
    println "id = ${it.id}   year = ${it.name}  "+it.name
}
println '--------------------------------------'

println '下面练习使用dataset'
testtable = sql.dataSet('testtable')

/*def anycity = testtable.findAll{ it.id>1 }
anycity.each{
    println 1
}*/
 
2.times{
    testtable.add(id:it,name:'使用dataSet添加'+it)
}

println "testtable.getSql():"+testtable.getSql()
println '总行数:'+testtable.rows().size()
 

num = 0
testtable.each{ 
    //println it[0]----也可以输出指定位置的元素!!
    num = num+1
    println it.id+",year="+it.name
}
//注意要使用${}输出参数的话,必须使用双引号。。。
println "${num}"

println '--------------------------------------'
println "下面显示当前数据库的运行实时状态"
sql.eachRow("show status "){
    //下面在{}里面定义的变量,在外面也找到,也就是作用域是全部的范围!!
    if(it.variable_name=="Uptime")
        uptime = it[1]
    else if (it.variable_name =='Questions')
        questions = it[1]
}
println "数据库运行时间Uptime for Database:${uptime}"
println "数据库查询的条目Number of Queries:${questions}"
println "每分钟的查询条目Queties per Minutes = "+Integer.valueOf(questions)/Integer.valueOf(uptime)

sql.eachRow("show status like 'Com_%'"){
    if(it.variable_name=="Com_insert")
        insertnum = Integer.valueOf(it[1])
    else if (it.variable_name == "Com_select")
        selectnum = Integer.valueOf(it[1])
    else if (it.variable_name == "Com_update")
        updatenum = Integer.valueOf(it[1])
}
println "查询语句有${selectnum},百分比:"+100*(selectnum/Integer.valueOf(uptime))+"%"
println "插入语句有${insertnum},百分比:"+100*(insertnum/Integer.valueOf(uptime))+"%"
println "更新语句有${updatenum},百分比:"+100*(updatenum/Integer.valueOf(uptime))+"%"

println '--------------------------------------'
println '下面将数据库里面的值保存到xml文件'
bldr = new groovy.xml.MarkupBuilder()
bldr.testtable{
    sql.eachRow('select * from testtable'){
        data(id:it.id,name:it.name)
    }
}
println bldr.text()
 集合
List

assert [1,2,3,4] ==(1..4)
//集合是有顺序的!!
assert [1,2,3,4] !=[1,2,4,3]
assert [1,2,3]+[1] ==[1,2,3,1]
//将一个元素添加到已经存在的list中
assert [1,2,3]<<1 ==[1,2,3,1]
//从已有的list中删除元素
assert [1,2,3,1]-[1] ==[2,3]
assert [1,2,3]*2 ==[1,2,3,1,2,3]
//flatten:扁平的意思
assert [1,[2,3]].flatten() ==[1,2,3]
assert [1,2,3].reverse()==[3,2,1]
//测试两个集合是否有交叉
assert [1,2,3].disjoint([4,5,6])
//intersect:得到两个集合中的交集
assert [1,2,3].intersect([4,3,1]) ==[3,1]
//对集合进行循环处理
assert [1,2,3].collect{it+3} ==[4,5,6]
assert [1,2,3,1].unique().size()==3
assert [1,2,3,1].count(1) ==2
assert [1,2,3,4].min() ==1
assert [1,2,3,4].max() ==4
assert [1,2,3,4].sum() ==10
assert [4,2,1,3].sort() ==[1,2,3,4]
//对集合进行循环处理判断,并返回结果
assert [4,2,1,3].findAll{it%2==0} ==[4,2]

//对集合的迭代
def expected = [1,2,3,'test']
expected.each{test -> println test}


Map:

def map = [a:1,'b':2]
println map    //[a:1, b:2]
println map.a
println map['a']
println map.keySet()  //[a, b]
 
map = [:]
map[1] = 'a';map[2]='b'
map[true] = 'p'
map[false] = 'q'
map[null]='x';map['null'] = 'z'
assert map ==[1:'a',2:'b',(true):'p',(false):'q',(null):'x'
    ,'null':'z']

//下面的例子很有用,对map进行了很快速的循环输出!!
def sb = new StringBuffer();
[1:'a',2:'b',3:'c'].each{k,v->sb << "$k:$v, "}

//下面是输出字符串
[1:'a',2:'b',3:'c'].each{k,v-> println "$k:$v, "}

assert sb.toString() =='1:a, 2:b, 3:c, '

//下面又是一种快速的输出map为字符串形式的方法
map = [1:'a',2:'b',3:'c']
def string = map.collect{k,v -> "$k:$v"}.join(', ')
assert string == '1:a, 2:b, 3:c'  
 
//下面演示一个对city进行分类的例子
assert [
    [name:'C',city:'London'],
    [name:'S',city:'London'],
    [name:'M',city:'LA'],
    [name:'Z',city:'HK'],
    [name:'A',city:'HK']        
].groupBy{it.city}==[
    London:[ [name:'C',city:'London'],
    [name:'S',city:'London']],
    LA:[ [name:'M',city:'LA']],
    HK:[ [name:'Z',city:'HK'] ,
    [name:'A',city:'HK'] ]
]

//map中顺序也是有关系的!顺序不对的map也不相等
assert [ [name:1,city:'L'],[name:2,city:'H']] != [ [name:2,city:'H'],[name:1,city:'L']]
 闭包

闭包的一个例子:

import static java.lang.Math.*

//闭包例子1
piA = { 22/7 }
piB = { 333/106 }
piC = { 355/113 }
piD = { 0.6*(3+sqrt(5))}
piE = { 22/7 +37/47 +888/83}
piF = { sqrt(sqrt(2143/22)) }

//这里就是闭包的实际算法部分。
howCloseToPI = { abs(it.value() - PI) }

algorithms = ['piA':piA,'piB':piB,'piC':piC,'piD':piD,'piE':piE,'piF':piF] 

findBestPI(algorithms)

def findBestPI(map){
    map.entrySet().sort(howCloseToPI).each{
        entry ->//下面调用了闭包的函数
        def diff = howCloseToPI(entry)
        println "Alorithm $entry.key differs by $diff"
    }
}

doubleNum = {num ->num*2}
println doubleNum(3)

//闭包例子2
//下面的方法定义就是使用了闭包。传入了num,closure,其中closure是函数类型。
processThenPrint = {num,closure->
  num = closure(num);println "num is $num"
}
//下面传入了函数名作为第二个参数
processThenPrint(3,doubleNum)
//下面传入第二个参数是匿名函数
processThenPrint(10){it/2}

//闭包例子3
//下面又是一个闭包的例子
def houston(Closure  doit){
   (10..1).each{
       count -> doit(count) 
   }
}

houston{ println it}

//闭包例子4,用于迭代
3.times{println 'Hi'}

[0,1,2].each{number -> println number}

//注意下面的it!!
[1,3,5].each{ println it}

def println = {println it}
[4,5,6].each println

map = ['a':1,'b':2]
map.each{key,value -> map[key]=value*2 }
assert map == ['a':2,'b':4]

//注意下面的each后面是小括号,不是大括号了!
doubler = {key,value -> map[key] = value*2}
map.each(doubler)
assert map == ['a':4,'b':8]

def doubleMethod(entry){
    map[entry.key] = entry.value *2;
}
doubler = this.&doubleMethod
map.each(doubler)
assert map == ['a':8,'b':16]

//下面对集合的一些操作很容易的结合了闭包方法的使用
//查询子元素
assert [1,2,3].grep{it<3} ==[1,2]
//判断是否有一个满足条件
assert [1,2,3].any{ it%2==0 }
//判断是否全部满足条件
assert [1,2,3].every{ it <4}
//将集合中全部元素join
assert (1..9).collect{it}.join() == '123456789'
assert (1..4).collect{it*2}.join() == '2468'

//闭包例子5:新的函数curry!以及演示一个通过闭包将list进行修改的例子!!
def add = {x,y -> x+y}
def mult = {x,y -> x*y}
assert add(1,3) == 4
assert mult(1,3) == 3

def min = {x,y -> [x,y].min()}
def max = {x,y -> [x,y].max()}
def sub = {x,y -> return 'x - y = '+(x-y)}

//注意下面的curry函数,意思是默认的传入参数到原有的函数的第一个位置,并将结果返回为一个新的函数
//例如下面的triple就是得到一个数值的三倍!!
def triple = mult.curry(3);assert triple(2) ==6
def atLeastTen = max.curry(10)
def subTen = sub.curry(10)
assert atLeastTen(5)==10
assert atLeastTen(15) == 15
assert subTen(13) == 'x - y = -3'

//
def pairWise(list ,invoke){
    if(list.size()<2) return []
    def next = invoke(list[0],list[1])
    return [next]+pairWise(list[1..-1],invoke)
}

assert pairWise(1..5,add) == [3,5,7,9]
assert pairWise(1..5,mult) == [2,6,12,20]
assert pairWise(1..5,min) == [1,2,3,4]
assert pairWise(1..5,max) == [2,3,4,5]

//inject--参数是初始值,然后放在一个闭包里面对list的每个元素进行迭代操作!
assert 'cbaxabc' == ['a','b','c'].inject('x'){
    result,item -> item +result+item
}
 对xml的操作

对xml的解析

def CAR_RECORDS = '''
<records>
<car name='HSV Maloo' make='Holden' year='2006'>
<country>Australia</country>
<record type='speed'>Production Pickup Truck with speed of 271kph</record>
</car>
<car name='P50' make='Peel' year='1962'>
<country>Isle of Man</country>
<record type='size'>Smallest Street-Legal Car at 99cm wide and 59 kg in weight</record>
</car>
<car name='Royale' make='Bugatti' year='1931'>
<country>France</country>
<record type='price'>Most Valuable Car at $15 million</record>
</car>
</records>
'''
//解析xml的第一步,进行分析--注意这里的找到的是根节点<records>,所以后面的car。size()就有值。
def records = new XmlSlurper().parseText(CAR_RECORDS)
//得到节点的数目
assert 3 == records.car.size()
//注意下面的得到car里面的country的条目,而不是直接进行records.country!!
assert 3 == records.car.country.size()
//depthFirst():计算全部的节点的数目   
assert 10 == records.depthFirst().collect{it}.size()

def firstRecord = records.car[0]
//得到一个节点里面的属性name
assert 'car' == firstRecord.name()
//得到一个节点里面的自定义属性,使用@属性名 
assert 'Holden' == firstRecord.@make.toString()
//text():得到节点里面的文本信息!不是属性。
assert 'Australia' == firstRecord.country.text()

//对节点进行判断,找到make属性含有e的条目数量
assert 2 == records.car.findAll {it.@make.toString().contains('e')}.size()
//使用正则表达式进行节点筛选
assert 2 == records.car.findAll{it.@make=~'.*e.*'}.size()

//找到全部的国家符合正则表达式的record节点的make属性!
assert ['Holden','Peel'] == records.car.findAll{ it.country =~ '.*s.*a.*'}
    .@make.collect{it.toString()}
    
//找到全部的type非空的record节点的type属性!!
assert ['speed','size','price'] == records.depthFirst().grep{it.@type!=''}.'@type'*.toString()

def countryOne = records.car[1].country
//查找父节点的两个方法!parent和使用路径表达式
assert 'Peel' == countryOne.parent().@make.toString()
assert 'Peel' == countryOne.'..'.@make.toString()

//将所有的节点按照指定顺序排序之后,再按顺序输出name属性!注意后面的一个×号!
def names = records.car.list().sort{ it.@year.toInteger()}.'@name'*.toString()
assert ['Royale','P50','HSV Maloo'] == names
 操作文件,属性文件:
myFileDir = "d:\\"
myFileName = 'mytest.txt'
myFile = new File(myFileDir + myFileName)

printFileLine = { println "File line:"+it}

myFile.eachLine ( printFileLine )

myFile.write('123')
myFile.append('123')

读取属性文件:
Properties properties = new Properties()
properties.load(new FileInputStream("d:\\conf.properties"))

println properties.getProperty("filename")
 正则表达式:
正则表达式:
assert 'Hello World!' =~ /Hello/
assert 'Hello World!' ==~ /Hello\b.*/
def p = ~/Hello\b.*/
assert p.class.name == 'java.util.regex.Pattern'

//下面的next方法是返回的下一个字符!
assert "1.23".replaceAll(/./){ch-> ch.next()}== "2/34"

assert "1.23".replaceAll(/\d/){num -> num.toInteger()+1}=='2.34'

//下面的 == 不可以换行!否则就是语法错误!!为什么??因为每一行后面默认就是有一个分号的!!
assert "1.23".replaceAll(/\d+/){num ->
 num.toInteger()+1} == '2.24'
 
分享到:
评论

相关推荐

    groovyandroid.github.io:Groovy Android网站

    Groovy Android华硕Zenfone 2 ... XDA的线程将继续作为用户,开发人员和编译器之间所有交互的基础。 但是,有时可能很难找到某些信息。 届时,该站点将尝试总结哪些可能被视为更重要或更重复的问题。 享受!!

    GRAILS课程学习记录总结

    Grails 是一个注重成效的开源 Web...要理解这些内容,你得需要点面向对象编程和 MVC Web 应用开发的基础知识。虽然阅读 并不要求熟悉 Java,但如果熟悉的话,你肯定能从中受益。 你还会看到这些例子大量用到了 Groovy。

    AndroidStudy:Android学习过程的一些总结

    扫描二维码下载APK示例 或者 更新日志 2019-06-20 ...优化内容: 1、优化dialog默认布局 ...Gradle理论与实践三:Gradle构建脚本基础 ( ) Gradle理论与实践四:自定义Gradle插件( ) Gradle配置中subprojects和allpr

    Spring 2.0 开发参考手册

    7.5.1. 基础 7.5.2. JavaBean属性 7.5.3. 基于JDK和CGLIB的代理 7.5.4. 对接口进行代理 7.5.5. 对类进行代理 7.5.6. 使用“全局”advisor 7.6. 简化代理定义 7.7. 使用ProxyFactory通过编程创建AOP代理 7.8....

    Maven权威指南 很精典的学习教程,比ANT更好用

    总结 2. 安装和运行Maven 2.1. 验证你的Java安装 2.2. 下载Maven 2.3. 安装Maven 2.3.1. 在Mac OSX上安装Maven 2.3.2. 在Microsoft Windows上安装Maven 2.3.3. 在Linux上安装Maven 2.3.4. 在FreeBSD或...

    spring chm文档

    7.5.1. 基础 7.5.2. JavaBean属性 7.5.3. 基于JDK和CGLIB的代理 7.5.4. 对接口进行代理 7.5.5. 对类进行代理 7.5.6. 使用“全局”advisor 7.6. 简化代理定义 7.7. 使用ProxyFactory通过编程创建AOP代理 7.8....

    Spring-Reference_zh_CN(Spring中文参考手册)

    7.5.1. 基础 7.5.2. JavaBean属性 7.5.3. 基于JDK和CGLIB的代理 7.5.4. 对接口进行代理 7.5.5. 对类进行代理 7.5.6. 使用“全局”advisor 7.6. 简化代理定义 7.7. 使用ProxyFactory通过编程创建AOP代理 7.8. 操作被...

    Spring中文帮助文档

    7.5.1. 基础 7.5.2. JavaBean属性 7.5.3. 基于JDK和CGLIB的代理 7.5.4. 对接口进行代理 7.5.5. 对类进行代理 7.5.6. 使用“全局”通知器 7.6. 简化代理定义 7.7. 使用ProxyFactory通过编程创建AOP代理 7.8. ...

    Spring API

    7.5.1. 基础 7.5.2. JavaBean属性 7.5.3. 基于JDK和CGLIB的代理 7.5.4. 对接口进行代理 7.5.5. 对类进行代理 7.5.6. 使用“全局”通知器 7.6. 简化代理定义 7.7. 使用ProxyFactory通过编程创建AOP代理 7.8. ...

Global site tag (gtag.js) - Google Analytics