Why can't Stream.flatMap accept a collection?

The following are examples of data classes:

class Country { List<Region> regions = new ArrayList<>(); List<Region> getRegions() { return regions; } } class Region { String getName() { return "some name"; } } 

Assuming I have a list of countries

  List<Country> countries = new ArrayList<>(); 

And I wanted to Stream them to my regions and their respective names, I would like to do the following:

  countries.stream().flatMap(Country::getRegions).map(Region::getName)... 

However, this code does not compile because the return value of "getRegions" is a Collection (List), unlike Stream, which accepts the FlatMap method. But since I know that any collection can be streamed through its Collection.stream () method, which should not be a problem. However, I have to write it as follows:

  countries.stream().flatMap(c -> c.getRegions().stream()).map(Region::getName)... 

Which (given the richer context) is much less readable than the first.

There are questions, is there any reason that I miss because it is cumbersome? I have many examples in our framework when I am forced to follow this route, always leaving me with a sour taste. (I think I just need to add Kotlin to our projects and extend the Stream class using the FlatMap method, which accepts the collection: p or me?)

+8
java collections java-8 java-stream flatmap
source share
1 answer

A technical reason that is not perfect, but may be why it was not done. You cannot overload the generic Java type.

They need to support

  Stream.flatMap(Function<Object, Stream<X>> function) 

which means they cannot overload it with

  Stream.flatMap(Function<Object, Collection<X>> function) 

since these two methods have the same signature after erasing.

They can add a method.

  Stream.flatMapCollection(Function<Object, Collection<X>> function) 

or

  Stream.flatMapIterable(Function<Object, Iterable<X>> function) Stream.flatMapI(Function<Object, Iterable<X>> function) 

but it will not be so.

+14
source share

All Articles