Java

昨天给大家介绍了Java 16中的Stream增强,可以直接通过toList()来转换成List。 主要涉及下面这几种转换方式: list.stream().toList();list.stream().collect(Collectors.toList());list.stream().collect(Collectors.toUnmodifiableList()); 然后,看到有网友评论问:Stream.toList()和Collectors.toList()的区别是什么?哪个性能好? 处理结果的区别,其实上一篇文章和视频里都有说: Stream.toList()返回的List是不可变List,不能增删改 Collectors.toList()返回的是个普通的List,可以增删改 Collectors.toUnmodifiableList()返回的List是不可变List,不...

前几天分享了如何优雅的调试Java Stream操作。然后有小伙伴对其中的一段代码有一些疑问:“为啥你的stream可以直接toList而不必collect?” 下面就给大家解读下这个内容。 疑问的代码片段如下: public class StreamTest { @Test void test() { List<String> list = List.of("blog.didispace.com", "spring4all.com", "openwrite.cn", "www.didispace.com"); List<String> result = list.stream() .filter(e -> e.contains("didispace.com")) ...

在Java 9中又新增了一些API来帮助便捷的创建不可变集合,以减少代码复杂度。 本期配套视频:Java 9 新特性:快速定义不可变集合 常规写法以往我们创建一些不可变集合的时候,通常是这样写的: // 不可变的SetSet<String> set = new HashSet<>();set.add("a");set.add("b");set.add("c");set = Collections.unmodifiableSet(set);// 不可变的ListList<Integer> list = new ArrayList<>();list.add(1);list.add(2);list.add(3);list = Collections.unmodifiableList(list); Java8的写法在Java 8的时候,利用St...

什么是交互式编程环境?重点词交互,在这样的编程环境中,你每输入一行代码,环境都会给你一个反馈,这就是交互式的编程环境。这种编程环境并不太适合工程化的复杂性需求,但在一些快速验证、简单计算之类的场景下还是非常好用的。其实交互式编程环境在其他高级语言中很早就有了,而Java直到Java 9才正式推出了这样的工具。 下面就来一起学习下,这个Java中的交互式编程环境JShell。 JShell快速入门启动JShell打开终端,然后执行命令:jshell,执行效果如下: ➜ ~ jshell| 欢迎使用 JShell -- 版本 9| 要大致了解该版本, 请键入: /help introjshell> 执行计算在jshell中可以快速的执行计算操作并获得结果,比如这样: jshell> 1+2$1 ==> 3 定义变量在jshell中也可以定义变量与函数,比如,你可以...

以前我们定义类都是用class关键词,但从Java 16开始,我们将多一个关键词record,它也可以用来定义类。record关键词的引入,主要是为了提供一种更为简洁、紧凑的final类的定义方式。 下面就来具体了解record类的细节。 声明record类声明record类的基础语法: record range(int start, int end){} 我们知道class类可以在单独文件中生命,也可以在其他类中申明。那么record类也一样,它有这几种申明方式: 单独文件申明: public record range(int start, int end){} 在类内部申明: public class DidispaceTest { public record range(int start, int end)...

隐藏类,是一种不能被其他类直接使用的类。引入隐藏类的主要目的是给框架来使用,使得框架可以在运行时生成类,并通过反射间接使用它们。可能有点抽象,不要紧,下面我们通过一个例子来直观的认识它! 隐藏类案例第一步:先创建一个普通的Java类 public class JEP371HiddenClasses { public static String hello() { return "https://www.didispace.com"; }} 第二步:编译一下,或得编译后的class文件。然后使用Base64对文件内容Encode,你可以用各种工具,也可以用下面代码来获取: String filePath = "JEP371HiddenClasses.class";byte[] b = Files.readAllBytes...

还记得Java 16中的instanceof增强吗? 通过下面这个例子再回忆一下: Map<String, Object> data = new HashMap<>();data.put("key1", "aaa");data.put("key2", 111);if (data.get("key1") instanceof String s) { log.info(s);} 上面这个场景里,Map中的Value值存在不同的类型,所以使用instanceof来判断取出的value是什么类型,然后根据不同类型来进行处理。那么,接下来继续思考一个问题,如果这个Map中的Value可能有这几种类型:String、Integer、Double,我们需要对不同类型分别做不同的处理,是不是处理结构要这样写: if (data.get("key") in...

面对这样的if语句,你是不是很难受呢? if (flag == 1) { log.info("didispace.com: 1");} else if (flag == 2) { log.info("didispace.com: 2");} else if (flag == 3) { log.info("didispace.com: 3");} else if (flag == 4) { log.info("didispace.com: 4");} else { log.info("didispace.com: x");} 是不是想到用switch来改进一下? switch(flag) { case 1: log.info("didispace.com: ...

Java 17推出的新特性Sealed Classes经历了2个Preview版本(JDK 15中的JEP 360、JDK 16中的JEP 397),最终定稿于JDK 17中的JEP 409。Sealed Classes有两种主流翻译:密封类、封闭类。个人喜欢前者多一些,所以在本文中都称为密封类。其实Sealed Classes的其他许多语言中并不是什么新鲜事物,C#、Scala等高级语言中都有类似的名称,但意义和作用各不相同。下面就来一起认识一下Java 17中的Sealed Classes。 密封类的作用在面向对象语言中,我们可以通过继承(extend)来实现类的能力复用、扩展与增强。但有的时候,有些能力我们不希望被继承了去做一些不可预知的扩展。所以,我们需要对继承关系有一些限制的控制手段。而密封类的作用就是限制类的继承。 已有的限制手段对于继承能力的控制,Java很早就已经有一...

instanceof这个关键词,主要用来判断某个对象是不是某个类的实例。 比如,有时候我们要处理一个类似这样的数据集: Map<String, Object> data = new HashMap<>();data.put("key1", "aaa");data.put("key2", 111); 这个Map中的Value值因为可能是不同的对象,所以定义的是Object。这个时候,当我们get出来的时候,就需要去判断和转换之后再去处理。 比如,我们取出key1的value,然后截取一段字符串的操作,就需要这样写: Object value =data.get("key1");if (value instanceof String) { String s = (String) value; System.out.println(s.substri...

假设有这样一个场景,我们需要做一个工具。用来自动生成项目文档,文档可以通过浏览器查看,所以最后产出物肯定是一堆html文件。为了让这些html文件更容易读,良好的格式肯定要保持,该换行的换行、该缩进的缩进。 那么,在组织最后内容的时候,你可能就会这样子来写: String html = "<html>\n" + "<body>\n"+ " <h1>Java 15 新特性:文本块 | 程序猿DD</h1>\n"+ " <p>didispace.com</p>\n"+ "</body>\n"+ "</html>\n"; 当然,也许你也会改进一下,用StringBuilder或者StringBuffer来优化,但不论用什么来写,都逃不了一些要转义的内容...

近日,New Relic发布了最新的2022 Java生态系统报告,这份报告可以帮助我们深入的了解Java体系的最新使用情况,下面就一起来看看2022年,Java发展的怎么样了,还是Java 8 YYDS吗? Java 11成为新的标准在2020年的时候,Java 11已经推出了1年多,但当时Java 8的占有率高达84.48%。2年过去了,Java 11上生产的比例第一次超过Java 8,占有率已经达到了48.44%。曾今的霸主Java 8几乎跌掉了一半,以46.45%占据第二。 而大势所趋的、整个Java生态都在拥抱的Java 17在排行榜上还是处于比较低的位置。这个其实还是意料之中的,因为生态的支持还需要一定时间的演进,比如Spring这个Java生态的大基座,对于Java 17的重要支持还要等到今年年底的Spring Boot 3发布(对这部分感兴趣的小伙伴记得关注我,公...

在这次的Java 18中,新增了一个@snipppet标签,主要用于JavaDoc中需要放示例代码的场景。其实在Java 18之前,已经有一个@code标签,可以用于在JavaDoc中编写小段的代码内容,比如在之前介绍Simple Web Server视频中,提到的这段样例代码,就是用@code标签来写的: * <p> Example of a simple file server:* <pre>{@code* var addr = new InetSocketAddress(8080);* var server = SimpleFileServer.createFileServer(addr, Path.of("/some/path"), OutputLevel.INFO);* server.start();* }<...

本期视频:https://www.bilibili.com/video/BV1YY4y1a7vG 在Java 18中,将UTF-8指定为标准Java API的默认字符集。有了这一更改,依赖于默认字符集的API将在所有实现、操作系统、区域设置和配置中保持一致。 做这一更改的主要目标: 当Java程序的代码依赖于默认字符集时,使其更具可预测性和可移植性。 阐明标准Java API在哪里使用默认字符集。 在整个标准Java API中对UTF-8进行标准化,但控制台I/O除外。 需要注意的是,这一更改的目标并不是定义新的标准Java API或受支持的JDK API,尽管这项工作可能会发现新的便利方法可能会使现有的API更易于使用,这一更改并不是要弃用或删除依赖默认字符集的标准Java API。 动机用于读写文件和处理文本的标准Java API允许将字符集作为参数传递。字符集控制Java编...

昨天分享了Java 18 新特性:简单Web服务器的jwebserver命令行功能。今天换一种方式,使用Java代码来实现一个静态资源服务器。 详细步骤我录了个视频放到B站了,感兴趣的小伙伴可以点击查看Java 18 新特性:Simple Web Server(2) 代码比较简单,直接贴出来了: public class Main { public static void main(String[] args) { System.out.println("Hello world!"); var addr = new InetSocketAddress(9000); var server = SimpleFileServer.createFileServer( addr, Path.of(...