2012-09-19 30 views
3

有在Groovy的方式來代替,如下面的一些代碼:Groovy的DSL - 快捷方式創建對象

Task a = new Task('a') 
Process p = new Process('p') 

的東西更容易,如:

task a 
process p 

其中taskprocess可方法調用來創建對象並將其返回或添加到腳本Map中。

我現在的主要問題是我不能使用a,因爲它沒有定義。

回答

5

要創建對象併爲其命名而不分配給變量,可以使用綁定。創建並保留對閉包的綁定的引用,並使實用方法taskprocess將新實例與名稱相關聯。例如:

def scriptBinding = new Binding() 

def task = { String name -> 
    scriptBinding[name] = new Task(name) 
} 
def process = { String name -> 
    scriptBinding[name] = new Process(name) 
} 

def script = { 
    task 'a' 
    process 'b' 

    println a 
    println b 
} 
script.binding = scriptBinding 
script() 

請注意,您必須引用ab因此它們被解釋爲字符串,而不是不確定的變量。如果您想省略引號,則可以使用評價未定義的符號,它們的字符串表示像這樣的自定義綁定對象:

class SymbolAsStringBinding extends Binding { 
    Object getVariable(String name) { 
     try { 
      super.getVariable(name) 
     } catch (MissingPropertyException e) { 
      name 
     } 
    } 

    boolean hasVariable(String name) { 
     true 
    } 
} 

隨着那此外,您可以編寫腳本:

def script = { 
    task a 
    process b 

    println a 
    println b 
} 
+2

您也可以使用'高清propertyMissing(列P){P}'以避免自定義綁定並已經有變量解析爲一個字符串 – Will

1

試試這個:

class Task { 
    String name 
    Task(name) { this.name = name } 
    String toString() { "task: $name".toString() } 
} 

def propertyMissing(String name) { this.getBinding()[name] = name } 

def task(name) { this.getBinding()[name] = new Task(name) } 

task a 
println a 

這將產生:

task: a 

本質上講,當你到達

task a 

聲明propertyMissing()將投入綁定命名a與內容它的名字的變量。 後來task()功能將替換爲新的任務傳遞姓名失蹤varible的名稱綁定變量aa