In Java 8, how to get Stream <T> from Stream <? extends the <T>> collection?

In Java 8, using packages java.util.functionand java.util.stream, as well as new lambda functions and method references, is the best way to turn Stream<Collection<T>>into Stream<T>?

Here is an example with a solution that I have found so far, but I'm not happy. To create Stream<T>from Stream<Collection<T>>, I use collect().stream()with intermediate HashSet(my Collectionis Set).

import java.security.Provider;
import java.util.HashSet;
import static java.lang.System.out;
import static java.security.Security.getProviders;
import static java.security.Provider.Service;
import static java.util.Arrays.stream;

public class ListMessageDigests {
    public static void main(final String... args) {
        stream(getProviders())
            .map(Provider::getServices)
            .collect(HashSet<Service>::new, HashSet::addAll, HashSet::addAll)
            .stream()
            .filter(service -> "MessageDigest".equals(service.getType()))
            .map(Service::getAlgorithm)
            .sorted()
            .forEach(out::println);
    }   
}   

Is there a more elegant way to convert Stream<Collection<T>>to Stream<T>? Like Stream<Set<Service>>in this example in Stream<Service>? I am not happy with the use of intermediates HashSetand .collect().stream()it seems to me that it is difficult.

PS: I know I could just do this:

import static java.security.Security.getAlgorithms;
public class ListMessageDigests {
    public static void main(final String... args) {
        getAlgorithms("MessageDigest")
            .forEach(out::println);
    }
}

getProviders() getServices, a Stream<Set<Service>>, Stream<Collection<T>>, .

+4
1

flatMap Collection#stream

<T> Stream<T> flatten(Stream<? extends Collection<? extends T>> stream){
    return stream.flatMap(Collection::stream);
}

:

import static java.lang.System.out;
import static java.security.Provider.Service;
import static java.security.Security.getProviders;
import static java.util.Arrays.stream;

public class ListMessageDigests {
    public static void main(final String... args) {
        stream(getProviders())
            .flatMap(p -> p.getServices().stream())
            .distinct()
            .filter(service -> "MessageDigest".equals(service.getType()))
            .map(Service::getAlgorithm)
            .sorted()
            .forEach(out::println);
    }
}

, distinct , , , .

+9

Source: https://habr.com/ru/post/1568942/