其實(shí)closure中的delegate類(lèi)似于類(lèi)中的this,讓我們看一個(gè)小例子,大家就清楚了 :)
class?DelegateDemo?{
????String?author?=?"山風(fēng)小子"
????def?someMethod(closure)?{
????????println?"The?original?delegate?of?closure?is:?${closure.delegate}"
????????closure.delegate?=?this
????????closure()
????}
????def?greet(words)?{
????????println?words
????}
}
def?delegateDemo?=?new?DelegateDemo()
delegateDemo.someMethod?{
????//?此處的delegate可以省略
????delegate.greet("Hello,?"?+?delegate.author)
}
delegateDemo.someMethod?{
????//?省略了delegate
????greet("Hello,?"?+?author)
}
運(yùn)行結(jié)果:????String?author?=?"山風(fēng)小子"
????def?someMethod(closure)?{
????????println?"The?original?delegate?of?closure?is:?${closure.delegate}"
????????closure.delegate?=?this
????????closure()
????}
????def?greet(words)?{
????????println?words
????}
}
def?delegateDemo?=?new?DelegateDemo()
delegateDemo.someMethod?{
????//?此處的delegate可以省略
????delegate.greet("Hello,?"?+?delegate.author)
}
delegateDemo.someMethod?{
????//?省略了delegate
????greet("Hello,?"?+?author)
}
The?original?delegate?of?closure?is:?Script16@13e6346
Hello,?山風(fēng)小子
The?original?delegate?of?closure?is:?Script16@13e6346
Hello,?山風(fēng)小子
注意:可能大家運(yùn)行結(jié)果中的‘Script16@13e6346’部分各不相同,但都是Script開(kāi)始的一個(gè)類(lèi)名(我這里的類(lèi)名為Script16)Hello,?山風(fēng)小子
The?original?delegate?of?closure?is:?Script16@13e6346
Hello,?山風(fēng)小子
在類(lèi)的實(shí)例方法中調(diào)用方法和引用屬性時(shí),我們可以省略方法或?qū)傩郧皌his(比如this.method(),this.property可簡(jiǎn)寫(xiě)為method(),property),
表示調(diào)用或引用的是本實(shí)例的方法或?qū)傩浴?br />類(lèi)似地,在closure中調(diào)用方法和引用屬性時(shí),我們也可以省略方法和屬性前的delegate,
表示調(diào)用或引用的是本closure的方法或?qū)傩裕ǘ鴆losure通過(guò)delegate隱式變量將方法調(diào)用和變量引用‘委派’給了delegate引用的那個(gè)對(duì)象)
那closure的delegate的默認(rèn)值是什么呢?默認(rèn)值是closure所在context中的this(為了方便理解起見(jiàn),可以暫時(shí)這么記憶,因?yàn)閏losure套closure的情況不是很多見(jiàn)。其實(shí)closure的delegate的默認(rèn)值是closure的隱式變量owner,而owner通常引用closure所在context中的this,除非closure所處的context又是個(gè)closure,那么owner引用的就是那個(gè)外層的closure,關(guān)于closure中的owner,我將在下篇文章《Groovy解惑——closure中的owner》中進(jìn)行講解),讓我再用一個(gè)例子來(lái)說(shuō)明一下吧:
class?DelegateDemo?{
????String?author?=?"山風(fēng)小子"
????def?someMethod2(closure)?{
????????println?"The?original?delegate?of?closure?is:?${closure.delegate}"
????????//?無(wú)需設(shè)置closure.delegate,因?yàn)閏losure的delegate默認(rèn)值已經(jīng)是DelegateDemo.this
????????//closure.delegate?=?this
????????closure()
????}
????def?greet(words)?{
????????println?words
????}
????def?test()?{
????????def?delegateDemo?=?new?DelegateDemo()
????????//?傳入someMethod2的closure?{
}?所處的context的this是DelegateDemo.this
????????//?所以closure的delegate的默認(rèn)值也是DelegateDemo.this
????????delegateDemo.someMethod2?{
????????????//?此處的delegate可以省略
????????????delegate.greet("Hello,?"?+?delegate.author)
????????}
????????delegateDemo.someMethod2?{
????????????//?省略了delegate
????????????greet("Hello,?"?+?author)
????????}
????}
}
def?dd?=?new?DelegateDemo()
dd.test()
運(yùn)行結(jié)果:????String?author?=?"山風(fēng)小子"
????def?someMethod2(closure)?{
????????println?"The?original?delegate?of?closure?is:?${closure.delegate}"
????????//?無(wú)需設(shè)置closure.delegate,因?yàn)閏losure的delegate默認(rèn)值已經(jīng)是DelegateDemo.this
????????//closure.delegate?=?this
????????closure()
????}
????def?greet(words)?{
????????println?words
????}
????def?test()?{
????????def?delegateDemo?=?new?DelegateDemo()
????????//?傳入someMethod2的closure?{

????????//?所以closure的delegate的默認(rèn)值也是DelegateDemo.this
????????delegateDemo.someMethod2?{
????????????//?此處的delegate可以省略
????????????delegate.greet("Hello,?"?+?delegate.author)
????????}
????????delegateDemo.someMethod2?{
????????????//?省略了delegate
????????????greet("Hello,?"?+?author)
????????}
????}
}
def?dd?=?new?DelegateDemo()
dd.test()
The?original?delegate?of?closure?is:?DelegateDemo@1b5d2b2
Hello,?山風(fēng)小子
The?original?delegate?of?closure?is:?DelegateDemo@1b5d2b2
Hello,?山風(fēng)小子
注意DelegateDemo.this是Java中的表示方法,在Groovy并不支持,這么寫(xiě)是為了方便Java開(kāi)發(fā)人員理解 :)Hello,?山風(fēng)小子
The?original?delegate?of?closure?is:?DelegateDemo@1b5d2b2
Hello,?山風(fēng)小子
由于第一個(gè)例子中的closure所處的context中的this是Script16.this,類(lèi)Script16是沒(méi)有author屬性和greet方法的,所以我們必須設(shè)置delegate
希望經(jīng)過(guò)我這么一解釋?zhuān)蠹覍?duì)closure的delegate有所認(rèn)識(shí),清楚區(qū)分delegate和this :)
附:朝花夕拾——Groovy & Grails