假設我們有一個動物流。
我們有不同的動物子類,我們希望對流應用過濾器以僅具有流的斑馬。我們現在仍然有一個動物流,但只包含斑馬。要獲得 Zebras 流,我們仍然需要進行投射。
Stream<Zebra> zebraStream = animalStream
.filter(Zebra.class::isInstance)
.map(Zebra.class::cast);
Java 14 為 instanceof 引入了模式匹配,因此我們現在可以使用:
if (animal instanceof Zebra zebra) {
System.out.println(zebra.countStripes());
}
有沒有辦法在流管道中使用模式匹配?當然你可以這樣做:
Stream<Zebra> zebraStream = animalStream.map(animal -> {
if (animal instanceof Zebra zebra) {
return zebra;
}
return null;
})
.filter(Objects::nonNull);
但恕我直言,這真的很難看。
uj5u.com熱心網友回復:
模式匹配 mapMulti
要將超型別的 Stream 強制為其子型別之一的 Stream ,您可以將instanceof 的模式匹配與 Java 16 結合使用,Java 16mapMulti()需要一個流元素和Consumer結果型別的 a :
Stream<Animal> animalStream = Stream.of();
Stream<Zebra> zebraStream = animalStream
.mapMulti((animal, consumer) -> {
if (animal instanceof Zebra zebra) consumer.accept(zebra);
});
模式匹配 flatMap
要為 instanceof 使用模式匹配,您還可以使用經典的流操作flatMap(),這就像是mapMulti()為了執行一對多的轉換。
兩者之間的重要區別是通過它的用零個或多個mapMulti()元素替換初始流元素,同時需要生成一個新的流來展平資料。在這種情況下,使用會更有優勢,因為如果串列很大,為每個元素生成單例流可能會很昂貴。ConsumerflatMap()mapMulti()
Stream<Zebra> zebraStream = animalStream
.flatMap(animal ->
animal instanceof Zebra zebra ? Stream.of(zebra) : null
);
請注意,根據檔案而不是空流,我們還可以回傳null(這很方便,因為 Stream.empty() 不回傳常量,而是產生一個新物件):
如果映射流是
null空流,則改為使用。
uj5u.com熱心網友回復:
我想你幾乎完成了!只需使用filter而不是map:
Stream<Zebra> zebraStream = animalStream.stream()
.filter(animal -> animal instanceof Zebra)
.map(Zebra.class::cast);
轉載請註明出處,本文鏈接:https://www.uj5u.com/gongcheng/532001.html
標籤:爪哇java流实例
