Skip to main content

Java 9 新特性 (EOL)

warning

生命周期结束时间(EOL): 2018/03/31

官方发布介绍页面:https://openjdk.org/projects/jdk9/

1. 模块系统 (Project Jigsaw)​

模块系统允许将代码组织成模块。

module com.example.myapp {
requires java.base;
exports com.example.myapp;
}

2. JShell (交互式编程工具)​

什么是交互式编程环境?重点词交互,在这样的编程环境中,你每输入一行代码,环境都会给你一个反馈,这就是交互式的编程环境。这种编程环境并不太适合工程化的复杂性需求,但在一些快速验证、简单计算之类的场景下还是非常好用的。其实交互式编程环境在其他高级语言中很早就有了,而Java直到Java 9才正式推出了这样的工具。

下面就来一起学习下,这个Java中的交互式编程环境JShell。

JShell 是一个交互式的 REPL 工具。REPL 是 Read-Eval-Print Loop 的缩写,表示读取-求值-输出循环。JShell 允许你在命令行中输入 Java 代码,并立即查看结果。

  1. 启动JShell

    打开终端,然后执行命令:jshell,执行效果如下:

    jdk-9-1.png

  2. 定义变量和执行计算

    在jshell中可以快速的执行计算操作并获得结果,比如这样:

    jdk-9-2.png

  3. 定义函数

    在jshell中也可以函数来封装操作,比如下面就是一个定义求和函数并调用它的例子:

    jdk-9-3.png

  4. 定义类

    在jshell中,定义一些简单的类,也是可以实现的,比如:

    jdk-9-4.png

  5. 查看帮助命令

    关于jshell常用命令,我们可以通过/help来查看

jdk-9-5.png

其它命令请自行查看。

3. 集合工厂方法​

集合工厂方法用于创建不可变集合。

List<String> list = List.of("a", "b", "c");
Set<String> set = Set.of("a", "b", "c");
Map<String, String> map = Map.of("key1", "value1", "key2", "value2");

以往我们创建一些不可变集合的时候,通常是这样写的:

// 不可变的Set
Set<String> set = new HashSet<>();
set.add("a");
set.add("b");
set.add("c");
set = Collections.unmodifiableSet(set);

// 不可变的List
List<Integer> list = new ArrayList<>();
list.add(1);
list.add(2);
list.add(3);
list = Collections.unmodifiableList(list);

Java 8 的写法

Set<String> set = Collections.unmodifiableSet(Stream.of("a", "b", "c").collect(toSet()));
List<Integer> list = Collections.unmodifiableList(Stream.of(1, 2, 3).collect(toList()));

Java 9 的写法

Set<String> set = Set.of("a", "b", "c");
List<Integer> list = List.of(1, 2, 3);
Map<String, String> map = Map.of("a", "1", "b", "2", "c", "3");
Map.of()
Map.of(k1, v1)
Map.of(k1, v1, k2, v2)
Map.of(k1, v1, k2, v2, k3, v3)
...

与asList的区别

看到这里,可能有的人会问了,之前不是对于集合有asXxx这样的方便方法了么?他们有啥区别吗?

这里就以List.of和Arrays.asList为例,给大家列一下它们的异同:

Java 9中推出List.of创建的是不可变集合,而Arrays.asList是可变集合

List.of和Arrays.asList都不允许add和remove元素,但Arrays.asList可以调用set更改值,而List.of不可以,会报java.lang.UnsupportedOperationException异常

List.of中不允许有null值,Arrays.asList中可以有null值

4. 私有接口方法​

接口可以包含私有方法。

interface MyInterface {
private void privateMethod() {
System.out.println("Private Method");
}

default void defaultMethod() {
privateMethod();
}
}

class MyClass implements MyInterface {}

MyClass obj = new MyClass();
obj.defaultMethod();

5. 钻石操作符与匿名类​

钻石操作符可以用于匿名类。

AbstractList<String> list = new AbstractList<>() {
@Override
public String get(int index) {
return null;
}

@Override
public int size() {
return 0;
}
};

6. Stream API 改进​

Stream API 增加了更多的方法。

List<Integer> list = List.of(1, 2, 3, 4, 5);
List<Integer> takeWhileList = list.stream().takeWhile(i -> i < 4).collect(Collectors.toList());
List<Integer> dropWhileList = list.stream().dropWhile(i -> i < 4).collect(Collectors.toList());

7. Optional 类改进​

Optional 类增加了更多的方法。

Optional<String> optional = Optional.of("Hello");
optional.ifPresentOrElse(System.out::println, () -> System.out.println("Value is absent"));

8. CompletableFuture 改进​

CompletableFuture 增加了更多的方法。

CompletableFuture.supplyAsync(() -> "Hello")
.thenApply(String::toUpperCase)
.thenAccept(System.out::println);

9. Process API 改进​

Process API 增加了更多的方法。

ProcessHandle currentProcess = ProcessHandle.current();
System.out.println("PID: " + currentProcess.pid());

10. HTTP/2 客户端​

新的 HTTP/2 客户端 API。

HttpClient client = HttpClient.newHttpClient();
HttpRequest request = HttpRequest.newBuilder()
.uri(URI.create("https://example.com"))
.build();
HttpResponse<String> response = client.send(request, HttpResponse.BodyHandlers.ofString());
System.out.println(response.body());

11. 多版本兼容 JAR​

支持多版本兼容的 JAR 文件。

// 在 JAR 文件中包含不同版本的类文件
META-INF/versions/9/com/example/MyClass.class

12. Stack-Walking API​

新的 Stack-Walking API。

StackWalker walker = StackWalker.getInstance();
walker.forEach(frame -> System.out.println(frame.getClassName()));

13. 增强的 @Deprecated 注解​

@Deprecated 注解增加了更多的属性。

@Deprecated(since = "9", forRemoval = true)
public void deprecatedMethod() {
// 示例代码
}

14. Try-With-Resources 改进​

Try-With-Resources 语句的改进。

BufferedReader reader = new BufferedReader(new FileReader("test.txt"));
try (reader) {
System.out.println(reader.readLine());
}

15. 进程 API 改进​

进程 API 增加了更多的方法。

ProcessHandle currentProcess = ProcessHandle.current();
System.out.println("PID: " + currentProcess.pid());