ScriptEngine 预定于全局变量
其实JDK ScriptEngine预定于全局变量和预定于Funciton是一样的,都需要GLOBAL_SCOPE类型的Bindings对象。想想就很简单了
Bindings globalBindings = engine.getBindings(ScriptContext.GLOBAL_SCOPE);globalBindings.put("valueName","value");
这样一来,所有createBindings得到的Bindings对象都具有一个valueName的全局变量,值是”value”字符串。只要在script中直接使用valueName变量就可以得到这个值。
很简单,但可以引申一个功能。比如,我们希望有个变量,一直保持的是当前时间的毫秒数,什么时候调用,就是什么时候的值。通常做法都是写一个 function getCurrentTimeMillis(),在调用的时候返回当前的时间。但可以简化成一个变量,用起来更爽。
事情是这样的。还是Bindings对象,这个对象是Map的子类,保存了所有运行时的变量,局部变量会在结束时候删除,全局变量一直保存。在Script运行到一处需要知道变量的值,如:
result = a + b;
a和b没有在之前的script中声明,ScriptEnging会在当前的bindings对象中找a和b的值。过程很没悬念,就是先用map的 containsKey()看看bindings中有没有一个叫a的变量。如果有,就用map中的get()方法将a的值取出来。否则会报一个“没有找到 变量的异常”(忘记英文是怎么报的了,就是这个意思)。
知道了运作方式,改出一个表示时间的变量就超easy了。
思路是这样的,实现一个Bindings的子类,覆盖get,在get某个key的时候返回特点的值。然后将这个Bindings的对象赋给GLOBAL_SCOPE,就OK了 。Code:
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("javascript");
Bindings bindings = new SimpleBindings(){
@Override//覆盖get方法
public Object get(Object key){
String k = key.toString();
if(k.equals("currentTime")){ //变量的名称是currenttime就返回当前的时间
return System.currentTimeMillis();
}else{
return super.get(key);
}
}
};
engine.setBindings(bindings, ScriptContext.GLOBAL_SCOPE);//把这个Binding对象设置成全局范围
这样在Script中只要出现currentTime这个变量,什么时候执行那么就什么时候调用Java的System.currentTimeMillis();方法。当前时间的毫秒值就得到了。
除了时间还可以引申出很多变量,比如机器IP,使用的端口,只要Java能得到的,Script就能有一个变量表示。更关键的是速度快。
变量就讲这些了,下一次再介绍调用第三方Dom4j包操作xml。
(常州java培训 http://www.thinksite.cn/list-114-1.html)