JDK14新特性详解

https://zh.wikipedia.org/wiki/Java%E7%89%88%E6%9C%AC%E6%AD%B7%E5%8F%B2

简介

本次的Jdk14版本将带来16个增强方案
在这里插入图片描述
除此之外,Jdk14版本修复了共1986项问题,其中大部分由Oracle工作人员完成

在这里插入图片描述

增强

  1. JEP 305 - Pattern Matching for instanceof (Preview)
  2. JEP 343 - Packaging Tool (Incubator)
  3. JEP 345 - NUMA-Aware Memory Allocation for G1
  4. JEP 349 - JFR Event Streaming
  5. JEP 352 - Non-Volatile Mapped Byte Buffers
  6. JEP 358 - Helpful NullPointerExceptions:
  7. JEP 359 - Records (Preview)
  8. JEP 361 - Switch Expressions
  9. JEP 362 - Deprecate the Solaris and SPARC Ports
  10. JEP 363 - Remove the Concurrent Mark Sweep (CMS) Garbage Collector
  11. JEP 364 - ZGC on macOS
  12. JEP 365 - ZGC on Windows
  13. JEP 366 - Deprecate the ParallelScavenge + SerialOld GC Combination
  14. JEP 367 - Remove the Pack200 Tools and API
  15. JEP 368 - Text Blocks (Second Preview)
  16. JEP 370 - Foreign-Memory Access API (Incubator)

环境

食用

JEP 305:instanceof的模式匹配:通过消除对通用样板代码的需求,提高了开发人员的生产率,并允许使用更简洁的类型安全的代码
在Jdk之前的版本中,使用instanceof模式匹配的时候需要手动进行强制转换成需要的类型。在该版本中可以直接在后面跟上变量名,接下来不用强转就能直接使用该变量

Object obj = "hello 14";
// Jdk之前版本
if (obj instanceof String) {
    String str = (String) obj;
    System.out.println("str length:" + str.length());
} else {
    System.out.println("obj not string.");
}

// Jdk14版本
if (obj instanceof String str) {
    System.out.println("str length:" + str.length());
} else {
    System.out.println("obj not string.");
}

JEP 343:打包工具:此孵化器工具为开发人员提供了一种打包Java应用程序的方式,以便以平台特定的格式进行分发
这些格式包括Windows上的msi和exe,MacOS上的pkg和dmg,以及Linux上的deb和rpm

JEP 345:G1的NUMA-Aware内存分配:此功能提高了非均匀内存访问(NUMA)系统上G1垃圾收集器的整体性能
NUMA技术:https://www.ibm.com/developerworks/cn/linux/l-numa/index.html

JEP 349:JFR事件流:此功能公开了JDK Flight Recorder(JFR)数据以进行连续监视,这将简化各种工具和应用程序对JFR数据的访问
HotSpot VM使用JFR发出500多个数据点,除了解析日志文件外,大多数其他方法无法使用。如果要使用数据,用户必须开始记录,停止记录,将内容转储到磁盘,然后解析记录文件。这对于应用程序概要分析非常有效,其中通常一次记录至少一分钟的数据,但不适用于监视目的。而在新特性中可以公开JFR发出的数据,用于持续监控

JEP 352:非易失性映射字节缓冲区:使用非易失性存储器时,此功能为JDK添加了文件映射模式
对FileChannel API进行了扩展,允许创建MappedByteBuffer实例。非易失性内存能够持久化数据,因此可以利用该特性来改进性能

JEP 358:实用的NullPointerExceptions:通过精确描述哪个变量为null以及其他有用信息,提高了 NullPointerExceptions的可用性。这将提高开发人员的生产率,并提高许多开发和调试工具的质量
目前该特性需要使用-XX:+ShowCodeDetailsInExceptionMessages参数开启

String str = null;
System.out.println(str.length());

/**
 * Jdk之前版本异常输出:
 * Exception in thread "main" java.lang.NullPointerException
 * 	at DemoNull.main(DemoNull.java:9)
 */

/**
 * Jdk14版本异常输出:
 * Exception in thread "main" java.lang.NullPointerException: Cannot invoke "String.length()" because "str" is null
 * 	at DemoNull.main(DemoNull.java:9)
 */

JEP 359:Records:此预览功能提供了一种紧凑的语法,用于声明保存浅层不变数据的类。从表面上看,此功能大大减少了此类中的样板代码,但最终目的是更好地允许将数据建模为数据
在之前的Jdk版本中,如果我们要申明一个final实体类,需要手动写构造器、getter、equals、hashCode、toString等方法。而现在,只需要使用record关键字,一行代码即可搞定,申明之后将自动获得一个构造器、getter、equals、hashCode、toString方法。在record申明的类中也可以定义其他构造器、方法、静态方法和静态属性。record申明的类不能再用abstract修饰。record申明的类不能继承其他的类。

/**
 * @author liujiazhong
 */
public final class Order {

    private final Long orderId;
    private final String orderCode;

    public Order(Long orderId, String orderCode) {
        this.orderId = orderId;
        this.orderCode = orderCode;
    }

    public Long getOrderId() {
        return orderId;
    }

    public String getOrderCode() {
        return orderCode;
    }

    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (!(o instanceof Order)) return false;
        Order order = (Order) o;
        return Objects.equals(getOrderId(), order.getOrderId()) &&
                Objects.equals(getOrderCode(), order.getOrderCode());
    }

    @Override
    public int hashCode() {
        return Objects.hash(getOrderId(), getOrderCode());
    }

    @Override
    public String toString() {
        return "Order{" +
                "orderId=" + orderId +
                ", orderCode='" + orderCode + '\'' +
                '}';
    }
}

/**
 * @author liujiazhong
 */
public record RecordOrder(Long orderId, String orderCode) {
}

// 测试
Order order1 = new Order(1001L, "TEST1001");
RecordOrder order2 = new RecordOrder(1002L, "TEST1002");
System.out.println(order1);
System.out.println(order2);
System.out.println(order1.getOrderCode());
System.out.println(order2.orderCode());

// 结果
Order{orderId=1001, orderCode='TEST1001'}
RecordOrder[orderId=1002, orderCode=TEST1002]
TEST1001
TEST1002

// 可以定义其他信息
public record RecordOrder(Long orderId, String orderCode) {

    public static final String TYPE = "online";

    public RecordOrder() {
        this(1003L, "TEST1003");
    }

    public static void printType() {
        System.out.println(TYPE);
    }

    public void printOrderCode() {
        System.out.println(orderCode);
    }

}

JEP 361:Switch表达式:它允许将switch用作语句或表达式,简化了日常的编码,这是JDK 12和JDK 13中的预览功能

String str = "A";
// Jdk之前的版本
switch (str) {
    case "A":
        System.out.println("A");break;
    case "B":
        System.out.println("B");break;
    default:
        System.out.println("default");
}

// Jdk12之后
switch (str) {
    case "A", "C" -> System.out.println("A || C");
    case "B" -> System.out.println("B");
    default -> System.out.println("default");
}

// yield用于返回值
int score = switch (str) {
    case "A" -> 90;
    case "B" -> 80;
    default -> {
        System.out.println("default");
        yield 70;
    }
};
System.out.println(score);

JEP 362:弃用Solaris和SPARC端口:在将来的发行版中将其删除
放弃对这些端口的支持将使OpenJDK社区中的贡献者能够加速新功能的开发,这些新功能将推动平台向前发展

JEP 363:删除并发标记扫描(CMS)垃圾回收器
CMS垃圾收集器在两年前已过时,并且自JDK 6起已成为CMS的后继产品的G1已成为默认GC,并且已经在许多情况下大规模使用。我们还看到引入了两个新的收集器,ZGC(Jdk11)和Shenandoah(Open Jdk12),同时对G1进行了许多改进 。CMS存在几个弊端,比如会产生内存碎片,并发清理后导致用户线程可用的空间不足,因为是并发清理,所以对CPU资源非常敏感,而且无法处理浮动垃圾
详细信息:https://openjdk.java.net/jeps/363

/**
 * 在Jdk14中通过-XX:+UseConcMarkSweepGC选项尝试使用CMS的话会得到下面的警告信息
 * Java HotSpot(TM) 64-Bit Server VM warning: Ignoring option UseConcMarkSweepGC; support was removed in 14.0
 */
List<String> list = new ArrayList<>();
while (true) {
    list.add("a");
}

JEP 364,JEP 365:ZGC on macOS and Windows:尽管大多数需要ZGC的用户也需要基于Linux的环境的可伸缩性,但是在Windows和macOS中也经常需要部署和测试它。还有某些桌面应用程序将从ZGC功能中受益。因此,ZGC功能已移植到Windows和macOS
ZGC与Shenandoah目标非常相似,在尽可能对吞吐量影响不大的前提下,实现在任意堆内存大小下都可以把停顿时间限制在10毫秒以内。ZGC收集器是一款基于Region内存布局的,(暂时)不设分代,使用了读屏障、染色指针和内存多重映射等技术来实现可并发标记-压缩算法,首要目标是低延迟
详细信息:https://openjdk.java.net/jeps/364
在这里插入图片描述
在这里插入图片描述
上图引用自:The Z Garbage Collector - An Introduction

/**
 * -XX:+UnlockExperimentalVMOptions -XX:+UseZGC
 */
List<String> list = new ArrayList<>();
while (true) {
    list.add("a");
}

JEP 366:弃用ParallelScavenge + SerialOld GC组合,该组合很少使用,但需要大量维护工作
详细信息:https://openjdk.java.net/jeps/366

/**
 * 使用-XX:+UseParallelGC -XX:-UseParallelOldGC或者-XX:-UseParallelOldGC参数启用组合后提示以下信息
 * Java HotSpot(TM) 64-Bit Server VM warning: Option UseParallelOldGC was deprecated in version 14.0 and will likely be removed in a future release.
 */
public static void main(String[] args) {
    List<String> list = new ArrayList<>();
    while (true) {
        list.add("a");
    }
}

JEP 367:删除Pack200工具和API:将删除java.util.jar软件包中的pack200和unpack200工具以及Pack200 API。这些工具和API 已在Java SE 11中弃用
删除原因:https://openjdk.java.net/jeps/367

JEP 368:文本块:在Java 首次将文本块作为预览功能(JEP 355)引入时,收到反馈后,添加了两个新的转义序列。该功能增强了Java程序中用非Java语言编写代码的字符串的可读性

// Jdk之前的版本
String sql1 = "select\n" +
        "\t*\n" +
        "from\n" +
        "\tord_order_item ooi\n" +
        "left join ord_order oo on\n" +
        "\tooi.order_id = oo.id\n" +
        "where\n" +
        "\too.order_code = 'TEST1001'\n" +
        "order by\n" +
        "\too.id desc";

// 三引号表示文本块
String sql2 = """
        select
        	*
        from
        	ord_order_item ooi
        left join ord_order oo on
        	ooi.order_id = oo.id
        where
        	oo.order_code = 'TEST1001'
        order by
        	oo.id desc
        """;

// 新增“\s”表示空格,“\”表示去除换行
String sql3 = """
        select
        	*
        from
        	ord_order_item ooi
        left join ord_order oo on
        	ooi.order_id = oo.id
        where
        	oo.order_code = 'TEST1001'
        order by\s\
        oo.id desc
        """;
System.out.println(sql1);
System.out.println(sql2);
System.out.println(sql3);

JEP 370:外部存储器访问API:此孵化器模块引入了一个API,以允许Java程序安全有效地访问Java堆之外的外部存储器
详细信息:https://openjdk.java.net/jeps/370

补充

在这里插入图片描述

链接

Java:https://www.oracle.com/java/
Jdk14:https://www.oracle.com/java/technologies/javase-jdk14-downloads.html
The Arrival of Java 14:https://blogs.oracle.com/java-platform-group/the-arrival-of-java-14

发布了36 篇原创文章 · 获赞 19 · 访问量 2417

猜你喜欢

转载自blog.csdn.net/momo57l/article/details/105543683