编程开源技术交流,分享技术与知识

网站首页 > 开源技术 正文

惊了,JDK都到23了,据说还有99%Java程序员都不会用optional?

wxchong 2024-09-28 01:37:32 开源技术 99 ℃ 0 评论

在 Java 中,Optional是从 Java 8 开始引入的一个类,用于解决空指针异常的问题。它提供了一种更安全、更优雅的方式来处理可能为空的值。以下是关于Optional的用法介绍以及其优点:

创建 Optional 对象

  1. ofNullable(T value)可以传入一个可能为 null 的值来创建Optional对象。如果传入的值不为 null,则返回一个包含该值的Optional对象;如果传入的值为 null,则返回一个空的Optional对象。例如:
     // 创建一个可能为 null 的字符串的 Optional 对象
     Optional<String> optionalStr = Optional.ofNullable(null);
     // 创建一个值为 10 的整数的 Optional 对象
     Optional<Integer> optionalInt = Optional.ofNullable(10);
  1. of(T value)传入一个非 null 的值来创建Optional对象。如果传入的值为 null,则会抛出NullPointerException异常。例如:
     // 创建一个值为 "Hello" 的字符串的 Optional 对象
     Optional<String> optionalStr = Optional.of("Hello");

判断 Optional 对象是否包含值

  1. isPresent()用于检查Optional对象是否包含非 null 的值。如果包含值,则返回true;否则,返回false。例如:
     Optional<String> optionalStr = Optional.ofNullable("Hello");
     // 判断 Optional 对象是否包含值,如果包含则打印相应信息
     if (optionalStr.isPresent()) {
         System.out.println("Optional contains a value.");
     } else {
         System.out.println("Optional is empty.");
     }
  1. isEmpty()从 Java 11 开始引入,用于检查Optional对象是否为空。如果为空,则返回true;否则,返回false。例如:
     Optional<String> optionalStr = Optional.ofNullable(null);
     // 判断 Optional 对象是否为空,如果为空则打印相应信息
     if (optionalStr.isEmpty()) {
         System.out.println("Optional is empty.");
     } else {
         System.out.println("Optional contains a value.");
     }

获取 Optional 对象中的值

  1. get()如果Optional对象包含非 null 的值,则返回该值;如果Optional对象为空,则会抛出NoSuchElementException异常。例如:
     Optional<String> optionalStr = Optional.ofNullable("Hello");
     // 获取 Optional 对象中的值并打印
     String str = optionalStr.get();
     System.out.println(str);
  1. orElse(T other)如果Optional对象包含非 null 的值,则返回该值;如果Optional对象为空,则返回指定的默认值。例如:
     Optional<String> optionalStr = Optional.ofNullable(null);
     // 如果 Optional 对象为空,则返回 "Default value"
     String str = optionalStr.orElse("Default value");
     System.out.println(str);
  1. orElseGet(Supplier<? extends T> other)如果Optional对象包含非 null 的值,则返回该值;如果Optional对象为空,则通过调用指定的Supplier函数来获取默认值。例如:
     Optional<String> optionalStr = Optional.ofNullable(null);
     // 如果 Optional 对象为空,则通过调用 lambda 表达式生成默认值
     String str = optionalStr.orElseGet(() -> "Generated default value");
     System.out.println(str);
  1. orElseThrow(Supplier<? extends X> exceptionSupplier)如果Optional对象包含非 null 的值,则返回该值;如果Optional对象为空,则通过调用指定的Supplier函数来抛出异常。例如:
     Optional<String> optionalStr = Optional.ofNullable(null);
     try {
         // 如果 Optional 对象为空,则通过调用 lambda 表达式抛出异常
         String str = optionalStr.orElseThrow(() -> new IllegalArgumentException("Value is null."));
     } catch (IllegalArgumentException e) {
         System.out.println(e.getMessage());
     }

对 Optional 对象中的值进行操作

  1. ifPresent(Consumer<? super T> consumer)如果Optional对象包含非 null 的值,则调用指定的Consumer函数来对该值进行操作。例如:
     Optional<String> optionalStr = Optional.ofNullable("Hello");
     // 如果 Optional 对象包含值,则打印该值
     optionalStr.ifPresent(str -> System.out.println("Value: " + str));
  1. map(Function<? super T,? extends U> mapper)如果Optional对象包含非 null 的值,则应用指定的函数对该值进行转换,并返回一个新的Optional对象,包含转换后的结果。如果原始的Optional对象为空,则返回一个空的Optional对象。例如:
     Optional<String> optionalStr = Optional.ofNullable("Hello");
     // 对 Optional 对象中的值进行转换,将字符串转换为其长度的 Optional 对象
     Optional<Integer> lengthOptional = optionalStr.map(String::length);
     if (lengthOptional.isPresent()) {
         System.out.println("Length: " + lengthOptional.get());
     }
  1. flatMap(Function<? super T,Optional<? extends U>> mapper)与map方法类似,但接受一个函数,该函数返回一个Optional对象。如果原始的Optional对象包含非 null 的值,并且函数返回的Optional对象也包含值,则返回这个包含转换后结果的Optional对象;否则,返回一个空的Optional对象。例如:
     Optional<String> optionalStr = Optional.ofNullable("Hello");
     // 对 Optional 对象中的值进行转换,将字符串转换为其长度的 Optional 对象
     Optional<Integer> lengthOptional = optionalStr.flatMap(str -> Optional.of(str.length()));
     if (lengthOptional.isPresent()) {
         System.out.println("Length: " + lengthOptional.get());
     }

Optional 的其他常用方法

  1. filter(Predicate<? super T> predicate)如果Optional对象包含的值满足指定的谓词条件,则返回该Optional对象;否则,返回一个空的Optional对象。例如:
     Optional<Integer> optionalInt = Optional.ofNullable(10);
     // 对 Optional 对象中的值进行过滤,只保留大于 5 的值
     Optional<Integer> filteredOptional = optionalInt.filter(i -> i > 5);
     if (filteredOptional.isPresent()) {
         System.out.println("Filtered value: " + filteredOptional.get());
     }
  1. stream()如果Optional对象包含值,则返回一个包含该值的单元素流;如果Optional对象为空,则返回一个空流。例如:
     Optional<String> optionalStr = Optional.ofNullable("Hello");
     // 将 Optional 对象中的值转换为流进行操作
     optionalStr.stream().forEach(System.out::println);

Optional 如何处理空指针异常

Optional通过以下方式来处理空指针异常:

  1. 避免直接访问可能为 null 的值传统的方式中,如果直接访问一个可能为 null 的变量,很容易引发空指针异常。而使用Optional,可以避免直接访问可能为 null 的值,而是通过Optional对象提供的方法来安全地获取值。例如,假设我们有一个方法返回一个可能为 null 的字符串:
     public String getNullableString() {
         return null;
     }
  • 如果直接访问这个返回值,可能会引发空指针异常:
     String str = getNullableString();
     System.out.println(str.length()); // 可能抛出空指针异常
  • 但是,如果使用Optional来包装这个返回值,就可以安全地处理可能为 null 的情况:
     Optional<String> optionalStr = Optional.ofNullable(getNullableString());
     optionalStr.ifPresent(str -> System.out.println(str.length())); // 如果字符串不为 null,则打印长度,否则不执行任何操作
  1. 提供明确的空值处理方式Optional提供了多种方法来处理空值情况,例如orElse、orElseGet和orElseThrow等。这些方法可以让开发者明确地指定在值为空时应该采取的行动,而不是在运行时意外地遇到空指针异常。例如,如果我们希望在值为空时返回一个默认值,可以使用orElse方法:
     Optional<String> optionalStr = Optional.ofNullable(getNullableString());
     String str = optionalStr.orElse("Default value");
     System.out.println(str);
  • 如果我们希望在值为空时通过一个函数生成默认值,可以使用orElseGet方法:
     Optional<String> optionalStr = Optional.ofNullable(getNullableString());
     String str = optionalStr.orElseGet(() -> "Generated default value");
     System.out.println(str);
  • 如果我们希望在值为空时抛出一个异常,可以使用orElseThrow方法:
     Optional<String> optionalStr = Optional.ofNullable(getNullableString());
     try {
         String str = optionalStr.orElseThrow(() -> new IllegalArgumentException("Value is null."));
     } catch (IllegalArgumentException e) {
         System.out.println(e.getMessage());
     }

ifPresentOrElse 方法

ifPresentOrElse方法是在 Java 9 中引入的,它允许在Optional对象包含值时执行一个操作,在值为空时执行另一个操作。

例如:

Optional<String> optionalStr = Optional.ofNullable("Hello");
// 如果 Optional 对象包含值,则打印该值,否则打印 "Optional is empty."
optionalStr.ifPresentOrElse(str -> System.out.println("Value: " + str), () -> System.out.println("Optional is empty."));

optionalStr = Optional.ofNullable(null);
// 如果 Optional 对象包含值,则打印该值,否则打印 "Optional is empty."
optionalStr.ifPresentOrElse(str -> System.out.println("Value: " + str), () -> System.out.println("Optional is empty."));

这个方法提供了一种更简洁的方式来处理Optional对象的空值情况,相比于使用ifPresent和orElse方法的组合更加直观。

Optional 的优点

  1. 明确的空值处理Optional强制开发者显式地处理可能为空的值,使得代码更加清晰地表达了对空值的预期和处理方式。这有助于减少由于意外的空指针异常而导致的错误,提高代码的可靠性。例如,使用orElse、orElseGet和orElseThrow等方法,开发者可以明确地指定在值为空时应该采取的行动,而不是依赖于隐式的空值处理。
  2. 安全的方法调用链Optional的方法可以安全地链接在一起,形成一个方法调用链。如果任何一个环节的Optional对象为空,整个调用链会立即停止执行,而不会引发空指针异常。例如,可以使用map和flatMap方法对Optional对象中的值进行转换和操作,而不用担心空指针异常的问题。
  3. 更好的代码可读性使用Optional可以使代码更加清晰地表达其意图,提高代码的可读性。其他开发者在阅读代码时,可以更容易地理解哪些值可能为空,以及如何处理这些空值情况。例如,当看到一个方法返回一个Optional对象时,开发者可以立即知道这个方法可能返回一个空值,并且需要进行适当的处理。
  4. 鼓励良好的编程习惯Optional鼓励开发者在编写代码时更加谨慎地处理空值情况,避免依赖于不可靠的假设。这有助于提高代码的质量和可维护性。例如,开发者在调用可能返回空值的方法时,会更加倾向于使用Optional来包装返回值,并进行适当的空值处理,而不是直接假设返回值不为空。

Optional提供了一种更安全、更优雅的方式来处理可能为空的值,避免了空指针异常的问题。它具有明确的空值处理、安全的方法调用链、更好的代码可读性和鼓励良好的编程习惯等优点。通过合理地使用Optional的各种方法,可以使代码更加健壮和易于维护。

Tags:

本文暂时没有评论,来添加一个吧(●'◡'●)

欢迎 发表评论:

最近发表
标签列表