java6內建JS引擎初接觸
阿新 • • 發佈:2019-02-01
由於要用到該技術,所以寫了幾個測試,直接上程式碼。
定義外部資源E:/ScriptEngine/test01.jsif(age>=18){
print('Old enough to vote!');
}else{
print('Back to school!');
}
定義外部資源E:/ScriptEngine/test02.js
if(age<25){
riskFactor = 1.5;
}else if(noClaims){
ristFactor = 0.75;
}else{
ristFactor = 1.0;
}
定義外部資源E:/ScriptEngine/test03.js
function Hello(){}
Hello.prototype.sayHello = function(value){
println('hello!'+value);
}
var hello = new Hello();
hello.sayHello('World1');
//使用指令碼引擎執行指令碼程式 public static void test01() throws ScriptException{ // 如果呼叫者可訪問執行緒上下文 ClassLoader,則呼叫此構造方法的效果與呼叫 ScriptEngineManager(Thread.currentThread().getContextClassLoader()) 相同 //ScriptEngineManager檢索感興趣的指令碼編寫的語言的ScriptEngine物件 ScriptEngineManager manager = new ScriptEngineManager(); ScriptEngine engine = manager.getEngineByName("js");//ScriptEngine用來處理指令碼解釋和求值 engine.put("age", 26);//賦值指令碼環境中所使用的變數 engine.eval("if(age>=18){println('Old enough to vote!');}else{println('Back to school!');}");//解析 JavaScript 指令碼,對指令碼表示式進行求值 }
//使用指令碼引擎執行外部資源中的指令碼 public static void test02() throws FileNotFoundException, ScriptException{ ScriptEngineManager manager = new ScriptEngineManager(); ScriptEngine engine = manager.getEngineByName("js"); engine.put("age", 26); engine.eval(new FileReader("E:/ScriptEngine/test01.js"));//對檔案或其它外部資源中得指令碼表示式進行求值 }
//使用指令碼引擎檢索結果
public static void test03() throws FileNotFoundException, ScriptException{
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("js");
engine.put("age", 26);
engine.put("noClaims", Boolean.TRUE);
Object result = engine.eval(new FileReader("E:/ScriptEngine/test02.js"));//eval()函式返回執行指令碼後所返回的值,預設情況下,將返回上次執行的表示式的值
System.out.println(result.toString());
}
//上下文屬性的作用域
public static void test04() throws ScriptException{
ScriptEngineManager manager = new ScriptEngineManager();
Bindings globalBindings = manager.getBindings();//屬於ScriptEngineManager的全域性上下文,每個ScriptEngineManager擁有一個Bindings
globalBindings.put("name", "yangYong");
ScriptEngine engine = manager.getEngineByName("js");
Bindings globalBindings02 = engine.getBindings(ScriptContext.GLOBAL_SCOPE);//每個引擎都共有一個ScriptEngineManager的Bindings
System.out.println("name="+globalBindings02.get("name"));
System.out.println(globalBindings==globalBindings02);
ScriptContext context = engine.getContext();//每個引擎都有自己獨立的scriptContext上下文
Bindings engineDefaultBindings = engine.getBindings(ScriptContext.ENGINE_SCOPE);//每個引擎的scriptContext中都有個預設屬於自己的Bindings
engineDefaultBindings.put("gender", "男");
engine.eval("name2 = name;println(name2);",engineDefaultBindings);
engineDefaultBindings.put("name", "zhangSan");
engine.eval("name2 = name;println(name2);",engineDefaultBindings);
Bindings engineCreatBindings = engine.createBindings();//每個引擎的scriptContext中也可以新建多個屬於自己的Bindings
engineCreatBindings.put("gender", "女");
System.out.println(engineDefaultBindings==engineCreatBindings);
System.out.println(engine.getBindings(ScriptContext.ENGINE_SCOPE).get("gender"));
System.out.println(engineCreatBindings.get("gender"));
engine.eval("name2 = name;println(name2);",engineCreatBindings);
}
//java應用程式與指令碼互動
public static void test05() throws FileNotFoundException, ScriptException{
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("js");
Bindings bindings = engine.createBindings();//Bindings:KV對對映,用來在Java應用程式和javascript指令碼之間交換資訊,即上下文
bindings.put("age", 26);
bindings.put("noClaims", Boolean.TRUE);
bindings.put("riskFactor", 1.0);
engine.eval("if(age<25){riskFactor = 1.5;}else if(noClaims){ristFactor = 0.75;}else{ristFactor = 1.0;}",bindings);//必須繫結bindings執行指令碼,否則報變數未定義異常
double risk = (Double) bindings.get("riskFactor");
System.out.println(risk);
}
//使用指令碼引擎執行指令碼程式
public static void test01() throws ScriptException{
// 如果呼叫者可訪問執行緒上下文 ClassLoader,則呼叫此構造方法的效果與呼叫 ScriptEngineManager(Thread.currentThread().getContextClassLoader()) 相同
//ScriptEngineManager檢索感興趣的指令碼編寫的語言的ScriptEngine物件
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("js");//ScriptEngine用來處理指令碼解釋和求值
engine.put("age", 26);//賦值指令碼環境中所使用的變數
engine.eval("if(age>=18){println('Old enough to vote!');}else{println('Back to school!');}");//解析 JavaScript 指令碼,對指令碼表示式進行求值
}
//指令碼內部訪問java資源
public static void test06() throws ScriptException{
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("js");
engine.eval("importPackage(java.util)");//importPackage()函式允許在指令碼內部匯入java包,即可在指令碼中例項化java物件
engine.eval("today = new Date();println(today);");
engine.put("name", "ZhangSan");
engine.eval("name2 = name.toUpperCase();println(name2);");
}
//重定向指令碼輸出
public static void test07() throws IOException, ScriptException{
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("js");
PipedReader pr = new PipedReader();
PipedWriter pw = new PipedWriter(pr);
//使用者可以通過與這個 PrintWriter 連通的 PrintReader 讀取實際的輸出,使 Java 應用程式能獲取指令碼執行輸出
PrintWriter out = new PrintWriter(pw);
engine.getContext().setWriter(out);
engine.eval("println('hello from javascript!');");
BufferedReader br = new BufferedReader(pr);
System.out.println(br.readLine());
}
//可編譯且可呼叫的引擎
public static void test08() throws ScriptException{
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("js");
if(engine instanceof Compilable){//判斷指令碼引擎是否支援編譯操作
Compilable compilable = (Compilable)engine;//用來儲存編譯的結果,從而能重複呼叫指令碼而沒有重複解釋的開銷
//compile()方法將指令碼編譯成無需重新編譯就能反覆執行的CompiledScript容器
CompiledScript script = compilable.compile("if(age<25){riskFactor = 1.5;}else if(noClaims){ristFactor = 0.75;}else{ristFactor = 1.0;}");
Bindings bindings = engine.createBindings();
bindings.put("age", 26);
bindings.put("noClaims", Boolean.TRUE);
bindings.put("riskFactor", 1.0);
Object result = script.eval(bindings);//使用CompiledScript的eval()方法計算編譯後的表示式
System.out.println(result.toString());
}
}
//呼叫指令碼中的函式和方法
public static void test09() throws ScriptException, NoSuchMethodException, FileNotFoundException{
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("js");
engine.eval("function increment(i){return i+1;}");
if (engine instanceof Invocable) {//判斷指令碼引擎是否支援編譯操作
Invocable invocable = (Invocable)engine;//Invocable允許從java程式碼呼叫定義在指令碼中的單個函式
Object result = invocable.invokeFunction("increment", new Object[]{10});// 呼叫指令碼中定義的頂層程式和函式
System.out.println("result = "+result);
}
ScriptEngine engine2 = manager.getEngineByName("js");
engine2.eval(new FileReader("E:/ScriptEngine/test03.js"));
if(engine2 instanceof Invocable){
Invocable invocable = (Invocable)engine2;
invocable.invokeMethod(engine2.get("hello"), "sayHello", "yangYong");//對以前的指令碼執行中已經編譯的指令碼物件(以 ScriptEngine 的狀態保持)呼叫某一方法
}
}
定義java檔案Hello.java
public interface Hello {
public int increment(int value);
public void sayHello(String name);
}
//呼叫指令碼中的函式和方法並將他們作為java程式中的介面實現
public static void test10() throws FileNotFoundException, ScriptException{
ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("js");
engine.eval("function increment(i){return i+1;}");
if (engine instanceof Invocable) {
Invocable invocable = (Invocable)engine;
Hello hello = invocable.getInterface(Hello.class);//返回一個介面的實現,該介面使用直譯器中編譯的函式
Object result = hello.increment(2);
System.out.println("result = "+result);
}
engine.eval(new FileReader("E:/ScriptEngine/test03.js"));
if(engine instanceof Invocable){
Invocable invocable2 = (Invocable)engine;
Hello hello = invocable2.getInterface(engine.get("hello"), Hello.class);// 返回一個介面的實現,該介面使用直譯器中已編譯指令碼物件的成員函式
hello.sayHello("zhangSan");
}
}