我是Groovy的新手,并且对闭包中的变量范围感到困惑。
例如,下面的代码工作正常。它打印两个5。
def x = 10
def y = 25
def myfunc(x) {
return {
println(x)
insideFunc(x)
}
}
def insideFunc(x) {
println(x)
}
closureFunc = myfunc(5)
closureFunc.call()
但是下面的代码会显示错误: groovy.lang.MissingPropertyException:没有这样的属性:x表示类。为什么?我认为insideFunc可以访问全局变量'x'?
def x = 10
def y = 25
def myfunc(x) {
return {
println(x)
insideFunc()
}
}
def insideFunc() {
println(x)
}
closureFunc = myfunc(5)
closureFunc.call()
答案 0 :(得分:1)
第二个脚本的问题是由于脚本的执行方式。 x
在run
方法中是本地范围的。当人们看到脚本在执行时变成什么时,这应该变得明显。从groovyConsole,以下是“Inspect AST”显示的内容(这是不完整的):
public class script1526974299557 extends groovy.lang.Script {
...
public java.lang.Object run() {
java.lang.Object x = 10
java.lang.Object y = 25
closureFunc = this.myfunc(5)
closureFunc.call()
}
public java.lang.Object myfunc(java.lang.Object x) {
return {
this.println(x)
this.insideFunc()
}
}
public java.lang.Object insideFunc() {
this.println(x)
}
}
显然,x
超出了insideFunc()
的范围。
然而,关于第一个版本,事情看起来不同。当insideFunc()
接受一个参数时,它的参数由闭包进行:
public class script1526974614817 extends groovy.lang.Script {
...
public java.lang.Object myfunc(java.lang.Object x) {
return {
this.println(x)
this.insideFunc(x)
}
}
public java.lang.Object insideFunc(java.lang.Object x) {
this.println(x)
}
}