耳朵里面痒是什么原因| 肝病去医院挂什么科| 什么尾花| 妈妈的外婆叫什么| 补肾壮阳吃什么好| pda是什么意思| 非营利性医院是什么意思| hicon是什么牌子| vintage什么意思| 许三多最后是什么军衔| zs是什么意思| 癫痫不能吃什么| 孕期便秘吃什么通便快| 老年人脚肿什么原因| 惜字如金是什么意思| 血管瘤是什么样子的图| 什么样才是包皮| 心肾不交是什么意思| 男孩小名叫什么好听| 口腔溃疡吃什么中成药| 花椒和麻椒有什么区别| 严重失眠吃什么药管用| 腿上的肉疼是什么原因| 自汗是什么意思| 晒伤用什么药膏| 无限未来为什么不写了| 偏光镜片是什么意思| 党工委书记是什么级别| 头好出汗是什么原因| 抛光是什么意思| 侧颜杀是什么意思| 大修基金什么时候缴纳| 缺铁性贫血吃什么食物| 飞机票号是什么意思| 十二指肠溃疡是什么症状| 看灰指甲去医院挂什么科| 闭口粉刺是什么原因引起的| 什么是白细胞| 电母是什么意思| 月经期间喝酒有什么危害| 柠檬有什么作用| 沉默不是代表我的错是什么歌| 肠胀气是什么原因引起的| 泡泡像什么| 左肺上叶钙化灶什么意思| 什么水果吃了对皮肤好| 燕麦片热量高为什么还能减肥| 单脐动脉是什么意思| 壶嘴为什么不能对着人| 幼犬吃什么| 儿童肠炎吃什么药| 1月19号什么星座| 做流产手术需要准备什么东西| 吃什么能排结石| 饧是什么意思| 什么人靠别人的脑袋生活| 脾虚是什么原因导致的| 执子之手什么意思| aosc医学是什么意思| 93岁属什么生肖| 鹅拉绿色粪便是什么病| shiraz是什么名字红酒| 君子兰叶子发黄是什么原因| rh血型阴性是什么意思| 气不够用是什么原因| 液基薄层细胞学检查是什么| 早搏什么意思| 睡醒咳嗽是什么原因| 18k黄金是什么意思| 什么是黄疸| 为什么长痱子| 硬膜囊受压是什么意思| 汇字五行属什么| 做照影是检查什么| 贬义词是什么意思| 瓒字取名有什么寓意| 尿酸高是什么| 衣服36码相当于什么码| 清洁度iv是什么意思| 小辣椒是什么意思| 后厨打荷是干什么的| 幡然醒悟是什么意思| 菊花有什么颜色| 五步蛇长什么样| 载脂蛋白b偏高是什么意思| 乙状结肠是什么意思| 眼压高吃什么药| 男性睾丸疼痛什么原因| 水瓜壳煲水有什么功效| 恒顺众生是什么意思| cc是什么意思| 11.2是什么星座| 左室舒张功能减低是什么意思| 为什么喜欢| 什么水果最老实| 尿常规白细胞偏高是什么原因| 50肩是什么意思| 日抛什么意思| 殉葬是什么意思| 打粉是什么意思| 脂肪瘤是什么原因引起的| 心电图t波改变什么意思| 减肥期间吃什么水果好| 打飞机是什么意思| 属猪的是什么命| 查心梗应该做什么检查| 解神是什么意思| 肺脓肿是什么病严重吗| nautical什么牌子| 留低是什么意思| 梦到男朋友出轨了预示什么意思| 人乳头瘤病毒51型阳性是什么意思| 传媒公司是干什么的| 妹控是什么意思| 接骨木是什么| 倒班什么意思| 化肥对人体有什么危害| 出离心是什么意思| 孕妇建档需要检查什么| 含漱是什么意思| 喜闻乐见什么意思| 篱笆是什么东西| 为什么孩子要跟爸爸姓| 81年属什么生肖| 屈光检查是什么| 甲状腺炎吃什么药好| 皮肤一碰就破是什么病| 乙型肝炎e抗体阳性是什么意思| 胖大海是什么| 叶公好什么| rush是什么意思| 多囊卵巢有什么症状表现| 晚上吃什么水果好| 口腔老是出血是什么原因| 是什么货币符号| 精神什么满| 厦门有什么区| romantic是什么意思| 肾小球肾炎吃什么药| 懒惰是什么意思| 秋葵有什么营养价值| 一个入一个肉念什么| 牛油果有什么功效| 儿茶是什么中药| 清风明月是什么意思| fnc是什么意思| 歇菜是什么意思| 梦见家里水管漏水是什么意思| 1901年属什么生肖| 什么叫肠化生| 琏是什么意思| 血癌是什么病| 做肠镜有什么危害| 孕妇刚生完孩子吃什么好| 犯罪心理学属于什么专业| 三氯蔗糖是什么东西| 4个火读什么| 男性生殖痒是什么原因| 九五至尊是什么生肖| 水瓶座是什么象星座| 盆腔积液有什么症状| 白带有点黄是什么原因| 英语四级是什么水平| 杀鸡吓什么| 什么是超七水晶| 不喜欢是什么意思| 项羽是什么生肖| 什么食物含钾最高| 什么原因引起荨麻疹| 愧疚是什么意思| 过期牛奶有什么用途| 胎儿左肾盂分离是什么意思| 为什么晚上血压比白天高| 围产期是什么意思| 电解质氯高是什么原因| 小孩小便红色是什么原因| ml 什么意思| 怀孕乳房会有什么变化| 蒙古族不吃什么肉| 半夜惊醒是什么原因| bottle什么意思| 牛加一笔是什么字| 深圳市市长什么级别| 眼睛长黄斑是什么原因| 反酸是什么症状| 什么叫穿刺| 辅助治疗是什么意思| 朝鲜和韩国是什么关系| 阴道炎是什么原因引起的| 叶酸片什么时候吃最好| 真菌阳性是什么意思| 割掉胆对人有什么影响| 执业药师证有什么用| 社畜什么意思| cn是什么意思二次元| 凝血常规是查什么的| 六味地黄丸有什么副作用| 蓝蓝的天上白云飘是什么歌| 苯佐卡因是什么药| 心不在焉什么意思| 产后大出血一般发生在什么时候| 下午4点多是什么时辰| 梦见栽树是什么意思| 解脲支原体阳性吃什么药最好| bj是什么意思| 尕尕是什么意思| 法身是什么意思| 司是什么级别| 黄体期是什么意思| 群青色是什么颜色| 白血球高是什么原因| 甘油三脂是什么| 鱼肝油什么时候吃最好| 胆囊炎挂什么科| 胃出血大便是什么颜色| 先期是什么意思| 魁拔4什么时候上映| 这次是我真的决定离开是什么歌| 什么是走读生| 冰箱eco是什么意思| 结肠炎吃什么食物好| 蚂蚁为什么要搬家| 答谢宴是什么意思| 石青色是什么颜色| 什么是脱肛| 减肥早上吃什么| 脑梗长期吃什么药好| 山东为什么简称鲁| 唯利是图是什么生肖| pB什么意思| 花甲之年是什么意思| 苹果跟什么榨汁好喝| 橙子皮泡水喝有什么好处| 晚上睡觉咳嗽是什么原因| 阴茎硬不起来吃什么药| 属马的本命佛是什么佛| 区域经理的岗位职责是什么| 低压低是什么原因| theme什么意思| 果蝇是什么| 失眠吃什么药见效快| 吴亦凡为什么退出exo| 冬至穿什么衣服| 屁股上长痘痘是什么原因| 长期贫血会导致什么严重后果| 舌头有点麻是什么病的前兆| 1800年是什么年| 各自安好是什么意思| 美容师都要学什么| 血糖高吃什么肉最好| 为什么乳头内陷| 父亲节出什么生肖| 子宫肌瘤做什么检查能查出来| 喉咙发痒吃什么药| com什么意思| 梦见死蛇是什么预兆| 鸡米头是什么| 糠是什么东西| moss是什么意思| 外交部部长是什么级别| 寿司醋可以用什么代替| 不孕不育挂什么科| 护理学是干什么的| 莲子不能和什么一起吃| 百度

福建公共卫生间隔断 上哪买优质的卫生间隔断

百度 “基层腐败特别是发生在农村地区的腐败,损害了人民群众的根本利益。

by Julien Ponge

Scenarios for using Oracle Nashorn as a command-line tool and as an embedded interpreter in Java applications

Until Java SE 7, JDKs shipped with a JavaScript scripting engine based on Mozilla Rhino. Java SE 8 will instead ship with a new engine called Oracle Nashorn, which is based on JSR 292 and invokedynamic. It provides better compliance with the ECMA normalized JavaScript specification and better runtime performance through invokedynamic-bound call sites.

This article is an introduction to using Oracle Nashorn in several ways. It covers using the standalone engine through the jjs command-line tool as well as using Oracle Nashorn as an embedded scripting engine inside Java applications. It shows the Java-to-JavaScript interoperability and how Java types can be implemented and extended from JavaScript, providing a seamless integration between the two languages.

The examples can be run using a recent JDK 8 early-access release. You can also use a custom build of OpenJDK 8. This is very simple to do thanks to the new OpenJDK build infrastructure (for example, sh configure && make images on a Mac OS X operating system with the XCode command-line tools installed).

[Editor's Note: Java SE 8 is now available from the OTN download page.]

Java Magazine Logo

Originally published in the January/February 2014 issue of Java Magazine.Subscribe today.

It’s Just JavaScript

A simple way to get started with Oracle Nashorn is to run JavaScript programs from the command line. To do so, builds of Oracle’s JDK or OpenJDK include a command-line tool called jjs. It can be found in the bin/ folder of a JDK installation along with the well-known java, javac, or jar tools.

The jjs tool accepts a list of JavaScript source code files as arguments. Consider the following hello.js file:

var hello = function() {

  print("Hello Nashorn!");
};

hello();

Evaluating it is as simple as this:

$ jjs hello.js

Hello Nashorn!
$
var data = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];


var filtered = data.filter(function(i) {
  return i % 2 == 0;
});
print(filtered);

var sumOfFiltered = filtered.reduce(function(acc, next) {
  return acc + next;
}, 0);
print(sumOfFiltered);

Listing 1

Oracle Nashorn is an ECMA-compliant implementation of the language; hence, we can run more-elaborate snippets, such as the one shown in Listing 1, which prints a filtered list in which only the even numbers remain from the original list. It also prints the sum of those even numbers:

2,4,6,8,10

30

While Oracle Nashorn runs ECMA-compliant JavaScript, it is important to note that objects normally accessible in a web browser are not available, for example, console, window, and so on.

Scripting Extensions

If you run jjs -help to get a comprehensive list of the jjs command-line tool commands, you will notice a few interesting features:

  • It can run scripts as JavaFX applications.

  • JavaScript strict mode can be activated.

  • Additional classpath elements can be specified for the Java Virtual Machine (JVM).

  • An intriguing scripting mode can be enabled.

The scripting mode is interesting if you plan to take advantage of jjs to run system scripts written in JavaScript, just as you would do in Python, Ruby, or Bash. The scripting mode mainly consists of two language extensions: heredocs and shell invocations.

Heredocs. Heredocs are simply multiline strings, and they use a syntax that is familiar to Bash, Perl, and Ruby programmers (see Listing 2). Text begins with << followed by a special termination marker, which is EOF in our case. The formatting is left intact until the termination marker. Also, JavaScript expressions can be embedded in ${...} expressions. Running this program yields the output shown in Listing 3.

A simple way to get started with Oracle Nashorn is to run JavaScript programs from the command line.



var data = {
 foo: “bar”,
 time: new Date()
};

print(<So...       foo = ${data.foo} and the current time is       ${data.time} EOF);  

Listing 2

$  jjs -scripting heredocs.js

So...
      foo = bar
and the current time is
      Thu Aug 01 2013 16:21:16 GMT+0200 (CEST)
$

Listing 3

Note that in scripting mode, double-quoted strings can embed expressions that will be evaluated: "Hello ${name}" will evaluate against the value of name, while 'Hello ${name}' will not.

Shell invocations. Shell invocations allow the invocation of external programs in which the command is put between back-tick characters. Consider the following example:

var lines =

'ls -lsa'.split("\n");
for each (var line in lines) {
  print("|> " + line);
}

It runs the ls -lsa command. A shell invocation returns the standard console output as a string, which enables us to split lines and print them prepended with "|> ", as shown in Listing 4. If you need more-elaborate control over invoked processes, you should know that a $EXEC function exists, which provides access to the standard input, output, and error streams.

jjs -scripting dir.js

|> total 72
|>  0 drwxr-xr-x  2 jponge  staff    238 Aug  1 16:12 .
|>  0 drwxr-xr-x  5 jponge  staff    170 Aug  1 12:15 ..
|>  8 -rw-r--r--  1 jponge  staff     90 Jul 31 23:36 dir.js
|>  8 -rw-r--r--  1 jponge  staff    304 Aug  1 15:56 hello.js
|>  8 -rw-r--r--  1 jponge  staff    143 Aug  1 16:12 heredocs.js
|>
$

Listing 4

Other goodies. The scripting mode provides further goodies:

  • The $ENV variable provides the shell environment variables.

  • The $ARG variable is an array of the program command-line arguments.

  • Comments can start with #, which is useful for making scripts executable on UNIX-like systems. exit(code) and quit() functions can terminate the current JVM process.

Consider the following executable.js file:

#!/usr/bin/env jjs -scripting

print(
"Arguments (${$ARG.length})");
for each (arg in $ARG) {
  print("- ${arg}")
}

We can make it executable and invoke it (arguments are passed after --), as shown in Listing 5.

$ chmod +x executable.js

$ ./executable.js
Arguments (0)
$ ./executable.js -- hello world !
Arguments (3)
- hello
- world
- !
$

Listing 5

Embedding Oracle Nashorn

The public API to embed Oracle Nashorn is simply javax.script. When Oracle Nashorn is available, its scripting engine is accessible through the nashorn identifier.

Listing 6 shows how you can access Oracle Nashorn from a Java application to define a sum function, call it, and then display the result.



package sample1;

import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;

public class Hello {

  public static void main(String... args) throws Throwable {
    ScriptEngineManager engineManager = 
new ScriptEngineManager();
    ScriptEngine engine = 
engineManager.getEngineByName("nashorn");
    engine.eval("function sum(a, b) { return a + b; }");
    System.out.println(engine.eval("sum(1, 2);"));
  }
}

Listing 6

The scripting engine object is the sole entry point to the Oracle Nashorn interpreter. It can be cast to the javax.script.Invocable interface, too:

Invocable invocable = (

Invocable) engine;
System.out.println(
invocable.invokeFunction(
"sum", 10, 2));

The Invocable interface also provides a method to convert evaluated code to a reference on a Java interface. Suppose that there exists some interface Adder as follows:

public interface Adder {

  int sum(int a, int b);
}

The evaluated code defines a sum function with two arguments; hence, we can use it as an implementation as follows:

Adder adder =

invocable.getInterface(
  Adder.class);
System.out.println(
  adder.sum(2, 3)); 

This is a convenient way to extend Java types from JavaScript, but fortunately it’s not the only one, as we will see in the next sections.

Not every JavaScript code is to be evaluated from a String: java.io.Reader; instances can be used, too, as shown in Listing 7.



engine.eval(new FileReader("src/sample1/greeter.js"));
System.out.println(invocable.invokeFunction("greet", "Julien"));

Listing 7

You should consult the complete javax.script APIs for more details, including the information about the ability to define scopes and bindings of script engines.

mustache.js

Let’s now call a real-world JavaScript library from a Java application. To do so, let’s use the popular mustache.js template library, which is commonly used to render view fragments in HTML applications. Briefly, given a JSON data object {"name":"Bean"} and a template "Hello {{name}}", Mustache renders "Hello Bean". The template engine can do more than that, though, because it also supports conditions, collection iteration, and more.

Suppose that we downloaded mustache.js. Listings 8a and 8b show our Java integration example.



package sample2;

import javax.script.Invocable;
import javax.script.ScriptEngine;
import javax.script.ScriptEngineManager;
import java.io.FileReader;

public class Mustache {

  public static void main(String... args) throws Throwable {
    ScriptEngineManager engineManager = 
new ScriptEngineManager();
    ScriptEngine engine = 
engineManager.getEngineByName("nashorn");
    engine.eval(new FileReader("src/sample2/mustache.js"));
    Invocable invocable = (Invocable) engine;

    String template = "Email addresses of {{contact.name}}:\n" +
        "{{#contact.emails}}\n" +
        "- {{.}}\n" +
        "{{/contact.emails}}";

    String contactJson = "{" +
        "\"contact\": {" +
        "\"name\": \"Mr A\", \"emails\": [" +
        "\"contact@some.tld\", \"sales@some.tld\"" +
        "]}}";



Listing 8a

Object json = engine.eval("JSON");

    Object data = 
invocable.invokeMethod(json, "parse", contactJson);

    Object mustache = engine.eval("Mustache");
    System.out.println(invocable.invokeMethod(
mustache, "render", template, data));
  }
}

Listing 8b

After getting a scripting engine reference for Oracle Nashorn, we evaluate the mustache.js code. We then define the Mustache template as a String. The data model needs to be a JSON object. In our case, we first have to define it as a String and call JSON.parse to have it as a JSON object. We can then call Mustache.render. Running this program yields the following output, calling mustache.js for template rendering:

$ java sample2.Mustache

Email addresses of Mr A:
- contact@some.tld
- sales@some.tld

$

Java Seen from Oracle Nashorn

In most cases, calling Java APIs from Oracle Nashorn is straightforward, with the resulting code being Java written in JavaScript.

print(java.lang.System.currentTimeMillis());

Java objects can be instantiated using the new operator:
var file = 
new java.io.File("sample.js");
print(file.getAbsolutePath());
print(file.absolutePath);

Listing 9

Basic example. We can call the System.currentTimeMillis() static method, as shown in Listing 9. And Java objects can be instantiated using the new operator:

var file =

new java.io.File("sample.js");
print(file.getAbsolutePath());
print(file.absolutePath);

Note that although java.io.File does not define an absolutePath method or public field, Oracle Nashorn inferred a property for it, so the expression file.absolutePath is equivalent to file.get AbsolutePath(). In fact, Oracle Nashorn treats the getXY() and setXY(value) methods as properties.

Dealing with arrays. The following snippet populates a queue as an instance of java.util.LinkedList:

var stack =

new java.util.LinkedList();
[1, 2, 3, 4].forEach(function(item) {
  stack.push(item);
});

print(stack);
print(stack.getClass());

This produces the following output, confirming that we are directly manipulating Java objects from JavaScript:

[4, 3, 2, 1]

class java.util.LinkedList

We can also take a tour through the new Java 8 stream APIs to sort the collection, although in this case, this is not the most efficient way to do so:

var sorted = stack

  .stream()
  .sorted()
  .toArray();
print(sorted);

This time, it prints something like [Ljava.lang.Object;@473b46c3, which indicates a Java native array. However, a Java array is not a JavaScript array. Internally, Oracle Nashorn provides JavaScript arrays using a custom class that also implements java.util.Map. Conversions can be performed using the to and from methods of the Oracle Nashorn–provided Java object:

var jsArray = Java.from(sorted);

print(jsArray);

var javaArray = 
Java.to(jsArray);
print(javaArray);

which prints:

1,2,3,4

[Ljava.lang.Object;@23a5fd2

Imports. By default, all references to Java types need to be fully qualified (for example, java.lang.String, java.util.LinkedHashSet, and so on). Oracle Nashorn does not import the java package by default, because references to String or Object conflict with the corresponding types in JavaScript. Hence, a Java string is java.lang.String, not String.

Mozilla Rhino was the predecessor of Oracle Nashorn as the JavaScript engine implementation provided with Oracle’s JDK releases. It featured a load(path) function to load a third-party JavaScript file. This is still present in Oracle Nashorn. You can use it to load a special compatibility module that provides importClass to import a class (like an explicit import in Java) and importPackage to import a package (like a wildcard import in Java):

load(

"nashorn:mozilla_compat.js");

importClass(java.util.HashSet);
var set = new HashSet();

importPackage(java.util);
var list = new ArrayList();

It is important to note that these functions import the symbolic references into the global scope of the JavaScript code being interpreted. While they are still supported for compatibility reasons, the use of mozilla_compat.js and importClass is discouraged. Instead, it is recommended that you use another function coming from the Mozilla Rhino heritage—JavaImporter—as shown in Listing 10.



	var CollectionsAndFiles = new JavaImporter(
    java.util,
    java.io,
    java.nio);

with (CollectionsAndFiles) {
  var files = new LinkedHashSet();
  files.add(new File("Plop"));
  files.add(new File("Foo"));
  files.add(new File("w00t.js"));
} 

Listing 10

JavaImporter takes a variable number of arguments as Java packages, and the returned object can be used in a with statement whose scope includes the specified package imports. The global JavaScript scope is not affected, making JavaImporter a much better alternative to importClass and importPackage.

Overloaded methods. Java allows method overloading, that is, the definition within a single class of several methods that have the same names but different signatures. The java.io.PrintStream class is a good example, providing many print and println methods for objects, strings, arrays, and primitive types.

Oracle Nashorn properly selects the most suitable target at runtime on a per-invocation basis. This means that you should never have to worry about overloaded methods when dealing with Java APIs. Still, there is a way to precisely select the required target if you need to. This need mainly occurs with ambiguous parameters when you are passing a function object in which different interface types are permitted by overloaded methods, such as with the submit methods of java.util.concurrent executors.

In the following code, the first call to println will select the println(String) overloaded method. The second call uses a JavaScript object property to access the println(Object) variant. The string to be passed provides a signature that Oracle Nashorn uses at resolution time. Note that as an exception, classes from the java package need not be qualified; hence, we can write println(Object) instead of the valid, but longer, println(java.lang.Object).

var stdout =

java.lang.System.out;
stdout.println("Hello");
stdout["println(Object)"]( 
"Hello");

Type objects. The Java.type function can be used to obtain references to precise Java types. These include not just objects but also primitive types and arrays:

var LinkedList = Java.type(

"java.util.LinkedList");
var primitiveInt = Java.type(
"int");
var arrayOfInts = Java.type(
"int[]");

The returned objects are an Oracle Nashorn–specific representation of mappings to Java types. It is important to note that they differ from instances of java.lang.Class. Type objects are useful as constructors and for instanceof-based comparisons. Let’s look at Listing 11.



	 var list = new LinkedList;
list.add(1);
list.add(2);
print(list);
print(list instanceof LinkedList);

var a = new arrayOfInts(3);
print(a.length);
print(a instanceof arrayOfInts);

Listing 11

It is possible to go back and forth between a type object and a Java class reference. The class property of type objects returns their java.lang.Class counterpart. Similarly, the static property is made available to java.lang.Class instances to get their corresponding type objects.



print(LinkedList.class);
print(list.getClass().static);
print(LinkedList.class === list.getClass());
print(list.getClass().static === LinkedList);

The code in Listing 12 would print the following:

class java.util.LinkedList

[JavaClass java.util.LinkedList]
true
true

Extending Java Types

Oracle Nashorn provides simple mechanisms for extending Java types from JavaScript code. It is important to be able to provide interface implementations and concrete subclasses.

Implementing interfaces. Given a Java interface, a simple way to provide an implementation is to instantiate it, and pass its constructor function a JavaScript object in which the methods to be implemented are given as properties.

Listing 13 provides a concrete implementation of java.util.Iterator, giving implementations of the next and hasNext methods (the remove method is provided by a default method in Java 8). We can run it, and check that it works as expected (see Listing 14).



var iterator = new java.util.Iterator({
  i: 0,
  hasNext: function() {
    return this.i < 10;
  },
  next: function() {
    return this.i++;
  }
});

print(iterator instanceof Java.type("java.util.Iterator"));
while (iterator.hasNext()) {
  print("-> " + iterator.next());
} 


Listing 13

true

-> 0
-> 1
-> 2
-> 3
-> 4
-> 5
-> 6
-> 7
-> 8
-> 9

Listing 14

When interfaces consist of a single method, a function object can be directly given with no need to perform an explicit new operator call. The example in Listing 15 illustrates this on collection streams.



var list = java.util.Arrays.asList(1, 2, 3, 4, 5, 6, 7, 8);
var odd = list.stream().filter(function(i) {
  return i % 2 == 0;
});
odd.forEach(function(i) {
  print(">>> " + i);
});

Listing 15

Running the code in Listing 15 prints the following:

>>> 2

>>> 4
>>> 6
>>> 8

Note that Oracle Nashorn also provides a language extension in the form of Oracle Nashorn functions, which provides an abridged syntax for small lambda functions. This works everywhere a single abstract-method type is expected from Java APIs, too. Therefore, we can rewrite the following code from Listing 15:

var odd = list.stream().filter(

  function(i) {
  return i % 2 == 0;
});

Like this:

var odd = list.stream().filter(

  function(i) i % 2 == 0);

This language extension is useful when dealing with the new Java SE 8 APIs that provide support for lambda expressions, because JavaScript functions can be used wherever a Java lambda is expected. Also, note that this shorter form is to be supported by JavaScript 1.8 engines.

The case of abstract classes is the same as interfaces: you provide a JavaScript object with the required method implementations to its constructor function. Or, directly pass a function when an instance of a single abstract-method class is required.

Using instance-bound implementations. To extend concrete classes, you have to use the Java.extend function. It takes a type object as a first argument to denote the base class to be extended. If the parameter is an interface type, it assumes that the base class is java.lang.Object. Further types can be given as extra parameters to specify a set of implemented interfaces.

Consider the example shown in Listing 16. The Java.extend function returns a type object, also called an extender. It can be invoked to create concrete subclasses; in our case, instance is a subclass of java.lang.Object that implements the two interfaces java.lang .Comparable and java.io.Serializable. Implementations are passed to instances being created through a JavaScript object passed to the constructors.



var ObjectType = Java.type("java.lang.Object");
var Comparable = Java.type("java.lang.Comparable");
var Serializable = Java.type("java.io.Serializable");

var MyExtender = Java.extend(
ObjectType, Comparable, Serializable);
var instance = new MyExtender({
  someInt: 0,
  compareTo: function(other) {
    var value = other["someInt"];
    if (value === undefined) {
      return 1;
    }
    if (this.someInt < value) {
      return -1;
    } else if (this.someInt == value) {
      return 0;
    } else {
      return 1;
    }
  }
});

print(instance instanceof Comparable);
print(instance instanceof Serializable);
print(instance.compareTo({ someInt: 10 }));
print(instance.compareTo({ someInt: 0 }));
print(instance.compareTo({ someInt: -10 })); 

Listing 16

Running the code in Listing 16 yields the following console output:

true

true
-1
0
1

Using class-bound implementations. Instances created from the same extender type share the same class although their implementations differ on a per-instance basis (see Listing 17).



var anotherInstance = new MyExtender({
  compareTo: function(other) {
    return -1;
  }
});

// Prints 'true'!
print(instance.getClass() === anotherInstance.getClass()); 

Listing 17

While this is fine in many cases, passing the implementation to each instance might not always be convenient. Indeed, there are cases where objects must be instantiated through some form of inversion-of-control mechanism, such as those found in dependency injection APIs. In such cases, the third-party APIs typically require a reference to the implementation class, which makes the previous extender mechanism unsuitable.

Fortunately, Java.extend allows implementations to be bound to a class definition rather than being specified for each instance. To do so, you simply need to pass an implementation JavaScript object as the last parameter.

Consider Listing 18, which defines two extender types: FooCallable and BarCallable. When creating instances foo and bar, there is no need to pass implementations. We can also check that instances do not have the same class definition. In fact, FooCallable.class or BarCallable.class can be passed to third-party Java APIs that need instances of java.lang.Class definitions.



 var Callable = Java.type("java.util.concurrent.Callable");

var FooCallable = Java.extend(Callable, {
  call: function() {
    return "Foo";
  }
});

var BarCallable = Java.extend(Callable, {
  call: function() {
    return "Bar";
  }
});

var foo = new FooCallable();
var bar = new BarCallable();

// 'false'
print(foo.getClass() === bar.getClass());

print(foo.call());
print(bar.call());

Listing 18

Although not illustrated by this example, classes defined with class-bound implementations provide constructors inherited from their superclass. In this example, our objects implicitly extend java.lang.Object and implement java.util.concurrent.Callable; hence, the corresponding class definition simply has a public no-arguments constructor.

Using instance-bound and class-bound implementations. Last but not least, it is possible to combine both instance-bound and class-bound implementations. You can refine the class-bound implementation of all or some of the methods by passing an implementation object to its constructor, as shown in Listing 19.



var foobar = new FooCallable({
  call: function() {
    return “FooBar”;
  }
});

// ‘FooBar’
print(foobar.call());

// ‘true’
print(foo.getClass() === foobar.getClass());  

Listing 19

Conclusion

This article covered various scenarios for using Oracle Nashorn as a command-line tool and as an embedded interpreter in Java applications. It also covered the interoperability between Java and JavaScript, including the ability to implement and extend Java types from JavaScript.

Oracle Nashorn is an excellent way to take advantage of a scripting language for polyglot applications on the JVM. JavaScript is a popular language, and the interaction between Java and JavaScript is both seamless and straightforward for a wide range of use cases.

JulienPonge-headshot

Julien Ponge (@jponge) is a longtime open source craftsman who is currently an associate professor in computer science and engineering at INSA de Lyon. He focuses his research on programming languages, virtual machines, and middleware as part of the CITI Laboratory activities.

绍兴本地人喝什么黄酒 什么人不能吃海带 全身发黄是什么原因 霉菌阴性是什么意思 葡萄球菌用什么抗生素
夏天适合种什么蔬菜 盘古是一个什么样的人 右小指麻木是什么征兆 月经期间吃什么好 吃茄子有什么好处
生化八项是检查什么 阴道吹气是什么原因 无利不起早是什么意思 狗狗发抖是什么原因 儿童中耳炎用什么药最好
有什么好的赚钱方法 胎膜早破是什么原因引起的 o型b型生的孩子是什么血型 心脏属于什么组织 紫外线过敏用什么药膏
业障什么意思hcv7jop9ns7r.cn 秽是什么意思hcv9jop5ns8r.cn 丰富是什么意思hcv9jop3ns2r.cn 什么的马hcv8jop6ns8r.cn 吃什么能流产hcv8jop5ns5r.cn
长期吃阿司匹林有什么副作用hcv8jop5ns9r.cn 什么样的人长寿hcv8jop0ns8r.cn 调养是什么意思hcv7jop6ns9r.cn 438是什么意思0297y7.com 什么牌子的冰箱最好jinxinzhichuang.com
土豆和什么不能一起吃hcv9jop6ns1r.cn 舌头尖发麻是什么原因hcv7jop6ns4r.cn 高血糖能吃什么水果hcv9jop5ns9r.cn 吃什么可以回奶hanqikai.com 人头什么动hcv9jop6ns4r.cn
三观不正是什么意思hcv9jop5ns9r.cn 绿茶女是什么意思hcv8jop0ns3r.cn 妈妈的表妹叫什么hcv8jop5ns0r.cn 肺气囊是什么病hcv8jop7ns9r.cn 落子无悔是什么意思hcv7jop6ns8r.cn
百度