从jdk8升级到jdk17
文章目录
- 写在前面
- 1、JDK17的安装与java环境变量
- 1.1、第一种:把jdk1.8更换为jdk17
- 1.2、第二种jdk1.8与jdk17并存
- 2、SpringBoot 3.0尝鲜
- 2.1、pom.xml
- 2.2、启动类
- 2.3、idea中可能需要你配置的内容
- 3、新特性
- 3.1、java 9 新增
- 3.2、java 10 新增
- 3.3、java 11 新增
- 3.4、java 12 新增
- 3.5、java 13 新增
- 3.6、java 14 新增
- 3.7、java 15 新增
- 3.8、java 16 新增
- 3.9、java 17 新增
写在前面
从jdk8升级到jdk17,会遇到哪些问题?
1、JDK17的安装与java环境变量
首先从官网上下载一个JDK17的包,windows系统可能有这两种包(压缩包和安装包)
https://www.oracle.com/java/technologies/javase/jdk17-archive-downloads.html
这里我们以压缩包为例,下载完直接解压,放到一个非中文路径下(复制这个路径)
接下有两种使用JDK17的方式:
1.1、第一种:把jdk1.8更换为jdk17
接下来找到系统环境变量,把JAVA_HOME变成JDK17的路径
1.2、第二种jdk1.8与jdk17并存
如果你只是想尝尝鲜,那么不建议你把环境变量改为jdk17。你只需解压jdk17后,在对应的编码工具里面添加jdk17,例如这里,我在idea中添加JDK17
2、SpringBoot 3.0尝鲜
SpringBoot 3.0最低使用jdk17、maven3.5
2.1、pom.xml
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"><modelVersion>4.0.0</modelVersion><parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent</artifactId><version>3.0.0-M4</version><relativePath/></parent><groupId>com.example</groupId><artifactId>demo</artifactId><version>0.0.1-SNAPSHOT</version><name>demo</name><description>springboot3-mavenDemo</description><properties><!--Jdk版本要求17以上--><java.version>17</java.version></properties><dependencies><!--引入spring-boot-starter-web,支持web开发--><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency></dependencies><build><plugins><!--spring boot maven插件,支持maven的全流程命令以及程序运行--><plugin><groupId>org.springframework.boot</groupId><artifactId>spring-boot-maven-plugin</artifactId></plugin></plugins></build><repositories><!--由于目前3.0还是处于里程碑版本,等到正式release版本,此配置不需要--><repository><id>spring-milestones</id><name>Spring Milestones</name><url>https://repo.spring.io/milestone</url><snapshots><enabled>false</enabled></snapshots></repository></repositories><pluginRepositories><pluginRepository><id>spring-milestones</id><name>Spring Milestones</name><url>https://repo.spring.io/milestone</url><snapshots><enabled>false</enabled></snapshots></pluginRepository></pluginRepositories></project>
2.2、启动类
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;@SpringBootApplication
public class DemoApplication {public static void main(String[] args) {SpringApplication.run(DemoApplication.class, args);}}
有这两个文件你就可以尝试启动了
2.3、idea中可能需要你配置的内容
1、设置中的ava编译器
2、项目结构中的设置
3、新特性
本文提到的新特性主要侧重于代码结构与API上
3.1、java 9 新增
1、module-info.java:该文件必须位于项目的根目录中。该文件用于定义模块需要什么依赖,以及那些包被外部使用。
2、jshell:jshell工具提供了一个交互式命令界面,可以评估声明,语句和表达式,无需编译即可返回执行结果。
3、接口的私有方法
public interface MyInterface {void normalInterfaceMethod();default void defaultMethod1(){privateMethod();}default void defaultMethod2(){privateMethod();}//接口的私有方法可以在JDK9中使用private void privateMethod(){System.out.println("这是一个接口的私有方法");}
}
4、资源自动关闭
InputStreamReader reader = new InputStreamReader(System.in);
OutputStreamWriter writer = new OutputStreamWriter(System.out);
//多资源用分号隔开
try (reader;writer) {//......
} catch (IOException e) {e.printStackTrace();
}
// reader和writer会自动关闭
5、可以在匿名实现类中重写方法等操作
Set<String> set = new HashSet<>(){//匿名实现类重写add方法。@Overridepublic boolean add(String s) {System.out.println("执行add方法");return super.add(s);}
};
set.add("1");
6、String 存储结构变更
JDK9将String底层存储数据改为byte数组,StringBuffer和StringBuilder也同样做了变更,将以往char数组改为byte数组。
7、使用of方法直接快速创建只读集合
List<String> list = List.of("A", "B", "C");
List<String> copy = List.copyOf(list);
System.out.println(list == copy); // trueList<String> list1 = new ArrayList<String>();
List<String> copy1 = List.copyOf(list1);
System.out.println(list1 == copy1); // false,非of方法创建的copyOf->false
8、增强 Stream API,Stream接口中新增4个方法:dropWhile、takeWhile、ofNullable,为iterate方法新增重载方法。
List<Integer> list = Arrays.asList(45,43,76,87,42,77,90,73,67,88);
list.stream().takeWhile((x) -> x < 80 ).forEach(System.out::println);// 返回结果
// 45
// 43
// 76
9、改进 Optional 类,主要是新增了三个方法:stream,ifPresentOrElse 和 or 。
List<String> list = List.of("A", "B", "C", "D", "E", "F");
Optional<List<String>> optional = Optional.of(list);
optional.stream().forEach(System.out::println);
10、多分辨率图像 API,在 java.awt.image 包下新增了支持多分辨率图片的API,用于支持多分辨率的图片。
11、支持HTTP2,全新的 HTTP 客户端 API 可以从 jdk.incubator.httpclient 模块中获取。因为在默认情况下,这个模块是不能根据 classpath 获取的,需要使用 add modules 命令选项配置这个模块,将这个模块添加到 classpath中。
12、其他
3.2、java 10 新增
1、可以使用var作为局部变量类型推断标识符,仅适用于局部变量
var str = "ABC"; //根据推断为 字符串类型
var l = 10L;//根据10L 推断long 类型
var flag = true;//根据 true推断 boolean 类型
var flag1 = 1;//这里会推断boolean类型。0表示false 非0表示true
var list = new ArrayList<String>(); // 推断 ArrayList<String>
var stream = list.stream(); // 推断 Stream<String>
//错误的用法
var error;//×
2、其他:将JDK多存储库合并为单存储库、垃圾回收接口、并行Full GC 的G1、应用数据共享、线程局部管控等。
3.3、java 11 新增
1、在Lambda表达式中,可以使用var关键字来标识变量,变量类型由编译器自行推断。
Arrays.asList("Java", "Python", "Ruby").forEach((var s) -> {System.out.println("Hello, " + s);});
2、字符串加强
// 判断字符串是否为空白
" ".isBlank(); // true
// 去除首尾空格
" Javastack ".strip(); // "Javastack"
// 去除尾部空格
" Javastack ".stripTrailing(); // " Javastack"
// 去除首部空格
" Javastack ".stripLeading(); // "Javastack "
// 复制字符串
"Java".repeat(3);// "JavaJavaJava"
// 行数统计
"A\nB\nC".lines().count(); // 3
3、InputStream 加强,transferTo,可以用来将数据直接传输到 OutputStream
var classLoader = ClassLoader.getSystemClassLoader();
var inputStream = classLoader.getResourceAsStream("javastack.txt");
var javastack = File.createTempFile("javastack2", "txt");
try (var outputStream = new FileOutputStream(javastack)) {inputStream.transferTo(outputStream);
}
4、HTTP Client API
var request = HttpRequest.newBuilder()
.uri(URI.create("https://javastack.cn"))
.GET()
.build();
var client = HttpClient.newHttpClient();
// 同步
HttpResponse<String> response = client.send(request, HttpResponse.BodyHandlers.ofString());
System.out.println(response.body());
// 异步
client.sendAsync(request, HttpResponse.BodyHandlers.ofString())
.thenApply(HttpResponse::body)
.thenAccept(System.out::println);
5、对Files类增加了writeString和readString两个静态方法
Files.writeString(Path.of("./", "tmp.txt"), // 路径"hello, jdk11 files api", // 内容StandardCharsets.UTF_8); // 编码
String s = Files.readString(Paths.get("./tmp.txt"), // 路径StandardCharsets.UTF_8); // 编码
6、一个文件中可以包含多个public类
7、Shebang文件,Shebang文件是Unix系统中常见的文件,以#!/path/to/executable作为文件的开头第一行,可以作为脚本小程序直接运行一段代码。
#!/g/jdk-11/bin/java --source 11public class SimpleInterest{public static void main(String[] args){if ( args == null || args.length < 3 ){System.err.println("Three arguments required: principal, rate, period");System.exit(1);}int principal = Integer.parseInt(args[0]);int rate = Integer.parseInt(args[1]);int period = Integer.parseInt(args[2]);double interest = Maths.simpleInterest(principal, rate, period);System.out.print("Simple Interest is: " + interest);}
}public class Maths{public static double simpleInterest(int principal, int rate, int period){if ( rate > 100 ){System.err.println("Rate of interest should be <= 100. But given values is " + rate);System.exit(1);}return ( principal * rate * period * 1.0 ) / 100;}
}
3.4、java 12 新增
1、Switch扩展了
switch (day) {case MONDAY, FRIDAY, SUNDAY -> System.out.println(6);case TUESDAY -> System.out.println(7);case THURSDAY, SATURDAY -> System.out.println(8);case WEDNESDAY -> System.out.println(9);
}int numLetters = switch (day) {case MONDAY, FRIDAY, SUNDAY -> 6;case TUESDAY -> 7;case THURSDAY, SATURDAY -> 8;case WEDNESDAY -> 9;
};
2、String类中新增transform()和indent()
3、Files类中新增mismatch()
4、支持unicode11和压缩数字格式化
var cnf = NumberFormat.getCompactNumberInstance(Locale.CHINA, NumberFormat.Style.SHORT);System.out.println(cnf.format(1_0000));System.out.println(cnf.format(1_9200));System.out.println(cnf.format(1_000_000));System.out.println(cnf.format(1L<<30));System.out.println(cnf.format(1L<<40));System.out.println(cnf.format(1L<<50));//1万//2万//100万//11亿//1兆//1126兆
5、其他:JVM Constants API、默认CDS存档、可中断的G1 Mixed GC等
3.5、java 13 新增
1、NioSocketImpl替换了PlainSocketImpl
public class HelloApp {public static void main(String[] args) {try (ServerSocket serverSocket = new ServerSocket(8888)) {boolean running = true;System.out.println("listened 8888");while (running) {Socket clientSocket = serverSocket.accept();//do something with clientSocket}} catch (IOException e) {e.printStackTrace();}}
}
2、新的关键字yield用于返回switch语句的内容
// 没有逻辑的返回
int numLetters = switch (day) {case MONDAY, FRIDAY, SUNDAY -> 6;case TUESDAY -> 7;case THURSDAY, SATURDAY -> 8;case WEDNESDAY -> 9;
};// 逻辑较多的处理String result = switch (number) {case 1, 2:// 逻辑代码yield "one or two";case 3:// 逻辑代码yield "three";case 4, 5, 6:yield "four or five or six";default:yield "unknown";};return result;
3、添加了“”“ 长文本内容 ”“”
开头"““之后必须另起一行,另外结尾的””"是否另起一行有不同的效果
String html = """<html><body><p>Hello, world</p></body></html>""";
3.6、java 14 新增
1、类型匹配instanceof增强
Object obj = "kuaidi100";
if(obj instanceof String str){//直接使用str
}
2、数据载体的类型 record
record默认为final的,成员变量也为final,所以没有set方法。在JDK15中对它进行了继续加强。
public record Kuaidi100Record(@Name("name") int x, int y) {public static String one;
}
3、其他:移除CMS垃圾收集器、ZGC支持windows,macOS等
3.7、java 15 新增
1、新加入 Edwards-Curve 数字签名算法(EdDSA)实现加密签名。
// example: generate a key pair and sign
KeyPairGenerator kpg = KeyPairGenerator.getInstance("Ed25519");
KeyPair kp = kpg.generateKeyPair();
// algorithm is pure Ed25519
Signature sig = Signature.getInstance("Ed25519");
sig.initSign(kp.getPrivate());
sig.update(msg);
byte[] s = sig.sign();// example: use KeyFactory to contruct a public key
KeyFactory kf = KeyFactory.getInstance("EdDSA");
boolean xOdd = ...
BigInteger y = ...
NamedParameterSpec paramSpec = new NamedParameterSpec("Ed25519");
EdECPublicKeySpec pubSpec = new EdECPublicKeySpec(paramSpec, new EdPoint(xOdd, y));
PublicKey pubKey = kf.generatePublic(pubSpec);
2、封闭类sealed,有了这个特性,意味着以后不是你想继承就继承,想实现就实现了,你得经过允许才行。
public abstract sealed class Studentpermits ZhangSan, LiSi, ZhaoLiu {...}
3、隐藏类
// 一个普通类
public class JEP371HiddenClasses {public static String hello() {return "https://www.didispace.com";}
}// 隐藏类
String filePath = "JEP371HiddenClasses.class";
byte[] b = Files.readAllBytes(Paths.get(filePath));
log.info(Base64.getEncoder().encodeToString(b));// 最终打印(这就是个隐藏类)
yv66vgAAAD0AFAoAAgADBwAEDAAFAAYBABBqYXZhL2xhbmcvT2JqZWN0AQAGPGluaXQ+AQADKClWCAAIAQAZaHR0cHM6Ly93d3cuZGlkaXNwYWNlLmNvbQcACgEALmNvbS9kaWRpc3BhY2UvZGVidWcvamF2YTE1L0pFUDM3MUhpZGRlbkNsYXNzZXMBAARDb2RlAQAPTGluZU51bWJlclRhYmxlAQASTG9jYWxWYXJpYWJsZVRhYmxlAQAEdGhpcwEAMExjb20vZGlkaXNwYWNlL2RlYnVnL2phdmExNS9KRVAzNzFIaWRkZW5DbGFzc2VzOwEABWhlbGxvAQAUKClMamF2YS9sYW5nL1N0cmluZzsBAApTb3VyY2VGaWxlAQAYSkVQMzcxSGlkZGVuQ2xhc3Nlcy5qYXZhACEACQACAAAAAAACAAEABQAGAAEACwAAAC8AAQABAAAABSq3AAGxAAAAAgAMAAAABgABAAAAAwANAAAADAABAAAABQAOAA8AAAAJABAAEQABAAsAAAAbAAEAAAAAAAMSB7AAAAABAAwAAAAGAAEAAAAGAAEAEgAAAAIAEw==// 使用隐藏类
void testHiddenClasses() throws Throwable {// 1. 加载encode之后的隐藏类String CLASS_INFO = "yv66vgAAAD0AFAoAAgADBwAEDAAFAAYBABBqYXZhL2xhbmcvT2JqZWN0AQAGPGluaXQ+AQADKClWCAAIAQAZaHR0cHM6Ly93d3cuZGlkaXNwYWNlLmNvbQcACgEALmNvbS9kaWRpc3BhY2UvZGVidWcvamF2YTE1L0pFUDM3MUhpZGRlbkNsYXNzZXMBAARDb2RlAQAPTGluZU51bWJlclRhYmxlAQASTG9jYWxWYXJpYWJsZVRhYmxlAQAEdGhpcwEAMExjb20vZGlkaXNwYWNlL2RlYnVnL2phdmExNS9KRVAzNzFIaWRkZW5DbGFzc2VzOwEABWhlbGxvAQAUKClMamF2YS9sYW5nL1N0cmluZzsBAApTb3VyY2VGaWxlAQAYSkVQMzcxSGlkZGVuQ2xhc3Nlcy5qYXZhACEACQACAAAAAAACAAEABQAGAAEACwAAAC8AAQABAAAABSq3AAGxAAAAAgAMAAAABgABAAAAAwANAAAADAABAAAABQAOAA8AAAAJABAAEQABAAsAAAAbAAEAAAAAAAMSB7AAAAABAAwAAAAGAAEAAAAGAAEAEgAAAAIAEw==";byte[] classInBytes = getDecoder().decode(CLASS_INFO);Class<?> proxy = MethodHandles.lookup().defineHiddenClass(classInBytes, true, MethodHandles.Lookup.ClassOption.NESTMATE).lookupClass();// 输出类名log.info(proxy.getName());// 输出类有哪些函数for(Method method : proxy.getDeclaredMethods()) {log.info(method.getName());}// 2. 调用hello函数MethodHandle mh = MethodHandles.lookup().findStatic(proxy, "hello", MethodType.methodType(String.class));String result = (String) mh.invokeExact();log.info(result);
}
4、其他
3.8、java 16 新增
1、主要是java10到15中的预览功能转正。
2、其他:可弹性伸缩的元数据区、 新的打包工具jpackage、针对Value-Based类的编译器warning提示、提供向量计算的API、提供操作外部内存的能力等
3.9、java 17 新增
1、正式引入密封类sealed class,限制抽象类的实现;
2、统一日志异步刷新,先将日志写入缓存,然后再异步刷新;
3、其他:特定于上下文的反序列化过滤器、弃用 Applet API 以进行删除、增强型伪随机数生成器、恢复始终严格的浮点语义
从jdk8升级到jdk17相关推荐
- jdk8升级成jdk17报错 module java.base does not “opens java.lang“ to unnamed module @1941a8ff
jdk9+ 出现错误 module java.base does not "opens java.lang" to unnamed module @1941a8ff 在启动类配置中 ...
- JDK8升级JDK9 HTT2 TLS问题解决之路(艰辛)
背景描述 s公告服务是雪球行情的公告抓取服务,主要负责从相关网站抓取A股.港股.美股公告,调用接口发贴.数据抓取是在该业务场景是行情数据的入口,影响以后的的处理逻辑.因此,通过代理池+proxy的方式 ...
- Java 8 要过时了?从JDK8飞升到JDK17,一次性给你讲明白
背景 2022年Spring6和 SpringBoot3相继推出,在此之前,Java社区一直是"新版任你发,我用Java 8",不管新版本怎么出,很少有人愿意升级. 这一次,Spr ...
- spring版本 jdk8_从JDK8升级到JDK11,看这篇就足够了
原文地址:https://blog.codefx.org/java/java-11-migration-guide/. 在原文的基础上,增加了一些我遇到的具体的坑还有在特定场景下的解决方案,供大家参考 ...
- JDK11变化详解JDK8升级JDK11详细指南
原文链接:https://yq.aliyun.com/articles/659407 官方英文原版: https://docs.oracle.com/en/java/javase/11/migrate ...
- JDK11变化详解,JDK8升级JDK11详细指南
为什么80%的码农都做不了架构师?>>> 官方英文原版: https://docs.oracle.com/en/java/javase/11/migrate/index.htm ...
- windows10 jdk8升级到11后环境变量配置不生效
一.问题 以前安装过安装版的jdk后,配置过环境变量,然后现在更换jdk版本且修改环境变量并不能生效,如原本安装了1.8,现更换为11,且配置了环境变量,但是java -version仍显示1.8. ...
- 从JDK8到JDK17,需要注意的一些新特性
这篇文章并非单一的介绍JDK17的新特性,而是将jdk8到jdk17之间所有新加入的特性进行了简单的汇总,罗列一系列重要的改动,以便从JDK8升级到JDK17. 模块化开发 这并非jdk17的新特性, ...
- openJDK 官方二进制下载
前言 由于Oracle的jdk收费license,JDK8 201~221开始不免费了,目前有最近的JDK17 LTS明确免费了,但是不确定什么时候会修改协议,而且升级jdk也不能从jdk8升级到jd ...
最新文章
- linux vim 高级,Vim命令高级用法
- 产权分割商铺,太坑人!
- 标签view文字自动换行
- jmeter响应数据Unicode编码转换为汉字
- matlab中(1 )什么意思,matlab中area(1)什么意?mat – 手机爱问
- css布局左右2边固定,中间自适应
- mos管防倒灌电路_MOS管自举电路工作原理及升压自举电路结构图
- 希尔排序--Java
- 配置vivado用vscode编辑文本
- CentOS 7中将Tomcat设置为系统服务
- List集合之LinkedList
- osgb转3dtiles 原理_自动控制原理实验箱无法通行故障维修
- html+div+css+jquery+javascript的关系
- 桌面打不开计算机控制面板,右键桌面nvidia控制面板打不开的解决方法 - 系统家园...
- 【神科普】诺基亚:你以为它死了,其实它已重回世界第二
- 操作 神通数据库_神通大型通用数据库
- 计算机初始《wps表格》教案,wps教案
- MMC-HVDC仿真模型,pscad柔性直流输电仿真mmc仿真模型,双端mmc模型,MMC为21电平NLM和均压控制
- MQTT自定义透传_DTU连接阿里云
- BrowserslistError: Unknown version 67 of android
热门文章
- 目标检测带标签数据增强代码
- 蚂蚁与大象共舞?DeFi 如何选择更完美的链上治理
- ACCESS 2003数据库的创建
- mac App Store下载出现“未知错误”可能原因及解决办法
- Python项目容器化实践 - 编排方案: Mesos+Marathon
- Vue SEO的四种方案
- Redisson 3.7.x 版本报非法反射:WARNING: An illegal reflective access operation has occurred
- Tomcat文件夹目录
- 小米耳机处于可配对模式_坚果上架Smartisan真无线耳机
- 云计算机不支持加密狗,电脑两个用户名会不会造成加密狗不能识别?