大家好,我是R哥。
Java 25 刚发布半年之久(Java 25 正式发布),很多人可能还没听说过,现在 Java 26 又来了,我真的人麻了啊。。。
需要注意的是,Java 26 并不是 LTS(长期支持版本),千万不要用在生产环境里,因为它许多特性还在预览阶段,可能会有不兼容的变动。
废话不多说了,下面我们来看看 Java 26 都有哪些新特性。。
如何下载
Java 26 的下载入口:
https://www.oracle.com/java/technologies/downloads/
如果你只是想本地装个环境体验一下,直接下就行,但千万别打算拿去跑生产。。
版本定位
这次得说明下,Java 26 并是一个长期支持的大版本,上一个长期支持的版本是 Java 25,如下表所示:
版本发布日期优先支持期限延长支持期限8 (LTS)03/201403/202212/20309 - 10 (non-LTS)09/201709/2018不支持11 (LTS)09/201809/202301/203212 - 16 (non-LTS)03/201909/2021不支持17 (LTS)09/202109/202609/202918 - 20 (non-LTS)03/202209/2023不支持21 (LTS)09/202309/202809/203122 (non-LTS)03/202409/2024不支持23 (non-LTS)09/202403/2025不支持24 (non-LTS)03/202509/2025不支持25 (LTS)09/202509/203009/203326 (non-LTS)03/202609/2026不支持27 (non-LTS)09/202603/2027不支持Java 版本分为 LTS(Long-Term Support,长期支持版) 和 Non-LTS(非长期支持版),它们的主要区别如下:
对比项LTS 版本(长期支持)Non-LTS 版本(非长期支持)发布周期每 2 年 一次每 6 个月 发布一次支持时长官方长期支持(8 年+)仅支持 6 个月适用场景生产环境、企业级项目、长期维护的系统个人学习、实验性项目、尝鲜新特性稳定性更稳定,企业级可用新特性多,但可能不稳定安全性持续提供安全更新和 bug 修复仅在生命周期内提供短期修复新特性主要以稳定性和性能优化为主包含最新特性,但可能在下个版本修改或移除所以,用不用 Java 26 分场景来看:
- 生产环境追求稳的团队,还是优先用 Java 21 和 Java 25。
- 想跟上 Java 演进方向的人,Java 26 很值得看,因为里面不少东西明显是在给下一个大版本试水。
这也是 Java 半年发版最有价值的地方,它不一定每次都让你全面升级,但它一直在替未来铺路。
Java 26 新特性
JDK 26 带来了 10 个重大升级:
编号特性名称中文解释备注500Prepare to Make Final Mean Final准备让 final 真正变成 final504Remove the Applet API移除 Applet API516Ahead-of-Time Object Caching with Any GC任意 GC 的 AOT 对象缓存517HTTP/3 for the HTTP Client APIHTTP Client 支持 HTTP/3522G1 GC: Improve Throughput by Reducing SynchronizationG1 通过减少同步提升吞吐量524PEM Encodings of Cryptographic Objects加密对象的 PEM 编码第 2 次预览525Structured Concurrency结构化并发第 6 次预览526Lazy Constants懒加载常量第 2 次预览529Vector API向量 API第 11 次孵化530Primitive Types in Patterns, instanceof, and switch模式匹配支持更多原始类型第 4 次预览其中包括 4 个预览特性、1 个孵化特性,看着数量不算多,但这 10 个里面,既有语法继续推进,也有运行时性能提升,还有标准库和安全边界的持续加强。
这些新特性涵盖了 Java 语言的创新、安全性增强、性能和运行时的改进、库的优化,以及对 JDK 的维护和清理工作,整体来说都是相当给力的升级。
完整特性说明可以参考:
- https://openjdk.org/projects/jdk/26/
- https://jdk.java.net/26/release-notes
1、语言层特性
530 - Primitive Types in Patterns, instanceof, and switch
模式匹配支持更多原始类型,第四次预览。
Java 这几年一直在补模式匹配这条线,instanceof、switch 等,一路都在往更统一的方向走。
但之前这套东西更多还是围着引用类型打转,碰到 long、float、double、boolean 这些原始类型,多少还是有点别扭。
Java 26 这次继续把这个坑填平,switch 现在能更自然地处理这些原始类型了。
来看一个示例:- float score = 86.5f;
- String level = switch (score) {
- case 0f -> "zero";
- case float s when s < 60f -> "fail";
- case float s when s < 85f -> "pass";
- case float s -> "excellent";
- };
复制代码 现在编译器对 switch 的检查也更严格了,这些修改使编译器能够识别出更多类型的编码错误,不过此前合法的少数 switch 结构现在将被拒绝。
500 - Prepare to Make Final Mean Final
准备让 final 真正变成 final。
这个名字非常直接,意思也很明确。
按正常理解,final 字段应该就是不可变的。但现实情况是,Java 里长期存在通过深度反射去修改 final 字段的玩法。
这就会带来两个问题:
- 代码语义没那么可信;
- JVM 也没法完全放心做相关优化。
Java 26 这次还没有一步到位封死,而是先对这类修改行为发出 warning 警告,提前给框架、序列化库、各种底层工具一个适配期。
未来的 Java 版本会默认限制 final 字段的修改,从而提升程序的安全性和运行效率。
对于应用开发者来说,如果确实有必要修改 final 字段,可以有选择地开启相关能力,这样既能避开当前的警告,也能应对将来的限制。
517 - HTTP/3 for the HTTP Client API
HTTP Client 支持 HTTP/3。
这个特性我觉得很多人会喜欢,因为它真的很实用。
Java 标准库自带的 HttpClient 这几年已经越来越顺手了,但在协议支持上一直差一口气,现在 HTTP/3 终于补上了。
而且这个支持方式挺舒服,不需要你换掉整套 API,只要显式指定协议版本就行:- var client = HttpClient.newBuilder()
- .version(HttpClient.Version.HTTP_3)
- .build();
- var request = HttpRequest.newBuilder(URI.create("https://openjdk.org/"))
- .version(HttpClient.Version.HTTP_3)
- .GET()
- .build();
复制代码 还有个很实在的点,如果目标服务不支持 HTTP/3,它默认还能自动降级到 HTTP/2 或 HTTP/1.1,完全透明的,不至于一上来就不可用。
所以,对于网关、微服务客户端、API 调用层,或者网络环境比较复杂的场景,这个特性是有实际价值的。
524 - PEM Encodings of Cryptographic Objects
加密对象的 PEM 编码,第二次预览。
做过证书、密钥、TLS 配置的人,对 PEM 肯定不陌生。
平时我们看到的这种内容就是 PEM 格式:- -----BEGIN PUBLIC KEY-----
- MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEi/kRGOL7wCPTN4KJ2ppeSt5UYB6u
- cPjjuKDtFTXbguOIFDdZ65O/8HTUqS/sVzRF+dg7H3/tkQ/36KdtuADbwQ==
- -----END PUBLIC KEY-----
复制代码 Java 26 继续预览这套 API,目标也很明确,就是把密钥、证书、证书吊销列表这些对象和 PEM 文本之间的转换,尽量做成标准能力,不再总让大家靠第三方库、自己手搓。
这类特性对企业开发真的是减负,尤其是安全接入、证书管理、合规场景。
525 - Structured Concurrency
结构化并发,第六次预览。
结构化并发已经预览很多次了,说明 OpenJDK 对它非常认真。
它解决的问题也很实际,以前你写多线程,不难,但一组有关系的并发任务,错误怎么传、取消怎么做、结果怎么收,写到后面经常乱。
结构化并发就是把一组相关任务当成一个整体来处理,简化了错误处理和取消操作,提升了程序的可靠性,也让监控变得更方便。
来看示例:- Response handle() throws InterruptedException {
- try (var scope = StructuredTaskScope.open()) {
- Subtask<String> user = scope.fork(() -> findUser());
- Subtask<Integer> order = scope.fork(() -> fetchOrder());
- scope.join();
- return new Response(user.get(), order.get());
- }
- }
复制代码 这种写法比一堆 Future、CompletableFuture 拼来拼去顺手太多了。尤其是和虚拟线程搭配起来以后,Java 并发这块真的是越来越像现代语言了。。。
结构化并发是把在不同线程中运行的相关任务当作一个整体来处理,而 Future 大多是在把多个任务作为单独任务对待时派上用场的。一个 scope 通常只会阻塞一次,等待它的子任务结果,然后集中处理异常。
你可能在会纳闷,为什么这些 fork 方法没有返回更强大的 CompletableFuture 对象,毕竟,这些方法返回的 Future 只有在确认它们完成后才能用。所以,使用 CompletableFuture 其实也没啥用,因为它主要是为未完成的 futures 异步编程模式设计的,而 StructuredTaskScope 则更偏向于阻塞式的操作。
所以,对于 Future 和 CompletableFuture 来说,它们虽然提供了一些并发自由度,但在结构化并发中反而起到了反作用。
526 - Lazy Constants
懒加载常量,第二次预览。
这个特性是 Java 25 里 StableValue 的继续演进版,在 Java 26 里名字直接改成了 LazyConstant,意思也更好懂。
懒加载常量存放的是不可变数据的对象,在 JVM 眼中就像真正的常量一样,能够享受到和声明字段 final 时相同的性能优化。不过,相比于 final 字段,懒加载常量在初始化时机上更具灵活性。
比如下面的示例:- class OrderController {
- private final LazyConstant<Logger> logger =
- LazyConstant.of(() -> Logger.create(OrderController.class));
- void submitOrder() {
- logger.get().info("order submitted");
- }
- }
复制代码 这样写的好处是,只有真正用到 logger 的时候才初始化,但 JVM 又能把它按常量去优化。
529 - Vector API
向量 API,第十一次孵化。
这个 API 真的挺能熬,已经到 第十一次孵化 了。
它的目标还是老样子,让 Java 可以表达向量计算,并在支持的 CPU 架构上,运行时编译成更优的向量指令,从而拿到比标量计算更好的性能。
这东西对普通 CRUD 业务同学感知不大,但对数据处理、科学计算、图像处理、AI 推理这类场景,在现如今 AI 技术发展的今天意义很大。
而且它一直还没正式转正,也说明这块能力依然在等更成熟的底层配合,比如 Valhalla 那条线。
2、性能和运行时特性
516 - Ahead-of-Time Object Caching with Any GC
任意 GC 的 AOT 对象缓存。
这个特性是 Project Leyden 方向上的继续推进。
简单说,就是 AOT 对象缓存不再只适配某一种 GC 了,现在可以使用任意 GC,连 ZGC 这种低延迟回收器也能兼容这套机制。。
它可以将预先初始化好的 Java 对象以 GC 无关的格式,顺序加载到内存中。还优化了提前缓存(ahead-of-time cache),让 HotSpot 虚拟机在启动和热身阶段表现得更快,同时支持任何 GC,包括低延迟的 ZGC。
所以,这一改进提升了资源利用率,也加快了 Java 应用的启动速度。
OpenJDK 在 JEP 516 里提到,像 Spring PetClinic 这样的应用,在已有的 AOT 类加载和链接方案下,生产启动速度可以提升 41%。
所以,这类能力对云原生、弹性扩容、冷启动场景都挺香的。
522 - G1 GC: Improve Throughput by Reducing Synchronization
G1 通过减少同步来提升吞吐。
通过提升内存效率,帮助开发者在更短的时间内完成更多工作。
Java 26 在 G1 上做的事情,就是减少了应用程序线程和垃圾回收线程之间的同步,提高了使用 G1 垃圾回收器时的吞吐量。
运行速度更快,就能支持更多用户而无需额外硬件,Java 大大提升了效率,降低了基础设施成本,还带来更流畅的用户体验。
官方给的数据也不算虚:
- 在频繁修改对象引用字段的应用里,吞吐提升大概有 5% - 15%;
- 就算不是这类重场景,也观察到了 最高 5% 的收益;
- 在 x64 平台上,G1 写屏障的指令数大概从 50 条 压到了 12 条。
这种特性很有价值,尤其是对于那些对 GC 敏感的应用来说。
3、其他特性
504 - Remove the Applet API
移除 Applet API。
这玩意终于要被彻底送走了。。
Applet API 在 JDK 9 就已经开始废弃,JDK 17 进入准备移除状态,到 Java 26 终于正式删除。
原因也很简单,现代浏览器早就不支持 Applet 了,所以,Applet 留在 JDK 里已经没什么意义。
移除 Applet API 后,可以缩减安装包和源代码的体积,同时提升应用的性能、稳定性和安全性。
如果你项目里现在还有 java.applet.Applet、javax.swing.JApplet 这类东西,那是你的代码真的该考古了。。。
还有两件事
除了 10 个 JEP,这次 Oracle 官方博客里还有两件偏企业侧的消息,也挺值得看。
第一件是 JavaFX 商业支持回来了,真是活久见了。
Oracle 这次明确说了,会重新提供 JavaFX 的商业支持,JDK 8 的 JavaFX 商业支持还延到了 2028 年 3 月。这个消息对大多数后端同学没那么刺激,但对桌面端、可视化、教学场景、老项目维护来说,其实挺现实。
第二件是 Oracle 推了一个新的 Oracle Java Verified Portfolio,把 JavaFX、Helidon、VS Code 的 Java 扩展这些能力弄进了一个企业级组合支持包里。
这类消息你要说跟日常写业务代码有多大关系,也未必。
但它至少说明一件事,Oracle 现在不是只想发 JDK,它还想把 Java 周边生态的企业支持也一块打包得更完整。
总结
Java 26 这次给我的感觉,不是王炸级大版本,而是一个处处都在憋着大招的过渡版本。
HttpClient 终于把 HTTP/3 补上了,结构化并发还在持续打磨,模式匹配继续往原始类型推进,G1 在默认 GC 的位置上继续狠狠压榨性能,AOT cache 开始跟更多 GC 体系打通,final 这玩意也终于要 final 了。
现在再看,Java 还是稳,还是强,但它的变化节奏已经不是那种一夜之间颠覆式的了,而是每 6 个月往前拱一点,版本号也越拉越大。
这恰恰就是 Java 最可怕的地方,为了升级而升级,一年 2 个版本,有必要吗?对于很多还在用 Java 8 的公司来说,这谁跟得上啊?
但升级到 Java 17、Java 21、Java 25 这些长期支持版本,还是很有必要的,毕竟它们带来的性能、安全、语言特性提升都是实打实的,而且主流框架都放弃 Java 8 了要求 Java 17+ 了。
比如:
- Spring Boot 正式弃用 Java 8,要求 17+!!
- Kafka 4.0 发布,Java 8 和 Zookeeper 彻底被抛弃了!!
所以,别停留在 Java 8 了,赶紧升级吧,Java 26 不用急着上,但 Java 17 还是很值得的。
⚠️ 版权声明:
本文系公众号 "Java技术宅" 原创,转载、引用本文内容请注明出处,抄袭、洗稿一律投诉侵权,后果自负,并保留追究其法律责任的权利。
来源:程序园用户自行投稿发布,如果侵权,请联系站长删除
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作! |