zoukankan      html  css  js  c++  java
  • 雷锋推到雷峰塔,Java implements Javascript。

    最近遇到这么一个问题,如何让用户在软件中自定义函数。

    举个例子,使用Java做一个小的监控系统,用户A希望CPU超过90%的时候报警,B用户希望内存超过90%的时候报警,C用户希望CPU超过90%或者内存超过80%的时候报警,D用户希望CPU超过60%且硬盘剩余小于10%的时候报警……

    程序员之力有限,而用户之欲无魇。以开发追需求,如抱薪救火,不妨让用户自己定义报警的规则。

    我们当然不需要为此开发一种脚本语言,我觉得JavaScript就是一种不错的语言。我们以一个单输入单输出的函数为例讲解如何使用雷锋来推倒雷峰塔……不对,用Java解析JavaScript。

    首先我们新建一个Java工程(完整代码见最后)。

    随后新建一个JavaScript解析器:

    ScriptEngineManager manager = new ScriptEngineManager();
    ScriptEngine engine = manager.getEngineByName("javascript");

    加载我们的脚本:

    脚本长这样:

    function (x){
        return x+1;
    };

    加载之:

    String js_code = readToString("scripts/user_define.js");

    随后尝试处理:

    try {
        engine.put("udfun", engine.eval(js_code));
        for (int i = 1; i < 10; ++i) {
            engine.put("val", i);
            System.out.printf("f(%d)=%f
    ",i,engine.eval("udfun(val);"));
        }
    } catch (ScriptException e) {
        e.printStackTrace();
    }

    可以看到我们先用了一个 engine.put("udfun", engine.eval(js_code));   加载函数,这样避免反复解析函数,随后不停地将数值put到js引擎中去,最后输出相应的结果。

    只要修改相应的JavaScript脚本就可以加载不同的配置。

    软件中大多数不确定的,且执行频率不是特别高的,性能要求不高的地方都可以这样留个口子。

    附上完整的Java代码:

     1 package javascriptevaltest;
     2 
     3 import java.io.File;
     4 import java.io.FileInputStream;
     5 import java.io.FileNotFoundException;
     6 import java.io.IOException;
     7 import java.io.UnsupportedEncodingException;
     8 import javax.script.ScriptEngine;
     9 import javax.script.ScriptEngineManager;
    10 import javax.script.ScriptException;
    11 
    12 public class JavascriptEvalTest {
    13 
    14     public static void main(String[] args) {
    15         ScriptEngineManager manager = new ScriptEngineManager();
    16         ScriptEngine engine = manager.getEngineByName("javascript");
    17         
    18         String js_code = readToString("scripts/user_define.js");
    19         try {
    20             engine.put("udfun", engine.eval(js_code));
    21             for (int i = 1; i < 10; ++i) {
    22                 engine.put("val", i);
    23                 System.out.printf("f(%d)=%f
    ",i,engine.eval("udfun(val);"));
    24             }
    25         } catch (ScriptException e) {
    26             e.printStackTrace();
    27         }
    28     }
    29 
    30     public static String readToString(String fileName) {
    31         String encoding = "ISO-8859-1";
    32         File file = new File(fileName);
    33         Long filelength = file.length();
    34         byte[] filecontent = new byte[filelength.intValue()];
    35         try {
    36             FileInputStream in = new FileInputStream(file);
    37             in.read(filecontent);
    38             in.close();
    39         } catch (FileNotFoundException e) {
    40             e.printStackTrace();
    41         } catch (IOException e) {
    42             e.printStackTrace();
    43         }
    44         try {
    45             return new String(filecontent, encoding);
    46         } catch (UnsupportedEncodingException e) {
    47             System.err.println("The OS does not support " + encoding);
    48             e.printStackTrace();
    49             return null;
    50         }
    51     }
    52 
    53 }
    View Code

    JavaScript代码在上面,略。

  • 相关阅读:
    Leetcode 122. Best Time to Buy and Sell Stock II
    Leetcode 337. House Robber III
    Leetcode 213. House Robber II
    java 常用正则表达式总结
    eclipse异常解决:Errors occurred during the build.........
    关于匿名内部类的理解!
    接口/抽象类的思考
    IO流对文件的读取操作
    标准类的建立,以及用集合对标准类中的元素进行存取操作
    利用集合进行对元素的添加和删除
  • 原文地址:https://www.cnblogs.com/TsingJyujing/p/6234952.html
Copyright © 2011-2022 走看看