首页 文章

Gradle / Groovy闭包范围混乱

提问于
浏览
2

我是Gradle / Groovy的新手,在嵌套的闭包中遇到了变量名称解析的问题 . 我有一个定义一些属性的自定义任务类,我使用闭包实例化该类型的潜在多个任务 . 这个闭包定义了一个名为与自定义任务类中的一个属性相同的变量,并且我遇到了一些奇怪的行为,这似乎违背了Groovy语言指南中定义的内容 . 有人可以回答下面代码中的问题吗?

class Something extends DefaultTask {
    def thing = "a"
}
/*
def thing = "b" // produces the error message:
                // > Could not find method b() for arguments [build_63hfhkn4xq8gcqdsf98mf9qak$_run_closure1@70805a56] on root project 'gradle-test'.
                // ...why?
*/
(1..1).each {
    def thing = "c"
    task ("someTask${it}", type: Something) {
        println resolveStrategy == Closure.DELEGATE_FIRST // prints "true"
        println delegate.class // prints "class Something_Decorated"
        println thing // prints "c" shouldn't this be "a" since it's using DELEGATE_FIRST?
        /*
        println owner.thing // produces the error message:
                            // > Could not find property 'thing' on root project 'gradle-test'
                            // shouldn't the "owner" of this closure be the enclosing closure?
                            // in that case shouldn't this resolve to "c"
        */
    }
}

EDIT: 出于某种原因,将所有 def 更改为 String 然后又回到 def 后,我无法再复制 def thing = "b" 行,从而产生奇怪的错误

1 回答

  • 1

    代码打印 c 因为名为 thing 的变量在闭包的词法范围内声明 . 这意味着闭包只能使用此变量的值 . 什么会有效:

    • 重命名闭包中定义的 thing 变量 .

    • 通过 delegate 明确引用 thing

    println delegate.thing

相关问题