Javascript (去)引用Java Nashorn中的方法变量
以代码为例: 示例1Javascript (去)引用Java Nashorn中的方法变量,javascript,java-8,nashorn,Javascript,Java 8,Nashorn,以代码为例: 示例1 var Executors = java.util.concurrent.Executors; var executor = Executors.newCachedThreadPool(); var fork = function (callable) { // Clarify Runnable versus Callable overloaded methods executor['submit(java.util.concurrent.Callable)
var Executors = java.util.concurrent.Executors;
var executor = Executors.newCachedThreadPool();
var fork = function (callable) {
// Clarify Runnable versus Callable overloaded methods
executor['submit(java.util.concurrent.Callable)'](callable);
};
fork(function(){ ... }); //ok
这很有效
但这不起作用:
示例2
var Executors = java.util.concurrent.Executors;
var executor = Executors.newCachedThreadPool();
var fork = executor['submit(java.util.concurrent.Callable)'];
fork(function(){ ... }); //fails, NullPointerException
我假设,这是因为fork
这里不是一个JS函数实例,它实际上是jdk.internal.dynalink.beans.SimpleDynamicMethod
我尝试使用fork.apply(executor,function(){…})
但是SimpleDynamicMethod自然没有apply
实际上,为什么示例2不起作用,而示例1起作用
这仅仅是纳肖恩的一种特权吗?有没有比示例1更好的方法来定义fork()函数
更新
在例2中
打印(叉子类型)代码>报告功能
print(fork)
报告[jdk.internal.dynalink.beans.SimpleDynamicMethod Future java.util.concurrent.AbstractExecutorService.submit(Callable)]
例外情况是(第13行读取fork(function(){
)
线程“main”java.lang.NullPointerException中的异常
在jdk.nashorn.internal.scripts.Script$^eval.\ul5(:13)
位于jdk.nashorn.internal.scripts.Script$^eval\.runScript(:5)
位于jdk.nashorn.internal.runtime.ScriptFunctionData.invoke(ScriptFunctionData.java:527)
Alex
在示例1中,var fork
是一个返回数组executor
的函数。在示例2中,var fork
是一个数组。这就是为什么不能使用()
和apply
fork[0](function(){…})
是否适合您
谢谢问题是您在调用中缺少了接收者“执行者”。通常,“获取”Java函数只适用于静态Java函数。例如:
jjs> var abs = java.lang.Math.abs;
jjs> abs(-10);
10
在您的示例中,我们可以将fork绑定到executor并使其等效为静态。此支持当前不存在。如果从类中“获取”,我们可能会支持将receiver添加为第一个参数。将为将来的版本提交增强请求。不幸的是,当前无法使用
绑定
、应用
、和调用
的POJO方法。我想将其添加为未来的增强功能。在上述示例中,您目前能做的最好的功能是:
executor['submit(Callable)'](function() { ... })
请注意,在一般情况下,对属性的索引访问(使用[]
运算符)的效率低于属性名称访问(使用
运算符),Nashorn使用字符串文字识别索引访问,并将其与属性名访问一样有效,因此您不会在这里遇到减速,只会受到一点视觉干扰。在上述情况下,它实际上会直接链接到执行器的虚拟方法
说到视觉干扰,您不必完全限定
java.util.concurrent.Callable
。当参数类型的非限定名称足以消除重载歧义时(通常情况下),您可以使用非限定名称,而不管它在哪个包中(也适用于您自己的类).这有帮助吗?谢谢你的链接,把它附加到这个问题上很好。实际上,我最初使用它作为我的代码的蓝图,只是想为服务器端库制作一个漂亮的JS模块包装ThreadExecutor代码。我可以像例1那样使用代码,我只是觉得额外的闭包是不必要的,也不需要取消理解背后的“魔力”。如果我将调用替换为fork[0](function(){…})
它抛出javax.script.ScriptException:TypeError:[jdk.internal.dynalink.beans.SimpleDynamicMethod Future java.util.concurrent.AbstractExecutorService.submit(Callable)]没有这样的函数“0”在jdk.nashorn.api.scripting.NashornScriptEngine.throwAsScriptException(NashornScriptEngine.java:563)的第16行中,现在一切都清楚了。我的想法已经接近尾声,但无法理解细节。要调用动态方法,需要对象的实例,除非上下文中有它(如示例1所示,它是闭合的一部分),Nashorn无法知道从何处调用它。我相信,通过添加您所描述的绑定函数的功能,将使JavaScript编码更容易。我相信会对其含义进行审查,到目前为止,我非常喜欢互操作性有多周到。感谢您的回答!Attila,您知道JD是否仍然如此K 8u102不能对Java类中的方法调用apply()
或call()
?有解决方法吗?
executor['submit(Callable)'](function() { ... })