Ce face Stream.mapMulti
mapMulti face același lucru ca flatMap, dar fără să creezi un stream pentru fiecare element. Lambda primește elementul și un „consumator” (Consumer); fiecare apel consumator.accept(x) trimite valoarea x în stream-ul rezultat. Dacă nu apelezi niciodată accept, elementul dispare.
Este mai eficient decât flatMap când un element produce puține valori, și mai ușor de citit când logica are if-uri. Tipul rezultatului trebuie de obicei scris explicit: .<String>mapMulti(...).
mapMultiToInt, mapMultiToLong și mapMultiToDouble produc direct stream-uri de numere primitive, cu sum() și average().
Parametri
| Parametru | Descriere |
|---|---|
f |
Funcția care primește elementul și consumatorul; apelează accept pentru fiecare valoare de trimis. |
Ce returnează
Un stream cu toate valorile trimise prin accept, în ordinea apelurilor.
Exemple
Exemplul 1: Filtrare și transformare într-un singur pas
Numerele negative sunt eliminate, iar cele pare apar de două ori.
import java.util.List;
public class Main {
public static void main(String[] args) {
List<Integer> numere = List.of(3, -1, 4, 7, -5, 10);
List<Integer> rezultat = numere.stream()
.<Integer>mapMulti((n, trimite) -> {
if (n < 0) {
return; // nimic trimis: elementul dispare
}
trimite.accept(n);
if (n % 2 == 0) {
trimite.accept(n); // pare: încă o dată
}
})
.toList();
System.out.println(rezultat);
}
}
Rezultat
[3, 4, 4, 7, 10, 10]
Exemplul 2: Variante pentru numere primitive
import java.util.List;
public class Main {
record Factura(String client, double suma, double tva) {}
public static void main(String[] args) {
List<Factura> facturi = List.of(new Factura("Ana", 100, 21), new Factura("Dan", 250, 52.5));
double total = facturi.stream()
.mapMultiToDouble((f, t) -> {
t.accept(f.suma());
t.accept(f.tva());
})
.sum();
System.out.println("Total cu TVA: " + total);
int litere = List.of("Iași", "Cluj").stream()
.mapMultiToInt((s, t) -> t.accept(s.length()))
.sum();
System.out.println("Litere: " + litere);
long kb = List.of(2L, 3L).stream()
.mapMultiToLong((n, t) -> t.accept(n * 1024))
.sum();
System.out.println("Octeți: " + kb);
}
}
Rezultat
Total cu TVA: 423.5
Litere: 8
Octeți: 5120
Exemplul 3: Doar valorile de un anumit tip
O listă cu obiecte amestecate; păstrăm doar textele, deja convertite la String.
import java.util.List;
public class Main {
public static void main(String[] args) {
List<Object> amestec = List.of("Ana", 12, "Brașov", 3.5, "Radu");
List<String> texte = amestec.stream()
.<String>mapMulti((o, t) -> {
if (o instanceof String s) {
t.accept(s);
}
})
.toList();
System.out.println(texte);
}
}
Rezultat
[Ana, Brașov, Radu]
Greșeli frecvente
- Nu scrii tipul rezultatului (
.<String>mapMulti). Compilatorul deduceObjectșitoList()devineList<Object>. - Încerci să returnezi o valoare din lambda.
mapMultinu folosește valoarea returnată; valorile se trimit doar prinaccept.
Comenzi înrudite
Stream.flatMap: Transformă fiecare element într-un stream și lipește toate aceste stream-uri într-unul singur.Stream.flatMapToInt: Ca flatMap, dar fiecare element produce un stream de numere primitive, iar rezultatul este un IntStream, LongStream sau DoubleStream.Consumer: O acțiune care primește o valoare și nu returnează nimic (afișează, salvează, trimite); o rulezi cu accept.Stream.filter: Păstrează în stream doar elementele care îndeplinesc o condiție.