Java 23:新功能正式公布

最新版本的 Java 开发工具包 23 (JDK) 在最新版本中具有四个新功能。到目前为止值得注意的两个主要功能是 Vector API、Stream Gatherers 的第二个预览以及模式中原始类型的预览 - 例如instanceof和switch。

友情提醒,最新版本将于 9 月 19 日发布。

Vector API
自Java Development Kit 16发布以来, Vector API一直在Java的早期版本中孵化,一直到最新版本22。
这个新版本将引入一个API来帮助表达在运行时编译的向量计算。

  • 是为了在不同支持的 CPU 架构上拥有最佳的向量指令。
  • 该提案的一些目标包括提供标准化 API、运行时编译、在x64和AArch64CPU 架构上提供更好的性能、优雅降级、与平台无关以及与 Valhalla 项目保持更多一致
  • 该项目旨在增强 Java 对象模型的值对象而是对象。

矢量 API 代码示例

static final VectorSpecies<Float> SPECIES = FloatVector.SPECIES_PREFERRED;

void vectorComputation(float[] a, float[] b, float[] c) {
    int i = 0;
    int upperBound = SPECIES.loopBound(a.length);
    for (; i < upperBound; i += SPECIES.length()) {
        // FloatVector va, vb, vc;
        var va = FloatVector.fromArray(SPECIES, a, i);
        var vb = FloatVector.fromArray(SPECIES, b, i);
        var vc = va.mul(va)
                   .add(vb.mul(vb))
                   .neg();
        vc.intoArray(c, i);
    }
    for (; i < a.length; i++) {
        c[i] = (a[i] * a[i] + b[i] * b[i]) * -1.0f;
    }
}

流收集器和流 API
如果您还记得,流收集器Stream Gatherers是 Java Development Kid 22 版本中预览的一部分。现在它将完全添加到 JDK 23 中。

  • Stream Gatherers 将增强Stream API以支持自定义操作。
  • 它们还允许流管道以当前内置操作难以实现的方式帮助转换数据。
  • 这样做的目标是使流管道更加灵活和富有表现力——这也将允许自定义操作来操纵无限大小的流。

使用 类文件 API 的目的是提供一个用于处理类文件的 API:

  • 该 API 跟踪 Java 虚拟机规范定义的类文件格式。
  • 这也意味着它将使 JDK 组件能够迁移到标准 API,并删除 Java 开发工具包的ASM 库副本。

类文件 API 添加了一些微调 :

  • 包括简化类 CodeBuilder ,
  • 默认情况下包含字节码指令的工厂方法,包括低级工厂、中级工厂和基本块的高级构建器。

下面是 ASM CodeBuilder 与 Java CodeBuilder 的一些示例代码。

ASM CodeBuilder 代码示例

ClassWriter classWriter = ...;
MethodVisitor mv = classWriter.visitMethod(0, "fooBar", "(ZI)V", null, null);
mv.visitCode();
mv.visitVarInsn(ILOAD, 1);
Label label1 = new Label();
mv.visitJumpInsn(IFEQ, label1);
mv.visitVarInsn(ALOAD, 0);
mv.visitVarInsn(ILOAD, 2);
mv.visitMethodInsn(INVOKEVIRTUAL,
"Foo", "foo", "(I)V", false);
Label label2 = new Label();
mv.visitJumpInsn(GOTO, label2);
mv.visitLabel(label1);
mv.visitVarInsn(ALOAD, 0);
mv.visitVarInsn(ILOAD, 2);
mv.visitMethodInsn(INVOKEVIRTUAL,
"Foo", "bar", "(I)V", false);
mv.visitLabel(label2);
mv.visitInsn(RETURN);
mv.visitEnd();

Java CodeBuilder 示例代码

ClassBuilder classBuilder = ...;
classBuilder.withMethod("fooBar", MethodTypeDesc.of(CD_void, CD_boolean, CD_int), flags,
                        methodBuilder -> methodBuilder.withCode(codeBuilder -> {
    Label label1 = codeBuilder.newLabel();
    Label label2 = codeBuilder.newLabel();
    codeBuilder.iload(1)
        .ifeq(label1)
        .aload(0)
        .iload(2)
        .invokevirtual(ClassDesc.of(
"Foo"), "foo", MethodTypeDesc.of(CD_void, CD_int))
        .goto_(label2)
        .labelBinding(label1)
        .aload(0)
        .iload(2)
        .invokevirtual(ClassDesc.of(
"Foo"), "bar", MethodTypeDesc.of(CD_void, CD_int))
        .labelBinding(label2);
        .return_();
});

在 Java Development Kit 23 中,

  1. Java CodeBuilder 删除了与低级方法重复的中级方法,或者更糟糕的是,不经常使用的中级方法。
  2. 同时您重命名其余的中级方法以提高可用性。
  3. 他们还完善了 ClassSignature 班级模型。这意味着它已得到改进,可以更准确地对superclasses和的通用签名进行建模superinterfaces。

根据此功能背后的 OpenJDK 提案,Java 平台应该定义和实现一个标准的类文件 API,该 API 与类文件格式一起发展,该格式可以轻松地更改或发展大约每六个月一次。

模式中的原始类型
正如前面提到的,随着 Java Development Kit 23 的最新计划功能和版本的发布,我们获得了另一个对于 Java 开发人员来说非常值得注意的预览功能: primitive types in patterns, instanceof,  switch

此功能将通过允许:

  • 模式上下文中的原始类型模式来显着增强模式匹配。
  • 然后我们扩展instanceof 和 switch 来处理所有原始类型。
  • 这还包括在嵌套和顶级上下文中使用原始类型模式的模式匹配: 提供易于使用的构造,消除由于不安全的强制转换而丢失信息的风险
  • 其他目标包括将模式类型与 对齐 instanceof、 instanceof 与安全转换对齐以及
  • 允许 switch 处理任何原始类型的值。

原始类型Primitive Type代码案例:

switch (x.getStatus()) {
    case 0 -> "okay";
    case 1 ->
"warning";
    case 2 ->
"error";
    case int i ->
"unknown status: " + i;
}

super(...) 之前的语句
Java 开发包 22 中预览的其他功能也可以很容易地应用到 Java 开发包 23 中。

  • 其中包括 super(...) 之前的语句,这将为开发人员表达构造函数行为(即字符串模板)提供更大的自由度。
  • 这将使表达包含运行时计算值(即作用域值)的字符串变得更加容易。
  • 这样就可以在线程内和线程间共享不可变数据,并隐式声明类和实例主方法。

代码:
public class PositiveBigInteger extends BigInteger {

    public PositiveBigInteger(long value) {
        if (value <= 0)
            throw new IllegalArgumentException("non-positive value");
        super(value);
    }

}

总之,这些变化将使初学者更容易编写程序,而无需了解为大型或企业应用程序开发而设计的编程语言功能。

甲骨文公司还透露了 2024 年的 Java 计划。甲骨文公司概述了涉及OpenJDK项目的改进措施,从用于开发较小的、面向生产力的功能的Amber,到用于将Java扩展到GPU等国外编程模型的Babylon,再到用于用值对象增强Java对象模型以消除长期存在的性能瓶颈的Valhalla。