Groovy:我怎样才能从方法实现中访问在类外定义的变量/对象?

时间:2011-12-25 14:33:34

标签: groovy

以下代码段演示了我的问题:

import java.util.timer.*  

s = "Hello"
println s
class TimerTaskExample extends TimerTask {  
        public void run() {  
            //println new Date() 
            println s 
        }  
}  

int delay = 5000   // delay for 5 sec.  
int period = 10000  // repeat every sec.  
Timer timer = new Timer()  
timer.scheduleAtFixedRate(new TimerTaskExample(), delay, period)  

在我的TimerTaskExample实现中,我想访问在“全局”脚本范围中创建的s。但我得到了以下痕迹:

Hello
Exception in thread "Timer-2" 
groovy.lang.MissingPropertyException: No such property: s for class: TimerTaskExample
at         org.codehaus.groovy.runtime.ScriptBytecodeAdapter.unwrap(ScriptBytecodeAdapter.java:50)
at     org.codehaus.groovy.runtime.callsite.GetEffectivePogoPropertySite.getProperty(GetEffectivePogoPropertySite.java:86)
at     org.codehaus.groovy.runtime.callsite.AbstractCallSite.callGroovyObjectGetProperty(AbstractCallSite.java:231)
at TimerTaskExample.run(ConsoleScript2:8)

我试过谷歌,但找不到解决方案。

非常感谢!

Yu SHen

3 个答案:

答案 0 :(得分:1)

Groovy本身没有“全局”范围; IMO最清楚的是将这种“全局”保留在类中,定义为静态终结,如Java:

public class Constants {
  static final String S = "Hello"
}

println Constants.S
class TimerTaskExample extends TimerTask {  
  public void run() {  
    println Constants.S  
  }  
}  

答案 1 :(得分:1)

看起来你正在使用Groovy脚本。

方法可以访问的唯一内容是:

  • 基类
  • 定义的属性
  • MetaClass定义的动态属性
  • 绑定

脚本允许使用未声明的变量(没有def),在这种情况下,假定这些变量来自脚本的绑定,并且如果尚未存在则添加到绑定中。

name = 'Dave'
def foo() {
    println name
}

foo()

对于每个脚本,Groovy都会生成一个扩展groovy.lang.Script的类,它包含一个main方法,以便Java可以执行它。在我的例子中,我只有一个类:

public class script1324839515179 extends groovy.lang.Script {
    def name = 'Dave'
    def foo() {
        println name
    }
    ...
}

你的例子中发生了什么?您有两个类,绑定变量位于Script类中。 TimerTaskExample对s

一无所知
public class script1324839757462 extends groovy.lang.Script {
    def s = "Hello"
    ...
}

public class TimerTaskExample implements groovy.lang.GroovyObject extends java.util.TimerTask {
    void run() {
        println s
    }
    ...
}

答案 2 :(得分:1)

虽然在绑定中定义了s(没有def),但是在脚本中定义的类中无法访问它。 要访问TimerTaskExample类中的s,可以按以下步骤操作:

class TimerTaskExample extends TimerTask {  
    def binding
    public void run() {  
        println binding.s 
    }  
}  

new TimerTaskExample(binding:binding)