2017-02-09 85 views
8

考慮下面的數據類的一個示例:爲什麼Stream.flatMap不能接受集合?

class Country { 

    List<Region> regions = new ArrayList<>(); 

    List<Region> getRegions() { 
     return regions; 
    } 

} 

class Region { 

    String getName() { 
     return "some name"; 
    } 

} 

。假定我會國家

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

的名單,我想澗那些其區域及其相應的名字,我想要做到以下幾點:

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

但是,該代碼不編譯,因爲「getRegions」的返回值是一個集合(List),而不是FlatMap方法接受的Stream。 但是因爲我知道任何Collection都可以通過它的Collection.stream()方法進行流式處理,這應該不是問題。仍然我被迫寫如下:

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

這是(給予一個更豐富的上下文)遠不如前者可讀。

問題是,有沒有什麼原因,我錯過了,因爲這是龐大的?我在我的框架中有很多例子,我不得不採取這種方式,總是讓我感到酸味。 (猜猜我只需要將Kotlin添加到我們的項目中,並使用flatMap方法擴展Stream類,該方法需要一個Collection:p或我?)

+0

我也嘗試了下面,因爲它在我的腦海中有意義,顯然它沒有編譯: Country :: getRegions :: stream – Lukas

+2

我同意'flatMap'應該接受一個集合,但我不確定SO是能夠提供一個明確的解釋,除了「寫它的人沒有這樣寫」。 – khelwood

+0

「不」也可以是答案:) – Lukas

回答

14

一個技術原因,這並不理想,但可能是爲什麼這不是理想沒做完。 Java中的泛型類型不能重載。

他們需要支持

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

,這意味着他們不能

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

超載它作爲這兩種方法各有擦除後相同的簽名。

他們可以添加一個方法

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

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

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

,但它不會是漂亮。

+0

是的,如果這些方法是補充說這將是一個改進。 – khelwood

+2

@ khelwood它可能不會更短。理想情況下,他們會增加對泛型的稀疏類型和重載的支持。 –

+1

這個答案實際上令人滿意。或者說它提供了一個有效的解釋。謝謝 – Lukas

相關問題