美文网首页
Android Gradle(二)- groovy

Android Gradle(二)- groovy

作者: Stan_Z | 来源:发表于2020-04-10 00:41 被阅读0次

gradle构建脚本的语言是groovy,它的特点是全面兼容java,同时也有自身比较有特色的语法及api,这里我只是简单例举一些我自己玩过的比较有特点的groovy一些写法和api,基本上在gradle中参与度比较高的核心语法和api都有涉及到。当然详细的内容还是看官方文档比较全面。
Apache Groovy官方文档
W3Cschool groovy教程

一、变量

强类型(要给其他模块、其他类使用)

int x = 10

弱类型(自己类内部使用):类似于var

def y = 11
二、字符串

' ' 单引号 不可变常量字符表示
“ " 双引号 可拓展字符串 //def str = "this is a ${variable}"
""" """ 三引号字符串能保持格式

核心api:这里重点学习StringGroovyMethods 它又继承于DefaultGroovyMethods。

def str = “groovy”

//字符串获取
str.getAt(0) 
str.getAt(0) //get操作
str[0]//类似数组操作
str[0..1] // [0,1]//范围操作

//常用api
each 变量
find查询第一个符合条件的值
findAll 找到所有符合条件值
any 只要有一项符合条件就返回true
every 每一项都符合条件才返回true
isNumber 是否是数字类型字符串
capitalize 字符串首字母大写
reverse 字符串倒序
minus 字符串删除部分字符串
等 

这些方法可以结合闭包使用,增加业务逻辑判断。

例如:
//查找第一个为数字的字符
str.find{
    String s -> s.isNumber()
}

字符串比较可以使用java的方式。
三、 逻辑控制

if else没差别。
switch case比java强大,case可以是任意类型的对象

def dest = 1.23
def result
switch (dest) {
    case 'foo':
        result2 = 'found foo'
       break
   case [4, 5, 6]:
        result = 'list'
       break
   case 12..30:
        result = 'range'
       break
   case Integer:
        result = “integer"
       break
   case BigDecimal:
        result = 'big decimal'
       break
   default: result = 'default'
}

for循环写法更简洁

//对范围的for循环
def sum = 0
for (i in 0..9) {
    sum += i
}

//对list的循环
for (i in [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]) {
    sum += i
}

//对map的循环
for (i in ["zhangsan": 1, "lisi": 2, "wangwu": 3]) {
    sum += i.value
}
四、 数据结构
list
def list1 = new ArrayList()//java 定义方式
def list = [1, 2, 3, 4, 5] //list初始化默认是arrayList
//or def list1 = [] 定义一个空集合
def array = [1, 2, 3] as int[] //通过as来转为数组或者其他类型集合
int[] arr = [1, 2, 3, 4] //数组

//列表元素添加
list.add(6)
list.leftShift(7) //也是添加
list << 8
def plusList = list + 9
println plusList.toListString()

//列表元素删除
list.remove(0) //删除index为0的元素
list.remove((Object) 7) //删除值为7的元素
list.removeAll { return it % 2 == 0 } //结合闭包做条件删除
println list

//列表排序
def sortList = [6, 0, 2, 3]
Comparator mc = { a, b -> a == b ? 0 : Math.abs(a) < Math.abs(b) ? -1 : 1 }
Collections.sort(sortList,mc) //使用Collections.sort排序,可以添加比较条件

//sortList.sort() 用集合自身sort方法
sortList.sort {
    a, b -> a == b ? 0 : Math.abs(a) < Math.abs(b) ? 1 : -1
}
println sortList

def sortStringList = ['abc', 'z', 'hello']
println sortStringList.sort { return it.size() }//可用闭包做排序条件

//列表查找
def findList = [-3, 9, 2, 4, 1]
println findList.findAll { return it % 2 == 0 }
println findList.any { return it % 2 == 0 }
println findList.every { return it % 2 == 0 }
println findList.min { return Math.abs(it) }
println findList.max()
println findList.count { return it % 2 == 0 } //统计
//闭包指定规则非常实用
map
def map = new HashMap() //Java方式
//默认key为单引号字符串
def colorMap = [red: 'ff00000', green: '00ff00', blue: '0000ff'] //closure map

//get
println colorMap.get('red')
println colorMap['red’] //类似数组操作
println colorMap.red // .操作

//put
colorMap.put('yellow', 'ffff00')
colorMap.yellow = 'ffff00'
//最常用的是.操作符

//可以添加不同类型数据
colorMap.complex = [a: 1, b: 2]
println colorMap.toMapString()

//map默认LinkedHashMap 修改:可以通过as指定特定Map, 或者直接强类型指定Map类型

//删除
//colorMap.remove(key)
//colorMap.removeAll {}

//map操作详解
def students = [ 
        1: [number: '0001', name: "zhangsan", score: 50],
        2: [number: '0002', name: "lisi", score: 70],
        3: [number: '0003', name: "wangwu", score: 60]
]

//遍历
students.each { def student ->
    println "key is ${student.key}" +
            "value is ${student.value}"
}

//遍历加入index下标
students.eachWithIndex { def student, int index ->
    println "index is ${index}," +
            "key is ${student.key}," +
            "value is ${student.value}"
}

//直接遍历key-value
students.eachWithIndex { key, value, index ->
    println "index is ${index}," +
            "key is ${key}," +
            "value is ${value}"
}

//查找
println students.find { def stu ->
    return stu.value.score >= 60
}

println students.findAll { def stu ->
    return stu.value.score >= 60
}

//count
//在闭包输出基础上再加个闭包条件 构造查找组合
println students.findAll { def stu ->
    return stu.value.score >= 60
}.collect {
    return it.value.name
}

//分组
def group = students.groupBy { def student ->
    return student.value.score >= 60 ? "及格" : "不及格" //两个作为新的key
}
println group.toMapString()

//排序
println students.sort {
    def stu1, stu2 ->
        Number score1 = stu1.value.score
       Number score2 = stu2.value.score
       return score1 == score2 ? 0 : score1 < score2 ? -1 : 1
}
range
//range是list子类,属于轻量级list。这个概念kotlin也有
def range = 1..10 //定义 
println range[0] //获取
println range.contains(10) //包含
println range.from + "," + range.to

//遍历也可以使用 each
range.each {
    return it //推荐
}
五、闭包

闭包是groovy核心功能,需要重点掌握

//无参闭包
def clouser = {
    println 'hello groovy'
}

//有参闭包
def clouser2 = {
    String name -> println "hello ${name}"
}
clouser2("closure”)//调用 传参

//多参闭包
def clouser3 = {
    String name, int age -> println "hello ${name},age is ${age}"
}
clouser3("zhangsan", 20)

//默认参数 it
def clouser4 = {
    println "hello ${it}"
}
clouser4("world!”)

//两种调用方式
clouser.call() //推荐 比较直观一点
clouser()

闭包本身是用来做业务逻辑的语句块,可以作为一种参数(Closure closure)传入方法:

例如:
def str = ‘hello'
//find查询第一个符合条件的值
str.find{
    String s -> s.isNumber()
}

闭包三个重要变量:
this 代表闭包定义处的类 
owner 代表闭包定义处的类或者对象
delegate 代表任意对象,默认与owner一致

闭包可以定义在类、方法、闭包中。

this 、owner 、delegate 在类中闭包、方法中闭包是一致的,闭包中的闭包有区别,其中owner、delegate指向最近的闭包对象,

人为的修改了delegate,那么会跟owner不一样。另外this owner闭包定义了就不能修改,delegate可以任意修改。

闭包委托策略
class Student{
    String name
     def pretty = {"my name is ${name}”}
    String toString(){
        pretty.call()
     }
}

class Teacher{
    String name
}

def student = new Student(name:"jack")
def teacher = new Teacher(name:"sara")
student.pretty.delegate = teacher //修改delegate 
//同时修改委托策, 默认是OWNER_FIRST
stu.pretty.resolveStrategy = Closure.DELEGATE_FIRST //先去delegate找,找不到再去owner找
println student.toString()
打印:my name is sara
六、面向对象
//类
class People {
    String name
    Integer age
   def increateAge(Integer years) {
        this.age += years
    }
}

def p = new People(name: 'stan', age: 20)//创建实体对象,并且赋值
println "this name is ${p.name},age is ${p.age}" //.name 等价于getName()
p.increateAge(10)

//接口
interface Action {
    void eat()
    void drink()
}

//接口实现
class ActionImpl implements Action {
    @Override
    void eat() {
    }

    @Override
     void drink() {
    }
}

//trait : 接口方法有默认实现 类似于接口适配模式
trait Action1 {
    abstract void eat()
    abstract void drink() //不做实现的需要加abstract关键字
     void play() { //可以实现
   }
}

class Action1Impl implements Action2{
    @Override
    void eat() {
     }

    @Override
     void drink() {
    }
}
七、元编程

runtime 运行期能力

class People {
    String name
    Integer age
   def increateAge(Integer years) {
        this.age += years
    }

    //methodMissing优先级高于invokeMethod
   def methodMissing(String name, Object args) {
        return "the method ${name} is missing"
   }

    //一个方法找不到时,会调用它作为原方法的代替
   def invokeMethod(String name, Object args) {
        return "the method is ${name}, the params is ${args}"
   }
}
八、metaClass 为类动态添加属性或者方法
//为类动态添加一个属性
People1.metaClass.sex = 'male'

//为类动态添加一个方法
People1.metaClass.sexUpperCase = {
    -> sex.toUpperCase()
}

//为类动态添加静态方法
People1.metaClass.static.createPerson = {
    String name, int age -> new People1(name: name, age: age)
}

def p2 = new People1(name: 'zs', age: 31)
println p2.sex
println p2.sexUpperCase()
def person3 = People1.createPerson('zht', 31)
println person3.name + "," + person3.age
//metaClass 使用场景:例如final class 属性和方法的拓展
九、文件操作
文件操作
def file = new File('../helloGroovy.iml')
//groovy 逐行读取文件
file.eachLine { line ->
   println line
}
//or
// groovy 一次获取所有文本
def text = file.getText()
//or
def list = file.readLines()

//读取文件部分内容

file.withReader { reader ->
   char[] buffer = new char[100]
   reader.read(buffer)
   return buffer
}

//copy功能
def copy(String sourcePath, String desPath) {
   try {
       def desFile = new File(desPath)
       if (!desFile.exists()) {
           desFile.createNewFile();
       }

       //读取源文件内容
       new File(sourcePath).withReader { reader ->
           def lines = reader.readLines()
           desFile.withWriter { writer ->
               lines.each { line ->
                   writer.append(line + "\r\n")
               }
           }
       }
       return true
   } catch (Exception e) {
   }
}
println copy('../helloGroovy.iml', '../helloGroovy2.iml')

def saveObject(Object object, String path) {
   try {
       def desFile = new File(path)
       if (!desFile.exists()) {
           desFile.createNewFile();
       }
       desFile.withObjectOutputStream { out ->
           out.writeObject(object)
       }
       return true
   } catch (Exception e) {
   }
   return false
}

def readObject(String path){
   def obj = null
   try {
       def file = new File(path)
       if(file == null || !file.exists())
           return null
       file.withObjectInputStream { input ->
           obj = input.readObject()
       }
       return true
   } catch (Exception e) {
   }
   return false
}
json文件操作
def list = [new People1(name: "stan", age: 31),
           new People1(name: "jack", age: 30)
]

//实体对象转json
def json = JsonOutput.toJson(list)

//打印出带格式的json
println JsonOutput.prettyPrint(json) 

//json转实体对象
def jsonSlurper = new JsonSlurper()
def resultList = jsonSlurper.parse(json.getBytes())
println resultList.collect()

//也可以使用Gson
//新建libs目录,添加Gson jar包,add library 就可以使用。使用与java写法一样

//一个获取网络请求再将json转为实体的小实例
def getNetworkData(String url) {
   //发送http请求
   def connection = new URL(url).openConnection()
   connection.setRequestMethod('GET')
   connection.connect()
   def response = connection.content.text
   //将json转化为实体对象
   def jsonSlu = new JsonSlurper()
   return jsonSlu.parseText(response)
}

def resp = getNetworkData(‘XXXX')
println resp
xml文件操作

//groovy如何解析一个xml格式数据
final String xml = """
<response version-api="2.0">
 <value>
   <books id="1" classification="novel">
     <book available="20" id="1">
        <title>百年孤独</title>
        <author id="1">马尔克斯</author>
     </book >
     <book available="14" id="2">
        <title>三体</title>
        <author id="2">刘慈欣</author>
     </book >
   </books>
   <books id="2" classification="android">
     <book available="30" id="3">
        <title>第一行代码</title>
        <author id="3">郭林</author>
     </book >
     <book available="18" id="4">
        <title>疯狂Android讲义</title>
        <author id="4">李刚</author>
     </book >
     <book available="32" id="5">
        <title>第二行代码</title>
        <author id="5">郭林</author>
     </book >
   </books>
 </value>
</response>
"""

//xml解析
def xmlSlurper = new XmlSlurper()
def result = xmlSlurper.parseText(xml)
println result.value.books[0].book[0].title.text() //获取节点值
println result.value.books[1].book[0].@available //获取节点属性

//遍历所有郭林的书
def lists = []
result.value.books.each { books -> //这里省略了def
   //对书节点进行遍历
   books.book.each { book ->
       def author = book.author.text()
       if (author.equals('郭林')) {
           lists.add(book.title.text())
       }
   }
}
println lists.toListString()

//深度遍历
println result.depthFirst().findAll { book ->
   if (book.author.text() == '郭林' ? true : false) {
       return book.title.text()
   }
}

//广度遍历
println result.value.books.children().findAll { node ->
   node.name() == 'book' && node.@id == '2'
}.collect { node ->
   return node.title.text()
}

//groovy如何创建一个xml格式数据
/**
* 静态写法
* <langs type='current' count='3' mainstream='true'>
<language flavor='static' version='1.5'>java</language>
<language flavor='dynamic' version='1.6'>groovy</language>
</langs>
*/

def sw = new StringWriter()
def xmlBuilder = new MarkupBuilder(sw)//生成xml数据的核心类

//创建根节点
xmlBuilder.langs(type: 'current', count: '3', mainstream: 'true') {
   //子节点
   language(flavor: "static", version: '1.5', 'java') //language下再想要子节点,那对language做闭包就好 { }
   language(flavor: "dynamic", version: '1.6', 'groovy')
}
println sw

/**
* 实体类转为xml
*/
class Langs {
   String type = 'current'
   int count = 3
   boolean mainstream = true
   def languages = [new Language(flavor: "static", version: '1.5', value: 'java'),
                    new Language(flavor: "dynamic", version: '1.6', value: 'groovy'),]
}

class Language {
   String flavor
   String version
   String value
}

def langs = new Langs()
println xmlBuilder.langs(type: langs.type, count: langs.count, mainstream: langs.mainstream) {
   langs.languages.each { lang ->
       language(flavor: lang.flavor, version: lang.version, lang.value)
   }
}
println sw

相关文章

网友评论

      本文标题:Android Gradle(二)- groovy

      本文链接:https://www.haomeiwen.com/subject/zzgkmhtx.html