map() — one-to-one transformation: each element produces exactly one result. flatMap() — one-to-many transformation: each element produces a stream of results, and all streams are flattened into one. Think of map() as a vending machine (one coin → one snack), while flatMap() is a bulk dispenser (one coin → a bag of snacks).
map():
Stream<R>.1// Each word → one length2List<Integer> lengths = words.stream()3 .map(String::length)4 .toList();5// Input: ["hello", "world"] → Output: [5, 5]
flatMap():
Stream<R>.1// Each sentence → multiple words2Stream<String> words = sentences.stream()3 .flatMap(s -> Arrays.stream(s.split(" ")));45// Flatten nested lists6List<Integer> flat = nested.stream()7 .flatMap(Collection::stream)8 .toList();
When to use flatMap:
1// Real-world: flatten order items2List<OrderItem> allItems = orders.stream()3 .flatMap(order -> order.getItems().stream())4 .collect(Collectors.toList());56// Real-world: get all unique tags7Set<String> allTags = articles.stream()8 .flatMap(a -> a.getTags().stream())9 .collect(Collectors.toSet());
Performance considerations:
Key difference: