前言:
大家回想一下自己第一次接觸Gradle
是什么時候?
相信大家也都是和我一樣,在我們打開第一個AS項目的時候,
發現有很多帶gradle字樣的文件:setting.gradle, build.gradle,gradle.warpper
,以及在gradle
文件中各種配置,
這些都是啥wy啊。。
特別對于一些小公司開發人員,因為接觸架構層面的機會很少,可能在使用AS幾年后都不一定對Gradle
有太多深入了解,這是實話,因為筆者就是這么過來的。。
而Gradle
又是進階高級
開發的必經之路。
好了,接下來進入正題,此系列筆者會由淺入深的方式,帶領大家來了解下,Gradle
背后究竟有哪些奧秘。
Gradle`定義:
很多開發喜歡把Gradle
簡單定義為一種構建工具,和ant,maven
等作用類似,
誠然Gradle確實是用來做構建,但是如果簡單得把Gradle拿來做構建,就太小看Gradle了.
筆者更愿意將Gradle看做一種編程框架
。在這個框架中,你可以做很多ant,maven等常用構建工具做不了的事情,
如將自己的任務task集成到構建生命周期中,完成文件拷貝,腳本編寫等操作。
Gradle
優缺點:
相較早期的構建工具:ant,maven等。
優點如下:
-
1.使用DSL Grovvy語言來編寫: :了解ant的同學應該都知道:ant使用的是xml配置的模式,而Gradle使用的是
表達性的Groovy
來編寫,Groovy同時
支持面向對象和面向過程
進行開發,這個特性讓Groovy
可以寫出一些腳本的任務,這在傳統ant,maven上是不可能實現的 -
2.基于java虛擬機: :
Groovy
是基于jvm
的語言,groovy
文件編譯后其實就是class文件,和我們的java
一樣。
所以在gradle構建過程中,我們完全可以使用java/kotlin去編寫我們的構建任務以及腳本,極大的降低我們學習的成本。
- 3.Gradle自定義task :可以構建自己的任務,然后掛接到gradle構建
生命周期
中去,這在ant,maven上也是不可能實現的, - 4.擴展性好 :gradle將關鍵配置扔給我們開發者,開發者配置好任務后,無需關心gradle是如何構建的。
缺點:
用過gradle都知道,低版本gradle的項目在高版本的gradle中經常出現很多莫名其妙的錯誤,
向后兼容性較差
。
介紹了那么多,下面正式來講解今天的主角:Groovy
Groovy
語法詳解
因為我們的Groovy和java很類似,所以這里我們以和java的差異性進行展開,這樣可以更好的去理解groovy語法
1.編程方式
java
:面向對象
groovy
:面向對象和過程
groovy不僅可以和java一樣面向對象進程編程,也可以創建面向過程的腳本開發:
package variable
int i1 = 1
double d1 = 1
println(i1.class)
println(d1.class)
2.語法簡潔
-
2.1:
分號
:groovy默認行尾不加分號 -
2.3:
setter/getter
:groovy默認給我們類內部屬性,創建setter和getter方法,外部只需要使用屬性名訪問即可 -
2.4:
字符串
:groovy支持三種類型的字符串表達式定義-
單引號
:不能使用+號代替,如果你確定這個字符串只是使用,不會更改那么你可以這么定義//單引號定義不可更改內容 def s1 = 's1' //使用轉移字符://s'a'2 def s2 = 's\\'a\\'2'
-
雙引號
:在字符串內部可以使用{2+3}"
-
三引號:支持自動換行
一般我們會使用前兩種,最后一種很少用
-
-
2.5:使用弱聲明:
def
,編譯過程會自動類型檢測,這個屬性和kotlin的val/var
很像。java
def str = "this is groovy str"
3.方法
3.1: 方法定義
groovy中:使用def聲明方法的返回值,如果沒有返回值,則默認返回一個null
def echo(){
return "echo this"
}
3.2:方法參數:
groovy傳入的參數可以省略參數類型,且可以設置參數默認值,有默認值調用的時候可以省略帶默認值的參數
def echo(message,name = '123'){
return "echo:"+message +name
}
調用:echo("hello groovy")
3.3:方法返回值
使用return返回,如果省略return,則返回的是最后方法最后一行
def echo(){
"echo this"
}
println echo()
結果:"echo this"
3.4:方法調用流程
groovy方法調用不像我們java,其內部給我們創建了很多判斷的分支,支持在運行期動態添加方法
下面是groovy方法調用流程圖:
gradle方法.png
- 3.4.1:
invokeMethod
:對于類中所有調用方法:包括已定義和未定義方法,都會走到這個invokeMethod方法中,需要實現:GroovyInterceptable
接口這個方法可以在我們方法執行器做一些方法類型參數等判斷
class Person implements GroovyInterceptable{
def name
def age
def score
@Override
Object invokeMethod(String methodName, Object args) {
return "this method name is $methodName"
}
def helloGroovy(){
return "hello $name"
}
}
調用:
def per = new Person(name: 'lily')
println per.helloGroovy()
println per.helloGroovy1()
結果:
this method name is helloGroovy
this method name is helloGroovy1
可以看到所有的方法都被分派到invokeMethod且沒有執行后續流程:這個和我們java運行期動態代理模式
有點類似,我們可以在invokeMethod
中實現一些AOP
的架構,如打印所有方法的統一日志
等。
- 3.4.2:
methodMissing
:對于未定義的方法,如果重寫這個methodMissing,則會調用這個方法Object methodMissing(String name, Object args) { println "methodMissing : $name" }
最新版本groovy未發現這個方法,應該是被去掉了 。不過這個對于我們開發關系不大
- 3.4.3:
元編程metaClass
:可以在運行期注入屬性和方法包括靜態方法,這個特性就比較厲害了,對于一些第三方類庫,可以使用這個方式在運行期動態創建方法,相當于對類庫進行了一次擴展
學習過kotlin的都知道:擴展函數和擴展屬性,差不多是這個用法
注入屬性:
class Person implements{
def name
def age
}
//注入屬性
Person.metaClass.sex = 'male'
def person1 = new Person(name: 'yuhb',age: 29)
println person1.sex
結果:male
注入方法:
//注入方法,使用閉包
Person.metaClass.sexUpperCase = { ->
sex.toUpperCase()
}
println person1.sexUpperCase()
結果:MALE
4.集合
4.1:集合分類
groovy中集合有三種:
列表List
:對應java中的List
def list = [1, 2, 3, 4,5,6]
映射Map
:對應java中的Map
def map = [key1:'value',key2:'value2']
注意:map中的key默認都是String類型的字符串,即使我們自己沒加,編譯器也會給我們加上
范圍Range
:groovy中獨有
def range = [1..100]
range其實就是指定了一個list的范圍,而不需要一個一個列出來
如下使用:
/******switch case*****/
println getGrade(87)
def getGrade(def number){
def result
switch (number){
case 0..<60:
result = "不及格"
break
case 60..<80:
result = "及格"
break
case 80..100:
result = "優"
break
default:
result = "不確定"
break
}
result
}
4.2:集合遍歷
所有集合都可以使用each
和eachWithIndex
進行遍歷,當然也可以使用java中的for循環,但在groovy中一般不這么用
class Stu{
def name
def age
@Override
String toString() {
return "name:$name age:$age"
}
}
def students = [
1:new Stu(name: 'lily',age: 12),
2:new Stu(name: 'lucy',age: 13),
3:new Stu(name: 'tom',age: 14),
4:new Stu(name: 'sara',age: 15)
]
/**1.遍歷**/
students.each {
println it.value.toString()
}
/**帶索引遍歷**/
students.eachWithIndex{ Map.Entry<Integer, Stu> entry, int i ->
println "index:$i key:$entry.key value:$entry.value "
}
4.3:查找
groovy中查找提供了find
和findAll
方法,用法如下:
//find查找一項
def stu1 = students.find {
it.value.age>12
}
println stu1.value
//findAll查找所有項
def stus = students.findAll {
it.value.age>12
}
//count:統計個數
def stuCount = students.count {
it.value.age>12
}
//多重查找
def stu2 = students.findAll {
it.value.age>12
}.collect {
it.value.name
}
4.4:分組:
使用groupBy
關鍵字
def group = students.groupBy {
return it.value.age>12?"大":"小"
}
4.5:排序:
使用sort
def sort = students.sort {student1,student2 ->
student1.value.age == student2.value.age?0:student1.value.age < student2.value.age?-1:1
}
-
JAVA
+關注
關注
19文章
2972瀏覽量
104867 -
開發
+關注
關注
0文章
370瀏覽量
40872 -
gradle
+關注
關注
0文章
26瀏覽量
728
發布評論請先 登錄
相關推薦
評論