作者:goodluckwj
來源:blog.csdn.net/qq_35634181/article/details/108867857
ExportTemperatureDto物體物件:
@Getter
@Setter
@ToString
public class ExportTemperatureDto {
private String name;
private Double morningTemperature;
private Double afternoonTemperature;
private String classId;
private String gradeId;
private Integer personId;
}
在一個ExportTemperatureDto的集合中,根據personId屬性去重,生成一個新的集合,
import static java.util.Comparator.comparing;
import static java.util.stream.Collectors.collectingAndThen;
import static java.util.stream.Collectors.toCollection;
public class StreamTest {
public static void main(String[] args) {
List<ExportTemperatureDto> temperatureList = Lists.newArrayList();
temperatureList.add(new ExportTemperatureDto(1, "haha"));
temperatureList.add(new ExportTemperatureDto(2, "haha"));
temperatureList.add(new ExportTemperatureDto(3, "haha"));
temperatureList.add(new ExportTemperatureDto(4, "haha"));
temperatureList.add(new ExportTemperatureDto(1, "hahaasdas"));
temperatureList.add(new ExportTemperatureDto(2, "hahaasdas"));
List<ExportTemperatureDto> result = temperatureList.stream()
.collect(
collectingAndThen(
toCollection(
() -> new TreeSet<>(comparing(ExportTemperatureDto::getPersonId))
),
ArrayList::new
)
);
result.forEach(System.out::println);
/*
輸出結果為:
personId為1的,其名稱為haha
personId為2的,其名稱為haha
因為TreeSet底層是使用TreeMap進行實作的,傳入了根據getPersonId進行比較的比較器
在判斷personId相同時,其比較結果為0,然后就會替換其value值,而key值是不會變化的,
又因為TreeSet是將傳入的元素作為key的,所以使用TreeSet時,當比較器比較的結果相同時,以不會將原來的值替換成比較后的值
*/
}
}
知其然知其所以然,這個stream流的操作看起來還是有點難度的,這里記錄一下,
使用到了collectingAndThen完成根據屬性進行去重的操作,對于該去重操作的關鍵使用到了collectingAndThen、toCollection、TreeSet,有點難以理解,當時我也是懵逼的,這里記錄一下,以后肯定還會用的到,
理解根據物件的屬性進行去重的核心是,將集合放到TreeSet中,然后再將TreeSet轉為List, 其中TreeSet要傳入一個根據哪個屬性進行比較的比較器,然后使用public ArrayList(Collection<? extends E> c)將TreeSet放入構造器中生成List,
上面的Stream操作可以使用普通的集合:
TreeSet<ExportTemperatureDto> treeSet = new TreeSet<>(Comparator.comparing(ExportTemperatureDto::getPersonId));
for (ExportTemperatureDto temperatureDto : temperatureList){
treeSet.add(temperatureDto);
}
List<ExportTemperatureDto> result2 = new ArrayList<>(treeSet);
只要能夠理解普通集合怎么操作的,那么使用Stream流操作時,就是要看對于API的使用是否熟悉,其實這個才是關鍵,只有理解了collectingAndThen、toCollection、JDK8的匿名函式這樣內容,才能看懂這個式子,
下面就簡單介紹一下:
首先說一下collectingAndThen方法的使用-------先進行結果集的收集,然后將收集到的結果集進行下一步的處理 ,紅字的兩句話是理解collectingAndThen的關鍵,首先看一下collectingAndThen需要傳遞的引數:
public static<T,A,R,RR> Collector<T,A,RR>
collectingAndThen(Collector<T,A,R> downstream,
Function<R,RR> finisher)
可以看到第一個引數是Collector介面的子類,所以還是對于對于Collector的處理,Collectors工具類里面的toList()、toSet()、joining()、mapping()、collectingAndThen()等幾乎所有的方法都可以使用,這樣感覺這個collectingAndThen就很強大了,可以嵌套的去使用,
第二個引數是一個Function函式,熟悉的同學都知道,Function函式是這樣的:R apply(T t),這個也是理解上面去重式子的關鍵,原來我想的是ArrayList::new呼叫的無參的構造方法,其實他呼叫的ArrayList的有參構造方法,
public ArrayList(Collection<? extends E> c)
呼叫的是上面那個構造方法,這樣就很清晰,就是把第一個引數downstream的結果,交給第二個引數Function函式的引數里面,R apply(T t),也就是將結果設定成t,
對于toCollection是一個通用的轉為集合的操作,當然在Collectors類里面也有toList()、toSet()方法,但是都不滿足于使用TreeSet來收集集合的方法,所以使用toCollection是一個通用的方法,使用TreeSet進行收集,然后傳入根據哪個屬性進行比較的比較器,這樣就可以了,
近期熱文推薦:
1.1,000+ 道 Java面試題及答案整理(2022最新版)
2.勁爆!Java 協程要來了,,,
3.Spring Boot 2.x 教程,太全了!
4.別再寫滿屏的爆爆爆炸類了,試試裝飾器模式,這才是優雅的方式!!
5.《Java開發手冊(嵩山版)》最新發布,速速下載!
覺得不錯,別忘了隨手點贊+轉發哦!
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/445859.html
標籤:Java
上一篇:java高級-續1
下一篇:集合框架--物件陣列的概述和使用
