详解Java8新特性如何防止空指针异常

 更新时间:2023年08月09日 11:16:32   作者:蜡笔小新丶henry  
要说 Java 编程中哪个异常是你印象最深刻的,那 NullPointerException 空指针可以说是臭名昭著的,不要说初级程序员会碰到, 即使是中级,专家级程序员稍不留神,就会掉入这个坑里,本文就和大家聊聊Java8新特性如何防止空指针异常

Java8 新特性如何防止空指针异常

要说 Java 编程中哪个异常是你印象最深刻的,那 NullPointerException 空指针可以说是臭名昭著的。不要说初级程序员会碰到, 即使是中级,专家级程序员稍不留神,就会掉入这个坑里。

Null引用的发明者 Tony Hoare 曾在 2009 年作出道歉声明,声明中表示,到目前为止,空指针异常大约给企业已造成数十亿美元的损失。

下面是 Tony Hoare 的原话:

我将 Null 引用的设计称为是一个数十亿美元的错误。1965 那年,我正在用面向对象语言(ALGOL W) 设计首个功能全面的系统。当时我的考量是,确保所有被使用的引用都是安全的,编译器会自动进行检查。但是,我没有抵住诱惑,加入了 Null 引用,仅仅是为了实现起来省事。这之后,它导致了数不清的 bug、错误和系统崩溃,也为企业导致了不可估量的损失。

事已至此,我们必须学会面对它。So, 我们要如何防止空指针异常呢?

唯一的办法就是对可能为 Null 的对象添加检查。但是 Null 检查是繁琐且痛苦的。所以一些比较新的语言为了处理 Null 检查,特意添加了特殊的语法,如空合并运算符。

在 Groovy 或 Kotlin 这样的语言中也被称为 Elvis运算符。

不幸的是,在老版本的 Java 中并没有提供这样的语法糖。Java8 中在这方面做了改进。所以,这篇文章就特意来介绍一下如何在 Java8 中利用新特性来编写防止 NullPointerException的发生。

Java8 中如何加强对 Null 对象的检查?

接下来,我们细说一下如何通过 Optional 类来对对象做空校验:

在业务系统中,对象中嵌套对象是经常发生的场景,如下示例代码:

 // 最外层对象
 class Outer {
     Nested nested;
     Nested getNested() {
         return nested;
     }
 }
 // 第二层对象
 class Nested {
     Inner inner;
     Inner getInner() {
         return inner;
     }
 }
 // 最底层对象
 class Inner {
     String foo;
     String getFoo() {
         return foo;
     }
 }

业务中,假设我们需要获取 Outer 对象对底层的 Inner 中的 foo 属性,我们必须写一堆的非空校验,来防止发生 NullPointerException

 // 繁琐的代码
 Outer outer = new Outer();
 if (outer != null && outer.nested != null && outer.nested.inner != null) {
     System.out.println(outer.nested.inner.foo);
 }

通过 Optional

在 Java8 中,我们有更优雅的解决方式,那就是使用 Optional 是说,我们可以在一行代码中,进行流水式的 map 操作。而 map 方法内部会自动进行空校验

 Optional.of(new Outer())
     .map(Outer::getNested)
     .map(Nested::getInner)
     .map(Inner::getFoo
     .ifPresent(System.out::println); // 如果不为空,最终输出 foo 的值

通过 suppiler 函数自定义增强 API

上面这种方式个人感觉还是有点啰嗦,我们可以利用 suppiler 函数来出一个终极解决方案:

 public static <T> Optional<T> resolve(Supplier<T> resolver) {
     try {
         T result = resolver.get();
         return Optional.ofNullable(result);
     }
     catch (NullPointerException e) {
         // 可能会抛出空指针异常,直接返回一个空的 Optional 对象
         return Optional.empty();
     }
 }

利用上面的 resolve 方法来重构上述的非空校验代码段:

 Outer obj = new Outer();
 // 直接调用 resolve 方法,内部做空指针的处理
 resolve(() -> obj.getNested().getInner().getFoo());
     .ifPresent(System.out::println); // 如果不为空,最终输出 foo 的值

最后

你需要知道的是,上面这两个解决方案并没传统的 null 检查性能那么高效。但在绝大部分业务场景下,舍弃那么一丢丢的性能来方便编码,是完全可取, 除非是那种对性能有严格要求的场景,我们才不建议使用。

到此这篇关于详解Java8新特性如何防止空指针异常的文章就介绍到这了,更多相关Java8空指针异常内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • java查找图中两点之间所有路径

    java查找图中两点之间所有路径

    这篇文章主要为大家详细介绍了java查找图中两点之间所有路径,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2019-01-01
  • Java开发第一个RESTful接口完全攻略

    Java开发第一个RESTful接口完全攻略

    restful接口是一种基于http协议的网络应用程序接口设计风格,它强调资源的表现形式和状态转移,下面这篇文章主要介绍了Java开发RESTful接口的相关资料,文中通过代码介绍的非常详细,需要的朋友可以参考下
    2026-01-01
  • SpringBoot如何升级到3.0

    SpringBoot如何升级到3.0

    这篇文章主要介绍了SpringBoot如何升级到3.0问题,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-09-09
  • Java解析zip文件,并识别压缩包里面的文件转换成可操作的IO流方式

    Java解析zip文件,并识别压缩包里面的文件转换成可操作的IO流方式

    这篇文章主要介绍了Java解析zip文件,并识别压缩包里面的文件转换成可操作的IO流方式,具有很好的参考价值,希望对大家有所帮助,如有错误或未考虑完全的地方,望不吝赐教
    2024-08-08
  • 基于HTML5+js+Java实现单文件文件上传到服务器功能

    基于HTML5+js+Java实现单文件文件上传到服务器功能

    应公司要求,在HTML5页面上实现上传文件到服务器功能,对于我这样的菜鸟,真是把我难住了,最后还是请教大神搞定的,下面小编把例子分享到脚本之家平台,供大家参考
    2017-08-08
  • Spring中的@PostConstruct注解使用方法解析

    Spring中的@PostConstruct注解使用方法解析

    这篇文章主要介绍了Spring中的@PostConstruct注解使用方法解析,@PostConstruct注解是用来处理在@Autowired注入属性后init()方法之前,对一些零散的属性进行赋值的注解,需要的朋友可以参考下
    2023-11-11
  • Java lock同步锁使用实例解析

    Java lock同步锁使用实例解析

    这篇文章主要介绍了Java lock同步锁使用实例解析,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友可以参考下
    2020-01-01
  • SpringMVC配置与使用详细介绍

    SpringMVC配置与使用详细介绍

    Spring MVC是一个基于Java的实现了MVC设计模式的请求驱动类型的轻量级Web框架,通过把Model,View,Controller分离,将web层进行职责解耦,把复杂的web应用分成逻辑清晰的几部分,简化开发,减少出错,方便组内配合
    2022-07-07
  • resty mail的简单发送邮件方法

    resty mail的简单发送邮件方法

    这篇文章主要为大家介绍了简单的resty mail发送邮件方法示例,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步早日升职加薪
    2022-03-03
  • MybatisPlus实现数据拦截的使用示例

    MybatisPlus实现数据拦截的使用示例

    在MyBatis-Plus中,可以通过自定义拦截器来实现对SQL语句的拦截和修改,本文就来介绍一下如何使用,具有一定的参考价值,感兴趣的可以了解一下
    2023-10-10

最新评论