In Java, flatMap(Function mapper) is an intermediate Stream operation that transforms each element into a stream and flattens all streams into a single stream. It is used for one-to-many transformations and flattening nested data structures.
- flatMap() is an intermediate operation and is lazy, meaning it is only executed when a terminal operation is invoked.
- Each mapped stream is closed automatically after being flattened. If the mapped stream is null, an empty stream is used.
- Unlike map(), which performs one-to-one transformations, flatMap() can produce zero or more elements per input element, resulting in a flattened stream.
import java.util.*;
import java.util.stream.*;
class GFG {
public static void main(String[] args) {
List<List<Integer>> numbers = Arrays.asList(
Arrays.asList(1, 2),
Arrays.asList(3, 4)
);
numbers.stream()
.flatMap(list -> list.stream())
.forEach(System.out::println);
}
}
Output
1 2 3 4
Explanation:
- numbers.stream() creates a stream of lists: [[1,2], [3,4]].
- flatMap(list -> list.stream()) converts each inner list into a stream and flattens them into a single stream: 1, 2, 3, 4.
- forEach(System.out::println) prints each element one by one.
Syntax
<R> Stream<R> flatMap(Function<? super T, ? extends Stream<? extends R>> mapper)
Parameters:
- mapper: A function that takes an element of type T and returns a Stream of elements of type R.
- T: Type of elements in the input stream.
- R: Type of elements in the resulting flattened stream.
Example 1: Flattening a Stream of Lists
import java.util.*;
import java.util.stream.Stream;
class Geeks
{
// Driver code
public static void main(String[] args)
{
// Creating a List of Lists
List<List<String>> listOfLists = Arrays.asList(
Arrays.asList("Geeks", "For"),
Arrays.asList("GeeksForGeeks", "A computer portal"),
Arrays.asList("Java", "Programming")
);
// Using Stream flatMap(Function mapper)
listOfLists.stream()
.flatMap(list -> list.stream())
.forEach(System.out::println);
}
}
Output
Geeks For GeeksForGeeks A computer portal Java Programming
Explanation: Here, flatMap() is used to flatten a stream of lists into a single stream of elements. Using map instead would not achieve this flattening effect.
Example 2: Mapping Strings to Characters at Position 2
import java.util.*;
import java.util.stream.*;
class Geeks {
public static void main(String[] args) {
List<String> list = Arrays.asList("Geeks", "GFG", "Java");
list.stream()
.flatMap(str -> str.chars().mapToObj(c -> (char) c))
.forEach(System.out::println);
}
}
Output
G e e k s G F G J a v a
Explanation: In this case, flatMap is used to create a stream of characters at position 2 from each string. If we used it map, the result would be a stream of streams, not a flattened stream of characters.
Example 3: Flattening Nested Integer Lists
import java.util.*;
import java.util.stream.Collectors;
class Geeks {
public static void main(String[] args){
// Creating a list of prime numbers
List<Integer> PrimeNumbers
= Arrays.asList(5, 7, 11, 13);
// Creating a list of odd numbers
List<Integer> OddNumbers = Arrays.asList(1, 3, 5);
// Creating a list of even numbers
List<Integer> EvenNumbers
= Arrays.asList(2, 4, 6, 8);
// Combining the above lists into a list of lists
List<List<Integer> > listOfListofInts
= Arrays.asList(PrimeNumbers, OddNumbers,
EvenNumbers);
// Printing the structure before flattening
System.out.println(
"The Structure before flattening is : "
+ listOfListofInts);
// Flattening the list of lists into a single list
// using flatMap
List<Integer> listofInts
= listOfListofInts.stream()
.flatMap(list -> list.stream())
.collect(Collectors.toList());
// Printing the structure after flattening
System.out.println(
"The Structure after flattening is : "
+ listofInts);
}
}
Output
The Structure before flattening is : [[5, 7, 11, 13], [1, 3, 5], [2, 4, 6, 8]] The Structure after flattening is : [5, 7, 11, 13, 1, 3, 5, 2, 4, 6, 8]
Explanation: This example demonstrates how flatMap flattens nested lists into a single list. Using map would keep the nested structure intact.
How does flatMap() work ?
flatMap() is essentially a combination of map() + flattening:
- Map: Apply the mapping function to each element.
- Flatten: Merge the resulting streams into a single stream.
It is commonly used for:
- Flattening nested collections (List<List<T>>)
- Splitting strings into characters
- Transforming objects into multiple elements in reactive streams
flatMap() vs map()
Feature | map() | flatMap() |
|---|---|---|
Transformation | One-to-one | One-to-many |
Output Stream | Same size as input | Can be different size |
Use Case | Simple transformations | Flatten nested structures |