Optional类详解及使用方法示例

Optional类是java8中引入的一个非常有用的类,它可以用来解决空指针异常带来的不便。这个类可以将对象包装为一个Optional对象,如果该对象为空,则可以使用一些默认值或者执行一些默认操作。Optional 是 Java 实现函数式编程的强劲一步,并且帮助在范式中实现。

Java8的Optional类提供了丰富的 API 方法,这里按照其功能分类介绍。

一、创建 Optional 对象的方法

empty()

  empty()方法用于创建一个空的Optional对象。该方法返回的Optional对象中没有包含任何值,因此它永远不会抛出 NullPointerException 异常。

下面是使用empty()方法创建一个空的 Optional 对象的示例:

Optional emptyOptional = Optional.empty();

        上述代码中,我们使用了Optional.empty()方法来创建一个空的 Optional 对象,并将该对象赋值给了一个名为 emptyOptional 的变量。

        当需要使用 Optional 类型的变量,但还不知道它的值应该是什么时,可以使用Optional.empty()方法来初始化该变量,以表示该变量当前还没有被赋值。

        在对 Optional 对象进行操作时,必须先判断 Optional 对象中是否实际包含值,否则可能会抛出 NoSuchElementException 异常。使用isPresent()方法可以判断 Optional 对象中是否包含值,如果返回 true,则说明 Optional 对象中包含值,否则说明 Optional 对象为空。

Optional emptyOptional = Optional.empty();

if (emptyOptional.isPresent()) {
    String value = emptyOptional.get();
} else {
    System.out.println("Optional对象为空");
}

         上述代码中,我们对创建的空的 Optional 对象进行了判断,由于 Optional 对象中并没有包含任何值,因此输出的结果是"Optional对象为空"。

of(T value)

  of(T value)方法用于创建一个包含指定值的 Optional 对象。该方法接收一个非 null 值作为参数,如果传入的参数为 null,则会抛出 NullPointerException 异常。

        下面是使用of()方法创建一个包含指定值的 Optional 对象的示例:

String str = "Hello World";
Optional optionalStr = Optional.of(str);

         上述代码中,我们使用Optional.of()方法将一个非 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。

创建包含指定值的 Optional 对象后,可以使用get()方法获取 Optional 对象中的实际值。

String str = "Hello World";
Optional optionalStr = Optional.of(str);

String value = optionalStr.get();
System.out.println(value); // 输出"Hello World"

        上述代码中,我们首先使用Optional.of()方法创建一个包含字符串类型的值的 Optional 对象,然后使用get()方法获取 Optional 对象中的实际值,并将其输出到控制台上。

需要注意的是,传入of()方法的参数必须是非 null 的值,否则会抛出 NullPointerException 异常。

String str = null;
Optional optionalStr = Optional.of(str); // 抛出 NullPointerException 异常

         上述代码中,我们将一个 null 值传入Optional.of()方法,由于传入的参数为 null,因此会抛出 NullPointerException 异常。

ofNullable(T value)

   ofNullable(T value)方法用于创建一个包含指定值的 Optional 对象。该方法接收一个可能为 null 的值作为参数,如果传入的参数为 null,则返回一个空的 Optional 对象。

下面是使用ofNullable()方法创建一个包含指定值的 Optional 对象的示例:

String str = "Hello World";
Optional optionalStr1 = Optional.ofNullable(str);

String str2 = null;
Optional optionalStr2 = Optional.ofNullable(str2);

        上述代码中,我们使用Optional.ofNullable()方法将一个可能为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr1 的变量。同时,我们也将一个为 null 的字符串类型变量 str2 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr2 的变量。

需要注意的是,使用ofNullable()方法创建 Optional 对象时,传入的参数可以为 null,此时会自动返回一个空的 Optional 对象。

String str = null;
Optional optionalStr = Optional.ofNullable(str);

         上述代码中,我们将一个为 null 的字符串类型变量 str 传入了Optional.ofNullable()方法。由于传入的参数为 null,因此该方法会返回一个空的 Optional 对象,不会抛出 NullPointerException 异常。

在对 Optional 对象进行操作时,必须先判断 Optional 对象是否实际包含值,否则可能会抛出 NoSuchElementException 异常。使用isPresent()方法可以判断 Optional 对象中是否包含值,如果返回 true,则说明 Optional 对象中包含值,否则说明 Optional 对象为空。

String str = "Hello World";
Optional optionalStr = Optional.ofNullable(str);

if (optionalStr.isPresent()) {
    String value = optionalStr.get();
} else {
    System.out.println("Optional对象为空");
}

         上述代码中,我们对创建的 Optional 对象进行了判断,由于 Optional 对象中包含非 null 的值,因此使用get()方法获取 Optional 对象中的实际值,并将其赋值给一个名为 value 的变量。

二、判断 Optional 对象是否包含值的方法

isPresent()

 isPresent()方法用于判断 Optional 对象中是否存在非 null 值。如果 Optional 对象中存在非 null 值,该方法会返回 true;否则返回 false。

下面是使用isPresent()方法判断 Optional 对象是否存在非 null 值的示例:

String str = "Hello World";
Optional optionalStr = Optional.ofNullable(str);

if (optionalStr.isPresent()) {
    String value = optionalStr.get();
} else {
    System.out.println("Optional对象为空");
}

 上述代码中,我们首先使用Optional.ofNullable()方法将一个可能为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。接着,我们使用isPresent()方法判断 Optional 对象中是否存在非 null 值,如果存在,则使用get()方法获取 Optional 对象中的实际值,并将其赋值给一个名为 value 的变量;否则输出“Optional对象为空”。

需要注意的是,在对 Optional 对象进行操作时,必须先判断 Optional 对象中是否存在值,否则可能会抛出 NoSuchElementException 异常。

String str = null;
Optional optionalStr = Optional.ofNullable(str);

String value = optionalStr.get(); // 抛出 NoSuchElementException 异常

 上述代码中,我们使用Optional.ofNullable()方法将一个为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。由于 Optional 对象中并不包含实际值(因为 str 为 null),因此在使用get()方法获取 Optional 对象中的实际值时会抛出 NoSuchElementException 异常。因此,在对 Optional 对象进行操作时,一定要先判断 Optional 对象中是否存在值。

isEmpty()

isEmpty()方法用于判断 Optional 对象是否为空,如果 Optional 对象中包含非 null 值,则返回 false;否则返回 true。

下面是使用isEmpty()方法判断 Optional 对象是否为空的示例:

String str = "Hello World";
Optional optionalStr = Optional.ofNullable(str);

if (optionalStr.isEmpty()) {
    System.out.println("Optional对象为空");
} else {
    String value = optionalStr.get();
    System.out.println("Optional对象的值为:" + value);
}

在上面的示例中,我们首先使用Optional.ofNullable()方法将一个可能为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。接着,我们使用isEmpty()方法判断 Optional 对象是否为空,如果为空,则输出“Optional对象为空”,否则使用get()方法获取 Optional 对象中的实际值,并将其赋值给一个名为 value 的变量,并输出“Optional对象的值为:Hello World”。

需要注意的是,在 JDK 11 中新增的isEmpty()方法与isPresent()方法的作用相反,这里我们演示的是 JDK 11 中的新版本,如果您使用的是旧版本的 JDK,则无法使用isEmpty()方法。

String str = "Hello World";
Optional optionalStr = Optional.ofNullable(str);

if (optionalStr.isPresent()) {
    String value = optionalStr.get();
    System.out.println("Optional对象的值为:" + value);
} else {
    System.out.println("Optional对象为空");
}

 上述代码中,我们使用isPresent()方法判断 Optional 对象中是否存在非 null 值。如果存在,则使用get()方法获取 Optional 对象中的实际值,并将其赋值给一个名为 value 的变量,并输出“Optional对象的值为:Hello World”;否则输出“Optional对象为空”。

三、获取 Optional 对象中的值的方法

get()

get()方法来获取包装在其中的实际值,但是它需要在 Optional 对象中存储一个非 null 的值,否则会抛出 NoSuchElementException 异常。

下面是使用get()方法获取 Optional 对象中的实际值的示例:

String str = "Hello World";
Optional optionalStr = Optional.ofNullable(str);

if (optionalStr.isPresent()) {
    String value = optionalStr.get();
    System.out.println("Optional对象的值为:" + value);
} else {
    System.out.println("Optional对象为空");
}

在上述代码中,我们首先使用Optional.ofNullable()方法将一个可能为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。接着,我们使用isPresent()方法判断 Optional 对象中是否包含非 null 值,如果存在,则使用get()方法获取 Optional 对象中的实际值,并将其赋值给一个名为 value 的变量,并输出“Optional对象的值为:Hello World”;否则输出“Optional对象为空”。

需要注意的是,在 Optional 对象没有值的情况下调用get()方法会抛出 NoSuchElementException 异常,因此在使用get()方法之前必须先判断 Optional 对象中是否存在值。可以使用isPresent()方法来判断 Optional 对象中是否存在值,或者使用orElse()方法设置默认值以避免抛出异常。

String str = null;
Optional optionalStr = Optional.ofNullable(str);

String value = optionalStr.get(); // 抛出 NoSuchElementException 异常

在上述代码中,我们使用Optional.ofNullable()方法将一个为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。由于 Optional 对象中并不包含实际值(因为 str 为 null),因此在调用get()方法时会抛出 NoSuchElementException 异常。 

orElse(T other)

  orElse(T other)方法用于在 Optional 对象不包含非 null 值的情况下提供默认值。

下面是使用orElse(T other)方法设置默认值的示例:

String str = null;
Optional optionalStr = Optional.ofNullable(str);

String value = optionalStr.orElse("默认值");
System.out.println("Optional对象的值为:" + value);

        在上述代码中,我们首先使用Optional.ofNullable()方法将一个为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。接着,我们调用orElse("默认值")方法来设置默认值。由于 optionalStr 中并没有实际值,因此orElse()方法会返回提供的默认值,并将其赋值给 name 变量。最后,输出“Optional对象的值为:默认值”。

        需要注意的是,调用orElse(T other)方法时必须指定一个非 null 的值作为参数,用于在 Optional 对象中不存在实际值时返回。

String str = null;
Optional optionalStr = Optional.ofNullable(str);

String value = optionalStr.orElse(null); // 抛出 NullPointerException 异常

        在上述代码中,我们同样使用Optional.ofNullable()方法将一个为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。接着,我们调用orElse(null)方法来设置默认值。由于传递给orElse()方法的参数为 null,因此在Optional对象中不存在实际值时,调用orElse(null)方法会抛出NullPointerException异常。因此,在调用orElse(T other)方法时必须指定一个非 null 的默认值。

orElseGet(Supplier other)

   orElseGet(Supplier other) 方法与 orElse(T other) 方法类似,都是在 Optional 对象不包含非 null 值的情况下提供默认值。不同的是,orElseGet(Supplier other) 方法需要传递一个 Supplier 对象作为参数,在 Optional 对象不包含非 null 值时,会调用该 Supplier 对象提供的方法来生成默认值。

下面是使用 orElseGet(Supplier other) 方法设置默认值的示例:

String str = null;
Optional optionalStr = Optional.ofNullable(str);

String value = optionalStr.orElseGet(() -> "默认值");
System.out.println("Optional对象的值为:" + value);

        在上述代码中,我们首先使用 Optional.ofNullable() 方法将一个为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。接着,我们调用 orElseGet(() -> "默认值") 方法来设置默认值。由于 optionalStr 中并没有实际值,因此 orElseGet() 方法会调用传递的 Supplier 对象来生成默认值,并将其赋值给 value 变量。因为我们传递的 Supplier 对象返回的是字符串 "默认值",所以 value 变量最终的值为 "默认值"。最后,输出“Optional对象的值为:默认值”。

需要注意的是,使用 orElseGet(Supplier other) 方法时,传递的 Supplier 对象不能为 null,否则会抛出 NullPointerException 异常。

String str = null;
Optional optionalStr = Optional.ofNullable(str);

String value = optionalStr.orElseGet(null); // 抛出 NullPointerException 异常

         在上述代码中,我们同样使用 Optional.ofNullable() 方法将一个为 null 的字符串类型变量 str 包装到 Optional 对象中,并将其赋值给了一个名为 optionalStr 的变量。接着,我们调用 orElseGet(null) 方法来设置默认值。由于传递给 orElseGet() 方法的参数为 null,因此会抛出 NullPointerException 异常。因此,在调用 orElseGet(Supplier other) 方法时必须指定一个非 null 的 Supplier 对象。

orElseThrow(Supplier exceptionSupplier)

  orElseThrow(Supplier exceptionSupplier) 方法是 Optional 类中的一个方法,用于在 Optional 对象为空时抛出指定的异常。具体来说,如果 Optional 对象的值为 null,那么将会调用传入的 Supplier 函数生成一个异常对象,然后将其抛出。

下面是一个使用 orElseThrow() 方法的示例:

Optional optionalStr = Optional.ofNullable(null);

String result = optionalStr.orElseThrow(() -> new RuntimeException("字符串为空"));

        在上述代码中,我们使用 Optional.ofNullable() 方法将一个 null 值包装成 Optional 类型的对象并赋值给 optionalStr 变量。接着,我们调用 orElseThrow() 方法设置了一个默认值,如果 Optional 对象当前的值为空,就会抛出由匿名Supplier 对象生成的RuntimeException 异常,并将异常信息设置为"字符串为空"。因为这个 Optional 为空,所以会抛出异常。

需要注意的是,使用 orElseThrow() 方法时,必须指定一个 Supplier 对象来生成异常。这个Supplier 对象返回的是需要抛出的异常对象。

Optional optionalStr = Optional.ofNullable(null);

String result = optionalStr.orElseThrow(null); // 抛出 NullPointerException 异常

        如果在调用orElseThrow() 方法时传递的 Supplier 参数为 null,则会抛出NullPointerException 异常。因此,在调用 orElseThrow(Supplier throwableSupplier) 方法时必须指定一个非null的Supplier函数。 

四、对 Optional 对象中的值进行操作的方法

ifPresent(Consumer consumer)

   ifPresent(Consumer consumer) 方法是 Optional 类中的一个方法,用于判断 Optional 对象是否有值(即不为 null)。如果该对象有值,则调用传入的 Consumer 函数处理该值。否则,什么也不做。

下面是一个使用 ifPresent() 方法的示例:

import java.util.Optional;

public class Example {
    public static void main(String[] args) {
        Optional optionalStr = Optional.of("Hello World!");

        optionalStr.ifPresent(str -> System.out.println("Optional 中包含非空字符串:" + str));
    }
}

        在这个示例中,我们首先创建了一个值为 "Hello World!"Optional 对象。接着,我们使用 ifPresent(Consumer consumer) 方法判断 Optional 对象是否有值,如果有则输出 "Optional 中包含非空字符串:" 连接上该字符串的值。

在运行这个程序后,输出结果应该为:

Optional 中包含非空字符串:Hello World!

         使用 ifPresent() 方法时,必须设置一个非空的 Consumer 函数。该函数用于处理 Optional 对象中包含的值。如果该对象为空,ifPresent() 方法不会做任何事情。

filter(Predicate predicate)

   filter(Predicate predicate)Optional 类中的一个方法,它用于过滤 Optional 对象中的值,只有当值满足特定条件时才保留。

该方法接受一个 Predicate 参数,这个参数是一个函数式接口,需要自己实现其中的 test(T t) 方法。test(T t) 方法用于测试指定对象是否符合特定条件。

        如果 Optional 对象中的值满足 Predicate 参数中的条件,则返回该值所在的 Optional 对象,否则返回一个空的 Optional 对象。

示例代码:

import java.util.Optional;

public class Example {
    public static void main(String[] args) {
        Optional optionalStr = Optional.of("Hello World!");

        Optional filtered = optionalStr.filter(str -> str.contains("World"));
        System.out.println("过滤后的 Optional 对象:" + filtered);
    }
}

        在上面的示例中,我们首先创建了一个值为 "Hello World!"Optional 对象。接着,我们使用 filter 方法并传入一个 Predicate 参数,这个 Predicate 参数判断字符串是否包含 "World" 子串,如果包含则返回此 Optional 对象,否则返回一个空 Optional 对象。

输出结果如下:

过滤后的 Optional 对象:Optional[Hello World!]

         需要注意的是,如果 Optional 对象中的值为 null,则直接返回一个空的 Optional 对象,并不会执行传进去的 Predicate 参数的计算。如果需要对 null 值进行判断,可以使用 Optional.ofNullable(T value) 方法来创建一个包含可空值的 Optional 对象。

map(Function mapper)

        map(Function mapper) 是 Optional 类中的一个方法,用于对 Optional 对象中的值进行转换,并返回一个新的 Optional 对象。该方法接受一个 Function 参数,这个参数也是一个函数式接口,需要自己实现其中的 apply(T t) 方法。apply(T t) 方法用于将指定类型的对象转换为另一种类型的对象。
        如果 Optional 对象中的值不为空,则将该值作为参数传递给 Function 对象中的 apply(T t) 方法,得到一个新的对象作为转换后的结果;否则直接返回一个空的 Optional 对象。

示例代码:

import java.util.Optional;

public class Example {
    public static void main(String[] args) {
        Optional optionalStr = Optional.of("Hello World!");

        Optional lengthOptional = optionalStr.map(String::length);
        lengthOptional.ifPresent(len -> System.out.println("字符串长度为:" + len));
    }
}

在上面的示例中,我们首先创建了一个值为 "Hello World!"Optional 对象。接着,我们使用 map 方法并传入一个 Function 参数,这个 Function 参数将字符串转换成了整型,即字符串的长度。在这里,我们使用方法引用 String::length,而不是使用 lambda 表达式来实现。

接着,我们使用 ifPresent 方法判断新的 Optional 对象是否为空,如果不为空则输出其中的值。

输出结果如下:

字符串长度为:11

        需要注意的是,在调用 map 方法时,返回值是一个新的 Optional 对象,因此我们可以在该对象上连续调用其他方法来进行操作,比如 orElse(T other)orElseGet(Supplier other) 等。同时如果 Function 对象中的转换过程中抛出了异常,则该方法也会将该异常包装进一个 RuntimeException 中重新抛出。

flatMap(Function> mapper)

  flatMap(Function> mapper)Optional 类中的一个方法,用于对 Optional 对象中的值进行转换,并返回一个新的 Optional 对象。该方法接受一个 Function 参数,这个参数也是一个函数式接口,需要自己实现其中的 apply(T t) 方法。apply(T t) 方法用于将指定类型的对象转换为另一种类型的 Optional 对象。

        如果 Optional 对象中的值不为空,则将该值作为参数传递给 Function 对象中的 apply(T t) 方法,得到一个新的 Optional 对象作为转换后的结果;否则直接返回一个空的 Optional 对象。与 map 方法不同,flatMap 方法可以将最终产生的 Optional 对象展开,使其成为一个扁平的对象。

示例代码:

import java.util.Optional;

public class Example {
    public static void main(String[] args) {
        Optional optionalStr = Optional.of("Hello World!");

        Optional lengthOptional = optionalStr.flatMap(str -> {
            if(str.contains("World")) {
                return Optional.of(str.length());
            } else {
                return Optional.empty();
            }
        });
        lengthOptional.ifPresent(len -> System.out.println("字符串长度为:" + len));
    }
}

        在上面的示例中,我们首先创建了一个值为 "Hello World!"Optional 对象。接着,我们使用 flatMap 方法并传入一个 Function 参数,这个 Function 参数将根据字符串中是否包含 "World" 子串,返回一个或者空的 Optional 对象。

        在这里,如果字符串中包含 "World" 子串,则返回包含字符串长度的 Optional 对象;否则返回一个空的 Optional 对象。最终得到的结果是一个扁平化的 Optional 对象。

        接着,我们使用 ifPresent 方法判断新的 Optional 对象是否为空,如果不为空则输出其中的值。

输出结果如下:

字符串长度为:11

        需要注意的是,在调用 flatMap 方法时,返回值是一个新的 Optional 对象,因此我们可以在该对象上连续调用其他方法来进行操作,比如 orElse(T other)orElseGet(Supplier other) 等。同时如果 Function 对象中的转换过程中抛出了异常,则该方法也会将该异常包装进一个 RuntimeException 中重新抛出。 

orElseThrow()

  orElseThrow()方法,用于在 Optional 对象为空时抛出指定的异常。该方法不接受任何参数,在 Optional 对象为空时会抛出一个默认的 NoSuchElementException 异常。如果需要指定其他类型的异常,请使用带有 Supplier exceptionSupplier 参数的重载方法。

示例代码:

import java.util.Optional;

public class Example {
    public static void main(String[] args) {
        Optional optionalStr1 = Optional.of("Hello World!");
        String str1 = optionalStr1.orElseThrow();
        System.out.println(str1);

        Optional optionalStr2 = Optional.empty();
        String str2 = optionalStr2.orElseThrow(() -> new RuntimeException("值不存在!"));
    }
}

        在上面的示例中,我们首先创建了一个值为 "Hello World!"Optional 对象 optionalStr1。接着,我们调用了 orElseThrow() 方法获取 optionalStr1 中的值,由于 optionalStr1 不为空,因此可以直接返回其中的值,并将其赋值给 str1。最终输出结果为 "Hello World!"。

     接着,我们创建了一个空的 Optional 对象 optionalStr2。接着,我们调用了 orElseThrow(Supplier exceptionSupplier) 方法,由于 optionalStr2 为空,因此该方法会抛出一个 RuntimeException 异常。在这里,我们通过 lambda 表达式传入了一个异常信息,表示值不存在。最终程序抛出异常,输出结果如下:   

Hello World!
Exception in thread "main" java.lang.RuntimeException: 值不存在!
	at Example.main(Example.java:10)

        需要注意的是,在调用 orElseThrow() 方法时,如果 Optional 对象为空,则该方法会抛出一个异常。因此在使用该方法时,需要确保 Optional 对象中有值。同时,如果需要抛出指定类型的异常,也可以调用带有 Supplier exceptionSupplier 参数的重载方法并传入异常信息。


上述是Java8中Optional类提供的常用方法,开发者可以根据自己的需求灵活使用。

 五、Optional类方法组合使用的示例

   组合使用 filter 和 map 方法

import java.util.Optional;

public class Example {
    public static void main(String[] args) {
        Optional optionalStr = Optional.of("123");

        int value = optionalStr
                .filter(str -> str.length() > 0) // 筛选出非空字符串
                .map(Integer::parseInt) // 将字符串转换成整型数字
                .orElse(0); // 如果 Optional 对象为空,返回默认值 0

        System.out.println(value); // 输出结果为 123
    }
}

        在上面的示例中,我们通过 Optional 类中的 filter 方法和 map 方法组合对字符串进行处理。首先,我们对字符串进行了非空过滤,然后将其转换成整型数字。最后,如果 Optional 对象为空,我们设置了一个默认值 0。最终输出结果为 123。

组合使用 filter 和 flatMap 方法

import java.util.Optional;

public class Example {
    public static void main(String[] args) {
        Optional optionalStr = Optional.of("hello, world");

        optionalStr
                .filter(str -> str.contains("world")) // 筛选出包含 "world" 的字符串
                .flatMap(str -> Optional.of(str.length())) // 将符合条件的字符串封装成新的 Optional 对象
                .ifPresent(System.out::println); // 输出长度大于等于 5 的字符串

    }
}

        在上面的示例中,我们使用了 filter 方法对字符串进行过滤,只保留包含 "world" 的字符串。接着,我们使用 flatMap 方法将符合条件的字符串封装成新的 Optional 对象。最后,我们通过 ifPresent 方法输出长度大于等于 5 的字符串的长度。

组合使用 map 和 orElseThrow 方法

import java.util.Optional;

public class Example {
    public static void main(String[] args) {
        Optional optionalStr = Optional.of("hello");
        
        int length = optionalStr
                .map(String::length) // 将字符串映射成其长度
                .orElseThrow(IllegalArgumentException::new); // 如果 Optional 对象为空,抛出 IllegalArgumentException 异常
        
        System.out.println(length); // 输出结果为 5
    }
}

        在上面的示例中,我们使用了 map 方法将字符串映射成其长度,并使用 orElseThrow 方法当 Optional 对象为空时抛出异常。

        需要注意的是,在使用 Optional 类中的方法组合时,每一个方法的返回值都是一个 Optional 对象,因此可以在该对象上继续调用其他方法,直到最终得到需要的值。同时,如果在方法组合的过程中出现了空值,那么后续的方法将不会被执行,并返回一个空的 Optional 对象。

组合示例

import java.util.Optional;

public class Example {
    public static void main(String[] args) {
        Optional optionalStr = Optional.of("Hello, World!");

        optionalStr
                .filter(str -> str.contains("World")) // 筛选出包含 "World" 的字符串
                .map(String::length) // 将剩余的字符串映射成其长度
                .flatMap(len -> {
                    if (len >= 10) {
                        return Optional.of("String length: " + len);
                    } else {
                        return Optional.empty();
                    }
                }) // 对字符串长度进行判断并封装成 Optional 对象
                .ifPresent(System.out::println); // 输出长度大于等于 10 的字符串
    }
}

        在上面的示例中,我们首先创建了一个值为 "Hello, World!"Optional 对象 optionalStr。接着,我们使用 filter 方法对 optionalStr 对象中的值进行筛选,只保留包含 "World" 子串的字符串。然后,我们使用 map 方法将剩余的字符串映射成其长度。接着,我们使用 flatMap 方法对字符串长度进行判断,并将符合条件的长度封装成一个新的 Optional 对象。最后,我们通过 ifPresent 方法输出长度大于等于 10 的字符串。

        需要注意的是,在调用 Optional 方法组合时,每一个方法的返回值都是一个 Optional 对象,因此可以在该对象上继续调用其他方法,直到最终得到需要的值。同时,如果在方法组合的过程中出现了空值,那么后续的方法将不会被执行,并返回一个空的 Optional 对象。

输出结果如下:

String length: 13

多层判断组合示例

获取用户信息

SecurityContextHolder.getContext().getAuthentication();
    if (authentication != null) {
		Object principal = authentication.getPrincipal();
		if (principal != null && principal instanceof LoginUser) {
			return (LoginUser) principal;
		}
	}

使用Java 8中的Optional类优化上述代码,使其更加简洁和易读。优化后的代码如下:

    
   // 使用Java 8中的Optional类优化上述代码,使其更加简洁和易读。优化后的代码如下:
   return Optional.ofNullable(SecurityContextHolder.getContext().getAuthentication())
    .map(Authentication::getPrincipal)
    .filter(principal -> principal instanceof LoginUser)
    .map(LoginUser.class::cast)
    .orElse(null);

解释:

  1. 使用ofNullable方法将可能为null的对象包装成Optional对象,以便在后续流式处理中操作。

  2. 使用map方法将Optional中的Authentication对象映射为其principal属性。

  3. 使用filter方法过滤类型不是LoginUser的情况。

  4. 如果存在符合条件的LoginUser对象,则使用map方法将其强转为LoginUser类型返回;否则,返回null。

你可能感兴趣的:(java,java)