Java flatMap - в чем разница stream.of() и collection.stream()
Я пытаюсь понять flatMap
: flatMap(x->stream.of(x) )
не течет поток и flatMap(x->x.stream())
работает и дает желаемый результат. Может кто-нибудь объяснить разницу между двумя?
import java.util.*;
import java.util.stream.*;
class TestFlatMap{
public static void main(String args[]){
List<String> l1 = Arrays.asList("a","b");
List<String> l2 = Arrays.asList("c","d");
Stream.of(l1, l2).flatMap((x)->Stream.of(x)).forEach((x)->System.out.println(x));
Stream.of(l1, l2).flatMap((x)->x.stream()).forEach((x)->System.out.println(x));
}
}
Выход:
[a, b]
[c, d]
a
b
c
d
2 ответа
То, что вы имели в виду, было так:
Stream.of(l1, l2)
// String[]::new isn't really needed in this simple example,
// but would be in a more complex one...
.flatMap((x)->Stream.of(x.toArray(String[]::new)))
.forEach((x)->System.out.println(x));
Что также приведет к сглаженному потоку a, b, c, d
как ты и ожидал. Stream.of()
поставляется в двух вариантах:
Stream.of(T)
принимая одно значение, как объяснил также ЭранStream.of(T...)
принимая массив (неList
как ты и ожидал)
Так как при прохождении List
в Stream.of()
, единственная применимая перегрузка - та, которая принимает одно значение, вы получили Stream<List<String>>
скорее, чем ожидалось Stream<String>
Stream.of(x)
производит поток из одного элемента - x
, Следовательно, flatMap
возвращает Stream<List<String>>
вместо Stream<String>
,
С другой стороны, x.stream()
где x
это Collection<E>
возвращает Stream<E>
чьим источником являются элементы Collection
так что в вашем случае он возвращает Stream<String>
, который позволяет flatMap
производить Stream<String>
содержащий все String
во всех List<String>
с источника Stream
,
Вы можете увидеть это в Javadoc:
<T> Stream<T> java.util.stream.Stream.of(T t)
Возвращает последовательный поток, содержащий один элемент.
против
Stream<E> stream()
Возвращает последовательный поток с этой коллекцией в качестве источника.