进行以下测试:
public static class Scripted { public void setThing(List<?> list) { System.out.println("Set via list"); } public void setThing(Object[] array) { System.out.println("Set array"); } } @Test public void testScripting() throws Exception { ScriptEngine engine = new ScriptEngineManager().getEngineByExtension("js"); engine.getContext().setAttribute("s",new Scripted(),ScriptContext.ENGINE_SCOPE); engine.eval("s.thing = Array(1,2,3);"); }
随着Rhino发行的Java 7版本,如果你运行这个,你会得到一个这样的异常:
javax.script.ScriptException: sun.org.mozilla.javascript.internal.EvaluatorException: The choice of Java constructor setThing matching JavaScript argument types (object) is ambiguous; candidate constructors are: void setThing(java.util.List) void setThing(java.lang.Object[]) (<Unknown source>#1) in <Unknown source> at line number 1
首先的Object []重载存在是因为以前版本的Rhino不会自动将数组转换为List,而是将它们转换为Object [].
如果这是一个个人项目,那么我将删除Object []重载.问题是这是一个公共API,现在可能有人打电话给这个方法.我仍然希望升级到Java 7,但是我想避免让JavaScript用户或使用阵列版本的方法的人感到烦恼.
有没有办法隐藏来自Rhino的Object []重载方法,而其他方法仍然可以调用它们?
解决方法
虽然它不是很优雅,但是有一种专门调用一个重载Java方法的方法.它在
Java Method Overloading and LiveConnect 3规范的最后一节中定义.基本上,您使用方括号的整个签名,使用方括号符号显示在错误消息中.在您的情况下,以下应该工作:
s["setThing(java.util.List)"](Array(1,3));
不幸的是,我们使用实现java.util.List的JavaScript数组进行的更改会破坏现有的代码.也许最好选择一个,以防万一有多种匹配的方法.
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。