Groovy閉包詳解


Groovy閉包是一種可執行代碼塊的方法,閉包也是對象,可以向方法一樣傳遞參數,因為閉包也是對象,因此可以在需要的時候執行,像方法一樣閉包可以傳遞一個或多個參數。閉包最常見的用途就是處理集合,可以遍歷某個集合,並將對元素的操作作用於遍歷出來的集合元素上。

閉包的語法是{comma-separated-form-parameter-list ->statement-list},如果不需要形參則可以省略->間隔符

下面是最簡單的閉包形式

1 def cols={
2             println "Hello Word!"
3         }
4cols.call()

帶參閉包

1 def cols2={param->
2             println "${param}"
3         }
4cols2("哈哈")

單個隱參數

def cols3={
            println "Hello ${it}"
        }
 cols3("二狗")

閉包在定義的時候就能訪問外部的屬性值

1 def greeting="Hello"
2 def cols4={param->
3 println "${greeting},${param}"
4  }
5  cols4("二狗")

閉包也常用在集合中,使用閉包可以更加的高效的遍歷集合的元素,並將閉包應用到每個元素中去。

1 [1,2,3,4,5].each { println it}
2 ['張三':100,'李四':200,'王五':300].each { println it}
3 ['張三':100,'李四':200,'王五':300].each { println it.key+":"+it.value}

也可以根據條件對集合進行篩選

1  [1,2,3,4].each {num-> if(num%2==0) println num}
2 ['張三':100,'李四':200,'王五':300].each {if(it.value==200) {println it}}

find方法返回集合中符合某個判斷標准的第一個值,在閉包中,集合元素使用的判斷條件必須是bool表達式

1 def num = [1,2,3,4].find{p->p>2}
2 println num
3 def map=['張三':100,'李四':200,'王五':300].find {it.value>100}
4 println map

findAll方法是遍歷所有的元素並返回一個符合條件的列表

1 num = [1,2,3,4].findAll {p->p>2}
2 println num
3 map = ['張三':100,'李四':200,'王五':300].findAll {it.value>100}
4 println map

collect用法:collect將遍歷某個集合,並使用閉包中的變換方法將集合中的元素轉換成一個新值,collect方法返回的是由轉換后的值所組成的列表

1 def  staff= ["李銘":10,"李浩":20,"二狗":50]
2 list=staff.collect {e->++e.value}
3 println "staff:${list}"
4 staff = staff.collect {e->++e.value;return e}
5 println staff

inject用法:inject可用於遍歷集合,首先將需要傳遞的值和集合中遍歷出來的元素傳給閉包,此時其傳遞的值將作為一個處理結果然后在和下一個集合元素一起傳給閉包,依次類推

1 def factories = [2,3,4,5].inject(1){p,e->p*e}
2 println "factories1:${factorials}"
3 list = [2,3,4,5]
4 def clos6 = {p,e->p*e}
5 factories = list.inject (1,clos6)
6 println "factories2:${factories}"

閉包可以作為方法的參數使用

 1 def filter(list ,predicate){
 2  return list.findAll(predicate)
 3 }
 4 def isEven={x-> return (x%2==0)}
 5 def isOdd={x-> return !isEven(x)}
 6 def table =[11,12,13,14]
 7 def evens = filter(table,isEven)
 8 def odds = filter(table,isOdd)
 9 println "even:${evens}"
10 println "odds:${odds}"

閉包也可以作為另一個閉包的參數使用

 1 def takewhile = { predicate, list ->
 2 def reslut = []
 3 for (element in list) {
 4 if (predicate(element)) {
 5 reslut << element
 6  }
 7 }
 8 return reslut
 9  }
10 def isEven = { x -> return (x % 2 == 0)}
11 def isOdds = { x -> return !isEven(x) }
12 def table = [45, 65, 81, 15, 22, 16]
13 def evens = takewhile(isEven, table)
14 println evens
15 def odds = takewhile(isOdds, table)
16 println odds

閉包作為返回值

1 //定義一個函數,函數的返回值是個閉包
2 def twice(x)
3 { return {y-> return x*y}}
4 //定義一個閉包接收函數的返回值,閉包里面的返回值是兩個參數的乘積
5 def multiply =twice(2)
6 //閉包所帶的參數就是twice()函數里面的返回值里面的參數
7 println "multiply(4):${multiply(4)}"

使用Groovy閉包進行選擇排序

 1 //選擇排序
 2         //定義一個閉包select
 3         def select={list->
 4             //定義swap閉包實現集合元素的交換
 5             def swap={
 6                 x,y,slist->
 7                     def temp=slist[x]
 8                     slist[x]=slist[y]
 9                     slist[y]=temp
10 
11             }
12             //定義minmos閉包選取集合中最小元素的坐標
13             def minmos={
14                 //From作為起始坐標,將以From為坐標的元素與集合中的其他元素進行大小比較
15                 mlist,From ->
16                     def mopos=From
17                     def next=From+1
18                 for (j in next..<mlist.size()){
19                     //如果有元素比起始坐標的元素小則將坐標進行調換,最終篩選出來的mopos坐標是元素最小的坐標
20                      if (mlist[j]<mlist[mopos])
21                          mopos=j
22 
23                 }
24                     return mopos
25             }
26             //從第一個坐標下的元素開始與其他元素進行比較,依次循環
27             for (i in 0..list.size()-1){
28                 def pos=minmos(list,i)
29                 swap(i,pos,list)
30             }
31             return list
32         }
33         table=[10,5,7,6,8,4,5]
34 
35         println select(table)

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM