将简单的表达式语言放入java中

时间:2011-06-08 20:46:31

标签: java expression

在我的Java应用程序中,用户可以指定如何从一系列元数据字段中命名文件。即

%artist% - %album% - %disctotal%

然后我的代码解析这些字段并重新编辑文件。但是我希望用户能够使用'表达语言',这样他们可以说:

$if(%disctotal% >= 01,%discno%) 

使用ifelse,比较长度和大小写等。

我不想从头开始写这个,有什么东西可以提供给我,我可以插入到我的代码中吗?

编辑:我认为我有一些很好的回复,但我的知识让我失望。让我们简化我希望用户能够编写的问题

$ if(%disctotal%> = 01,%discno%)

进入gui的一个领域。

然后在我的Java代码中,我希望能够将此表达式应用于一组文件,因此对于每个文件,我都具有disctotal的值,并且discno但是我希望能够将表达式转换为某些内容像

if(discTotal> = 1) {      返回discNo } 其他 {      返回“” }

我不想做的是编写识别字符串的代码(“ $ if(%disctotal%> = 01,%discno%)“是一个if语句,因为这很难做。

然后扩展这个我希望表达式允许诸如大写字段,检查字段长度等内容。

或者:也许它应该以这种方式工作,用户输入表达式,然后在每个文件的日后,Java代码用实际值替换每个变量

即 $ if(%disctotal%> = 01,%discno%) - > $ if(2> = 01,1)

然后将其传递给exopression语言进行解析并给出结果,

这是Javascript的想法吗?

4 个答案:

答案 0 :(得分:8)

如何使用JavaScript engine that is bundled with Java 1.6

您可以看到如何传递所有参数:

ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine engine = manager.getEngineByName("JavaScript");
engine.put("artist", artist);
...

您可以使用

回读该值
ScriptEngine.get(...)

胶水的最后一点是用函数声明包围用户的表达式,并编写一个调用该函数的表达式并将结果赋值给一个众所周知的变量。

所以要开始试验,让我们有一个函数来测试表达式:

private static void printResult(final ScriptEngine jsEngine, String name, String expr) throws ScriptException {
    Object result = jsEngine.eval(expr);
    System.out.println(name + " result: " + result + "; expr: " + expr);
}

现在让我们称之为:

public static void main(String[] args) throws Exception {
    ScriptEngineManager sem = new ScriptEngineManager();
    ScriptEngine jsEngine = sem.getEngineByName("JavaScript");
    printResult(jsEngine, "Hello World", "'Hello World'");
    printResult(jsEngine, "Simple Math", "123 + 456");
}

这会产生:

Hello World result: Hello World; expr: 'Hello World'
Simple Math result: 579.0; expr: 123 + 456

现在让我们试试你的用例:

public static void main(String[] args) throws Exception {
    ScriptEngineManager sem = new ScriptEngineManager();
    ScriptEngine jsEngine = sem.getEngineByName("JavaScript");

    String expr = "artist + '-' + album + (disktotal > 1 ? ('-D' + diskno) : '')";

    jsEngine.put("artist", "U2");
    jsEngine.put("album", "The Joshua Tree");
    jsEngine.put("disktotal", 1);
    jsEngine.put("diskno", 1);
    printResult(jsEngine, "Single Disk", expr);

    jsEngine.put("artist", "Tori Amos");
    jsEngine.put("album", "To Venus and Back");
    jsEngine.put("disktotal", 2);
    jsEngine.put("diskno", 2);
    printResult(jsEngine, "Muti-Disk", expr);
}

产生结果:

Single Disk result: U2-The Joshua Tree; expr: ...
Muti-Disk result: Tori Amos-To Venus and Back-D2; expr: ...

注意Tori最后有'D2'。

答案 1 :(得分:2)

我会调查FreeMarker。这是一个模板引擎。你可以将带有el结构的字符串传递给Freemarker,并为它提供你想要绑定到字符串的对象,它会给你一个字符串。

答案 2 :(得分:0)

一种选择是使用解析器生成器。

ANTLR是Java的一个这样的工具。如果您是创建语法的新手,您会发现语法IDE ANTLRWorks很有用。

答案 3 :(得分:0)

我猜您正在寻找template engine