从Java8到Java17(六)

278 阅读2分钟

这是我参与11月更文挑战的第12天,活动详情查看:2021最后一次更文挑战

继续向前看,上文总结了Java12的一些更新。从12到16都是一些小修小补,也或者在默默开发着一些内部的优化、憋的大招之类的。半年一个小版本的迭代确实也很难塞进多少新东西,我们也应该转换一下心态,不要总期待每过一个数字版本都有巨量的更新,毕竟时代变了。

今天讲讲后续的一些API和语言特性上的变化。

字符串块

这个更新还是挺有用的,之前在Java中写一些字符串还是挺难受的,各种各样的转义符看的眼花缭乱,现在在这个字符串块内随便写,json、html和SQL等等看起来也很清晰很多。

//SQL
String query = """
    SELECT "EMP_ID", "LAST_NAME"
    FROM "EMPLOYEE_TB";
"""

//HTML

String html = """
              <html>
                  <body>
                      <p>Hello, world</p>
                  </body>
              </html>
              """;

分别用三个单引号开始和结束即可。人们对一门编程语言的好恶都是由这一系列细节组成的,大面上的性能有时候真差不多。

instanceof增加模式匹配

在过去很长一段时间,用instanceof时就会明显增加一行代码的长度,因为类型判断完之后还要做一下转换才能用。一个直觉的逻辑是我既然判断完了,为什么不能直接用?

if (obj instanceof String) {
    String s = (String) obj;   
    ...
}

obj已经是String了,还要转换,这个操作就很反人类。所以现在如果判断成立,就会自动转换,(String)不用再写了,又是一个可以俘获人心的小功能。不过需要注意2个问题:

  1. 需要确定的类型判断才能使用
  2. 作用域的范围需要注意

第一种可以通过这个例子说明,并不是一个明确的类型判断:

//correct
if (obj instanceof String s && s.length() > 5) {
    flag = s.contains("jdk");
}

//error
if (obj instanceof String s || s.length() > 5) {    
    ...
}

作用域的问题可以看下面的例子:

class Example2 {
    Point p;

    void test2(Object o) {
        if (o instanceof Point p) {
            // p 是当前用于匹配的临时对象
            ...
        } else {
            // p 是属性中的p
            ...
        }
    }
    //以上if和else中o并不是同一个对象
}