详细分析Java中的Optional类以及应用场景

这篇具有很好参考价值的文章主要介绍了详细分析Java中的Optional类以及应用场景。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

前言

在实战中学习,灵活运用每个操作类,具体如下:
java optional,Java,java,Optional,Null

1. 基本知识

源码主要如下:

java optional,Java,java,Optional,Null

大致含义如下:

这是一个容器对象,可能包含或不包含非空值。如果有值存在,isPresent() 方法将返回 true,而 get() 方法将返回该值。
提供了一些依赖于包含值的存在或缺失的其他方法,例如 orElse()(如果值不存在,则返回默认值)和 ifPresent()(如果存在值,则执行一段代码块)。
这是一个基于值的类;在 Optional 实例上使用依赖于身份的操作(包括引用相等性(==)、身份哈希码或同步)可能会产生不可预测的结果,应该避免使用。
自 Java 1.8 起。

用开发的角度来讲,该类是 Java 8 中引入的一个用于处理可能为 null 的值的容器类。

它的设计目的是为了解决在代码中频繁出现的空指针异常问题。

不过这个类有好有坏,适当使用即可,其缺点就是造成代码过于冗长(= - = )
最主要是引入额外的对象开销。

了解基本的特性以及薄弱项之后,站在后端的角度灵活运用其API以及常用方法

2. 常用API

创建Optional的对下你个有以下三种方式:

  1. Optional.of(value): 创建一个包含非空值的 Optional 对象
    如果传递的值为 null,会抛出 NullPointerException
Optional<String> nonNullOptional = Optional.of("Hello, World!");
  1. Optional.ofNullable(value): 创建一个 Optional 对象,如果传递的值为 null,仍然会创建一个空的 Optional 对象
Optional<String> optional = Optional.ofNullable(someNullableValue);
  1. Optional.empty(): 创建一个空的 Optional 对象
Optional<String> emptyOptional = Optional.empty();

👇

常用的操作方法如下:

  1. isPresent(): 判断 Optional 对象是否包含非空值
if (optional.isPresent()) {
    // 做一些操作
}
  1. ifPresent(Consumer<? super T> consumer): 如果 Optional 对象包含非空值,则执行传入的操作
optional.ifPresent(value -> System.out.println("Value: " + value));
  1. orElse(T other): 如果 Optional 对象包含非空值,则返回该值;否则返回传入的默认值
String result = optional.orElse("Default Value");
  1. orElseGet(Supplier<? extends T> other): 类似于 orElse,但是默认值是由传入的 Supplier 提供的
String result = optional.orElseGet(() -> generateDefaultValue());
  1. orElseThrow(Supplier<? extends X> exceptionSupplier): 如果 Optional 对象为空,则抛出由传入的 Supplier 提供的异常
String result = optional.orElseThrow(() -> new NoSuchElementException("Value not present"));

👇👇

链式操作:Optional 提供了一些方法,在不解包 Optional 的情况下进行链式操作(这有助于避免空指针异常,并使代码更加清晰)

比如如下例子: nullableValue 不为 null,则将其转换为大写;否则,返回默认值 "Default"

String result = Optional.ofNullable(nullableValue)
                        .map(String::toUpperCase)
                        .orElse("Default");

3. Demo

通过示例的Demo操作上述的方法

import java.util.Optional;
public class Demo {
    public static void main(String[] args) {
        // 示例1: 创建包含非空值的 Optional 对象
        Optional<String> nonNullOptional = Optional.of("码农, 研究僧!");

        // 示例2: 创建可能为空值的 Optional 对象
        String nullableValue = null;
        Optional<String> optional = Optional.ofNullable(nullableValue);

        // 示例3: 使用 isPresent 判断是否包含非空值
        if (nonNullOptional.isPresent()) {
            System.out.println("Non-null value: " + nonNullOptional.get()); // 此处有空值,为true,输出 Non-null value: 码农, 研究僧!
        } else {
            System.out.println("Non-null value is not present.");
        }

        // 示例4: 使用 ifPresent 执行操作,没有空值才会执行!
        nonNullOptional = Optional.of("码农, 研究僧!");
        nonNullOptional.ifPresent(value -> System.out.println("Value from optional: " + value)); // 没有空值,就会输出 Value from optional: 码农, 研究僧!

        // 示例5: 使用 orElse 获取值或默认值
        String result = optional.orElse("Default Value");
        System.out.println("Result from orElse: " + result); // 输出默认值 Result from orElse: Default Value

        // 示例6: 使用 orElseGet 获取值或由 Supplier 提供的默认值
        String resultFromSupplier = optional.orElseGet(() -> generateDefaultValue());
        System.out.println("Result from orElseGet: " + resultFromSupplier); // 输出Supplier提供的默认值

        // 示例7: 使用 orElseThrow 抛出异常
        try {
            String resultOrThrow = optional.orElseThrow(() -> new RuntimeException("Value not present"));
            System.out.println("Result from orElseThrow: " + resultOrThrow);
        } catch (RuntimeException e) {
            System.out.println("Exception caught: " + e.getMessage()); // 此处对象为空,所以输出了这语句 Exception caught: Value not present
        }

        // 示例8: 链式操作
        String chainedResult = Optional.ofNullable(nullableValue)
                .map(String::toUpperCase)
                .orElse("Default Chain");
        System.out.println("Chained result: " + chainedResult); // 输出默认值:Chained result: Default Chain
    }

    private static String generateDefaultValue() {
        return "Default Value from Supplier";
    }
}

截图如下:

java optional,Java,java,Optional,Null

4. 应用场景

应用场景一般用于方法返回值或者集合操作中

场景一

当方法的返回值可能为 null 时,使用 Optional 可以清晰地表达这一点,并要求调用者明确处理可能的空值情况

public Optional<String> findUserById(String userId) {
    // 在数据库中查找用户,可能返回 null
    // 使用 Optional 封装返回值
    // 返回 Optional.ofNullable(user) 或 Optional.empty()
}

场景二

在对集合进行操作时,某些操作可能返回 null(例如在查找元素时)。
使用 Optional 可以更好地处理这些情况,而不是直接返回 null

public Optional<String> findFirstEvenNumber(List<Integer> numbers) {
    // 在集合中查找第一个偶数,可能返回 null
    // 使用 Optional 封装返回值
    // 返回 Optional.ofNullable(evenNumber) 或 Optional.empty()
}

场景三

在防御性编程中,通过使用 Optional 可以更好地处理可能为 null 的值,避免空指针异常

public Optional<String> getUserName(User user) {
    // 获取用户的名称,用户对象可能为 null
    // 使用 Optional 封装返回值
    // 返回 Optional.ofNullable(userName) 或 Optional.empty()
}

场景四:

设计自己的 API 时,如果某个方法的返回值可能为空,使用 Optional 可以使 API 更加健壮和易于理解。

public Optional<Product> findProductById(String productId) {
    // 根据产品ID查找产品,产品可能不存在
    // 使用 Optional 封装返回值
    // 返回 Optional.ofNullable(product) 或 Optional.empty()
}

场景五:

当处理多层嵌套的对象时,使用 Optional 可以避免深层次的 null 检查,使代码更加简洁

public Optional<String> getAddressCity(User user) {
    // 获取用户地址的城市,用户、地址对象可能为 null
    // 使用 Optional 封装返回值
    // 返回 Optional.ofNullable(city) 或 Optional.empty()
}

虽然看起来很新鲜, 可以提高代码的健壮性,但需要注意不要滥用

主要如下,还是重点讲讲:

  1. 造成代码冗长,本来一个null值就可以解决
  2. 引入多一个对象多一个开销,如果本身追求速度,就不用刻意这样
  3. 再者如果嵌套多层对象还这么使用,开发的可能感觉很牛,看的同事可能觉得臭臭臭臭臭

在某些情况下,直接使用 null 可能是更简单和清晰的选择
使用 Optional 主要是为了增加对空值的明确处理,使代码更加防御性和易读文章来源地址https://www.toymoban.com/news/detail-860017.html

到了这里,关于详细分析Java中的Optional类以及应用场景的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 详细分析Java中的@JsonFormat注解和@DateTimeFormat注解

    下文中涉及MybatisPlus的逻辑删除的知识,可看我之前这篇文章:详细讲解MybatisPlus实现逻辑删除 对应的Navicat设置数据库最新时间可看我这篇文章:Navicat 设置时间默认值(当前最新时间) 为了使 @JsonFormat 生效,项目必须引入 Jackson 库的相关依赖: (如果是springboot项目,可不

    2024年01月23日
    浏览(41)
  • 【Java中的Thread线程的简单方法介绍和使用详细分析】

    提示:若对Thread没有基本的了解,可以先阅读以下文章,同时部分的方法已经在如下两篇文章中介绍过了,本文不再重复介绍!! 【Java中Tread和Runnable创建新的线程的使用方法】 【Java中的Thread线程的七种属性的使用和分析】 提示:以下是本篇文章正文内容,下面案例可供参

    2024年02月15日
    浏览(41)
  • 安卓之DocumentsProvider应用场景以及优劣分析

    本文深入探讨了安卓 DocumentsProvider 的应用场景,分析了其优势与不足,并提供了简单的代码实现。 DocumentsProvider 是安卓系统中用于文件存储与访问的关键组件,为应用开发者提供了强大的文件管理能力。 DocumentsProvider 是安卓系统中的一个组件,允许应用以统一的方式访问和

    2024年02月04日
    浏览(41)
  • 全面理解java中的构造方法以及this关键字的用法(超详细)

    Hello,各位铁汁们!我是小🐟儿哈!今天我又来更新我的Java基础学习博客了。 本篇主要内容概述: 1、🍚如何用构造方法初始化对象 2、🍚为啥要有this这个 3、🍚this.属性名访问成员变量、成员方法 4、🍚this.方法名 || this.()的用法 目录 初识构造方法  构造方法的使

    2023年04月09日
    浏览(62)
  • Java反射机制,动态代理,hook以及在Retrofit源码中的应用

    1.反射的基础知识: Java的反射机制是指在程序的运行状态中,可以构造任意一个类的对象,可以了解任意一个对象所属的类,可以了解任意一个类的成员变量和方法,可以调用任意一个对象的属性和方法。这种动态获取程序信息以及动态调用对象的功能称为Java语言的反射机

    2024年02月13日
    浏览(44)
  • 详细分析Java中的list.foreach()和list.stream().foreach()

    典故来源于项目中使用了两种方式的foreach,后面尝试体验下有何区别! 先看代码示例: 使用List的forEach : 使用Stream API的forEach : 两者输出结果都为如下: 既然两个都输出差不多的结果,但两者还是稍微有些小区别,具体看下文! forEach() 是List接口的一部分,用于对列表中

    2024年04月25日
    浏览(45)
  • 安卓之缓存的应用场景以及各种技术优劣分析

            本文主要探讨了安卓开发中的缓存技术及其应用场景,通过分析几种常见的缓存技术,包括内存缓存、磁盘缓存和网络缓存,阐述了它们的优点和缺点。此外,本文还提供了相应的代码示例,以帮助读者更好地理解这些缓存技术的实现方式。         在当今的

    2024年02月01日
    浏览(41)
  • 安卓之文本转视频的应用场景以及技术优劣分析

            随着科技的进步,文本与视频这两种信息传递形式之间的界限正在逐渐模糊。特别是在安卓平台上,将文本转换为视频的功能已经成为一种重要的应用场景。本文将深入探讨这一功能的应用场景、涉及的关键技术,以及其优劣分析。 1.1、 内容创作与分享      

    2024年01月22日
    浏览(65)
  • 怎么通过Fiddler对APP进行抓包?以及高级应用场景分析

    目录 前言 简单说下Fiddler的抓包原理: 使用fiddler代理远程捕获APP请求 Fiddler高级应用场景介绍 1、url地址重写  fiddler抓包详细教程:全网抓包天花板教程,B站讲的最详细的Fiddler/Charles抓包教学视频。2小时包你学会_哔哩哔哩_bilibilihttps://www.bilibili.com/video/BV1tv4y1575S/?spm_id_from

    2024年02月08日
    浏览(60)
  • JAVA深化篇_29—— 线程使用之线程联合以及Thread类中的其他常用方法【附有详细说明及代码案例】

    线程联合 当前线程邀请调用方法的线程优先执行,在调用方法的线程执行结束之前,当前线程不能再次执行。线程A在运行期间,可以调用线程B的join()方法,让线程B和线程A联合。这样,线程A就必须等待线程B执行完毕后,才能继续执行。 join方法的使用 join()方法就是指调用该

    2024年02月05日
    浏览(48)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包