2013-07-16 40 views
1

在搖籃腳本我有一個代表一個Groovy閉包,我創建了一個函數調用該委託方法如下所述:從Groovy中的函數調用閉包的委託方法?

// Simplified example 
ant.compressFiles() { 
    addFile(file: "A.txt") 
    addFile(file: "B.txt") 
    addAllFilesMatching("C*.txt", getDelegate()) 
} 

def addAllFilesMatching(pattern, closureDelegate) { 
    // ... 
    foundFiles.each { 
     closureDelegate.addFile(file: it) 
    } 
} 

是否有可能做這更漂亮的方法,而不用將代理傳遞給函數?是否有可能以某種方式擴展委託新的方法?

回答

0

這可以通過創建一個返回Closure功能來解決:

ant.compressFiles() addAllFilesMatching("A.txt", "B.txt", "C*.txt") 

Closure addAllFilesMatching(String... patterns) { 
    // Calculate foundFiles from patterns... 
    return { 
     foundFiles.each { foundFile -> 
      addFile(file: foundFile) 
     } 
    } 
} 
0

你可以先宣佈關閉,設置其delegateresolveStrategy,然後把它傳遞給each

def addAllFilesMatching(pattern, delegate) { 

    def closure = { 
    addFile file: it 
    } 

    closure.delegate = delegate 
    closure.resolveStrategy = Closure.DELEGATE_FIRST 

    foundFiles = ["a.txt", "b.txt", "c.txt", "d.txt"] 

    foundFiles.each closure 
} 
+0

可能的工作,但由於它需要更多的代碼,我仍然需要委託傳遞給函數,我不真的認爲這不合格更漂亮。 –

0

這個怎麼樣?

這是對WillP答案的微小修改(這是絕對正確的,應該這樣做),應該更漂亮一些(根據您的請求),因爲它使用閉包而不是方法。

def addAllFilesMatching = {pattern -> 
    // ... foundFiles based on pattern 
    foundFiles.each { 
     delegate.addFile(file: it) 
    } 
} 

ant.compressFiles() { 
    addFile(file: "A.txt") 
    addFile(file: "B.txt") 

    addAllFilesMatching.delegate = getDelegate() 
    addAllFilesMatching("C*.txt") 
} 
+0

'delegate.addFile'可能只是'addFile',對吧?雖然它更好,但我仍然認爲在代碼複雜性方面這是一個很大的改進。我希望有一些神奇的方法可以讓我的函數訪問委託(或類似的),但也許並不存在。 –

+0

@DavidPärsson那麼當委託在閉包中被操縱時,會有很大的區別。在Groovy控制檯或Groovy Web控制檯中嘗試[運行此示例](http://paste.ubuntu.com/5881575/)以查看區別。 – dmahapatro