Java Stream mapMulti() Method

The mapMulti() method in Java is introduced in JDK 16 and is part of Stream interface. In this guide, we will learn how to use mapMulti() method in Java with practical examples and real-world use cases to better understand its usage.

Table of Contents

  1. Introduction
  2. mapMulti() Method Syntax
  3. Examples
    • Basic Usage
    • Using mapMulti() with Complex Transformations
  4. Real-World Use Case
  5. Conclusion

Introduction

The Stream.mapMulti() method in Java allows mapping each stream element to multiple values and flattening them into a single stream. Unlike flatMap(), it uses a BiConsumer to handle the element processing and add multiple results to the stream.

This method is useful when you need to transform each element into zero, one, or multiple values while keeping control over how elements are produced.

mapMulti() is often used when the transformation logic for each element involves generating multiple results in a flexible way.

mapMulti() Method Syntax

The syntax for the mapMulti() method is as follows:

<R> Stream<R> mapMulti(BiConsumer<? super T, ? super Consumer<R>> mapper)

Parameters:

  • mapper: A BiConsumer that consumes an element of the stream and a Consumer to which multiple elements can be passed.

Returns:

  • A new Stream consisting of the mapped elements.

Throws:

  • This method does not throw any exceptions.

Examples

Basic Usage

To demonstrate the basic usage of mapMulti(), we will create a Stream of integers and use mapMulti() to map each integer to its square and cube.

Example

import java.util.stream.Stream;

public class MapMultiExample {
    public static void main(String[] args) {
        Stream<Integer> stream = Stream.of(1, 2, 3);

        // Use mapMulti() to map each integer to its square and cube
        Stream<Integer> mappedStream = stream.mapMulti((number, consumer) -> {
            consumer.accept(number * number); // Square
            consumer.accept(number * number * number); // Cube
        });

        // Print the mapped elements
        mappedStream.forEach(System.out::println);
    }
}

Output:

1
1
4
8
9
27

Using mapMulti() with Complex Transformations

This example shows how to use mapMulti() to split a stream of sentences into a stream of words.

Example

import java.util.stream.Stream;

public class MapMultiComplexExample {
    public static void main(String[] args) {
        Stream<String> stream = Stream.of("Hello world", "How are you");

        // Use mapMulti() to split sentences into words
        Stream<String> wordStream = stream.mapMulti((sentence, consumer) -> {
            for (String word : sentence.split(" ")) {
                consumer.accept(word);
            }
        });

        // Print the mapped elements
        wordStream.forEach(System.out::println);
    }
}

Output:

Hello
world
How
are
you

Real-World Use Case

Example 1: Expanding Hierarchical Data

In real-world applications, mapMulti() can be used to expand hierarchical data, such as transforming a stream of directories into a stream of files:

import java.io.File;
import java.util.stream.Stream;

public class MapMultiFileExample {
    public static void main(String[] args) {
        Stream<File> directories = Stream.of(new File("dir1"), new File("dir2"));

        // Use mapMulti() to expand directories into files
        Stream<File> fileStream = directories.mapMulti((directory, consumer) -> {
            File[] files = directory.listFiles();
            if (files != null) {
                for (File file : files) {
                    consumer.accept(file);
                }
            }
        });

        // Print the mapped elements (files)
        fileStream.forEach(System.out::println);
    }
}

Output:

(Note: The actual output will depend on the contents of the directories.)

Example 2: Flattening Nested Collections

mapMulti() can also be used to flatten nested collections, such as a stream of lists of integers, into a single stream of integers.

import java.util.List;
import java.util.stream.Stream;

public class MapMultiFlattenListExample {
    public static void main(String[] args) {
        Stream<List<Integer>> listOfNumbers = Stream.of(
            List.of(1, 2, 3),
            List.of(4, 5),
            List.of(6, 7, 8)
        );

        // Use mapMulti() to flatten the nested lists into a single stream of integers
        Stream<Integer> flatStream = listOfNumbers.mapMulti((list, consumer) -> {
            for (Integer number : list) {
                consumer.accept(number);
            }
        });

        // Print the flattened stream
        flatStream.forEach(System.out::println);
    }
}

Output:

1
2
3
4
5
6
7
8

Example 3: Transforming and Filtering Data

Another real-world use case of mapMulti() is when transforming and filtering data at the same time. In this example, we will take a stream of integers, map them to their multiples, and only add the multiples that are even.

import java.util.stream.Stream;

public class MapMultiTransformAndFilterExample {
    public static void main(String[] args) {
        Stream<Integer> stream = Stream.of(1, 2, 3, 4);

        // Use mapMulti() to map each integer to its multiples, filtering even multiples
        Stream<Integer> mappedStream = stream.mapMulti((number, consumer) -> {
            int square = number * number;
            int cube = number * number * number;
            
            // Add only even results to the stream
            if (square % 2 == 0) {
                consumer.accept(square);
            }
            if (cube % 2 == 0) {
                consumer.accept(cube);
            }
        });

        // Print the filtered and mapped elements
        mappedStream.forEach(System.out::println);
    }
}

Output:

4
8
64

Conclusion

The Stream.mapMulti() method is used for performing one-to-many mappings of elements in a stream. This method is particularly useful for scenarios where you need to produce a dynamic number of results for each input element.

By understanding and using this method, you can efficiently manage and process streams of values in your Java applications, allowing for flexible and complex data transformations.

Leave a Comment

Your email address will not be published. Required fields are marked *

Scroll to Top