How do I use Optional Stream with flatMap?

Using the Optional.stream() method with flatMap is a common scenario when you want to work with collections and operations involving Optional.

The Optional.stream() method converts an Optional value into a Stream, which will either contain the single value (if the Optional is present) or be empty (if the Optional is empty). This is particularly useful in combination with flatMap when working with streams.

Here’s how to use Optional.stream with flatMap in practice:

Example

Here’s an example demonstrating the usage of Optional.stream with flatMap:

package org.kodejava.util.stream;

import java.util.Optional;
import java.util.stream.Stream;

public class OptionalStreamExample {
    public static void main(String[] args) {
        Optional<String> optional1 = Optional.of("Hello");
        Optional<String> optional2 = Optional.of("World");

        // Combine optionals using flatMap and stream
        String result = Stream.of(optional1, optional2)
                .flatMap(Optional::stream)
                .reduce((s1, s2) -> s1 + " " + s2)
                .orElse("No Value");

        System.out.println(result); // Output: Hello World
    }
}

Explanation of the Code:

  1. Stream of Optionals:
    • Start with a Stream containing Optional objects (in this case, optional1 and optional2).
  2. FlatMap with Optional.stream:
    • Use flatMap(Optional::stream) to convert each Optional into a stream:
      • If the Optional contains a value, it will be represented as a Stream with a single element.
      • If the Optional is empty, it results in an empty Stream.
  3. Reduce the Result:
    • Use the reduce method on the resulting stream to combine the values.
    • In the example, s1 + " " + s2 concatenates the non-empty values together.
    • If the result is absent after combining, it defaults to "No Value" using orElse.

Why Use Optional.stream with flatMap?

  • Stream-Friendly Operations: It allows you to continue working seamlessly in the stream pipeline even if the values are wrapped in Optional.
  • Handling Empty Optionals: Automatically avoids null pointer exceptions or manual checks for empty Optional values.
  • Code Simplicity: Reduces boilerplate code by directly transforming Optional into a stream.

Another Example: Filtering and Transforming

Here’s another example where we filter and transform Optional values:

package org.kodejava.util.stream;

import java.util.Optional;
import java.util.stream.Stream;

public class OptionalStreamFilter {
    public static void main(String[] args) {
        Optional<Integer> optional1 = Optional.of(10);
        Optional<Integer> optional2 = Optional.of(20);

        // Sum values greater than 15
        int sum = Stream.of(optional1, optional2)
                .flatMap(Optional::stream)
                .filter(val -> val > 15)
                .mapToInt(Integer::intValue)
                .sum();

        System.out.println("Sum: " + sum); // Output: Sum: 20
    }
}

Key Points:

  • Optional.stream bridges the gap between Optional and Stream APIs.
  • Common use cases include combining multiple Optional values, filtering, transforming, or reducing them in a stream flow.

Leave a Reply

This site uses Akismet to reduce spam. Learn how your comment data is processed.