Java中的stream流分組示例詳解
什么是stream流
Java 8引入的Stream API是處理集合數(shù)據(jù)的一種全新方式,它代表了對數(shù)據(jù)元素序列進行函數(shù)式操作的抽象。Stream不是數(shù)據(jù)結(jié)構(gòu),而是一種高級的數(shù)據(jù)處理工具,允許你以聲明式的方式處理數(shù)據(jù)集合,類似于SQL語句操作數(shù)據(jù)庫。
Stream的核心特點:
- 聲明式編程:只需說明"做什么"而非"如何做",代碼更簡潔易讀
- 函數(shù)式風格:與Lambda表達式完美結(jié)合,操作更靈活
- 管道操作:多個操作可以連接起來形成數(shù)據(jù)處理流水線
- 內(nèi)部迭代:不同于集合的外部迭代(使用for-each),Stream在內(nèi)部處理迭代過程
- 延遲執(zhí)行:中間操作不會立即執(zhí)行,只有遇到終結(jié)操作才會觸發(fā)計算
- 不可復用:一個Stream只能被消費一次
1、根據(jù)某個字段分組
// 按 department 字段分組
Map<String, List<User>> groupedByDept = users.stream()
.collect(Collectors.groupingBy(User::getDepartment));2、按多個字段分組(組合分組)
1、方法一:使用 String 拼接作為分組 key(簡單但不夠靈活)
Map<String, List<User>> grouped = users.stream()
.collect(Collectors.groupingBy(
user -> user.getDepartment() + "-" + user.getJobTitle()
));2、使用 Map.Entry(Java 8+ 就支持):
Map<Map.Entry<String, String>, List<User>> grouped = users.stream()
.collect(Collectors.groupingBy(
user -> Map.entry(user.getDepartment(), user.getJobTitle())
)); 這樣 key 是一個 Map.Entry<部門, 職位>,可以唯一確定一個組合
3、使用 record(Java 16+):
// 定義一個記錄類作為分組 key
record DeptJobKey(String department, String jobTitle) {}
Map<DeptJobKey, List<User>> grouped = users.stream()
.collect(Collectors.groupingBy(
user -> new DeptJobKey(user.getDepartment(), user.getJobTitle())
));3、分組后獲取其他統(tǒng)計信息
1、分組后統(tǒng)計每組的數(shù)量
Map<String, Long> countByDept = users.stream()
.collect(Collectors.groupingBy(
User::getDepartment,
Collectors.counting() // 統(tǒng)計每個部門的用戶數(shù)
));
2、分組后獲取每組中的某個屬性集合,比如所有部門下的用戶名
Map<String, List<String>> namesByDept = users.stream()
.collect(Collectors.groupingBy(
User::getDepartment,
Collectors.mapping(User::getName, Collectors.toList()) // 只提取 name 字段
));
3、分組后求每組的某個屬性的最大值 / 最小值 / 平均值
Map<String, Optional<Integer>> maxAgeByDept = users.stream()
.collect(Collectors.groupingBy(
User::getDepartment,
Collectors.mapping(User::getAge, Collectors.maxBy(Comparator.naturalOrder()))
));
// 或者更直觀地使用 Collectors.maxBy / averagingInt 等
//或者使用 Collectors.summarizingInt 做綜合統(tǒng)計
Map<String, IntSummaryStatistics> ageStatsByDept = users.stream()
.collect(Collectors.groupingBy(
User::getDepartment,
Collectors.summarizingInt(User::getAge) // 統(tǒng)計年齡:count, sum, min, max, avg
));4、自定義分組key
Map<String, List<User>> collect = javaList.stream().collect(Collectors.groupingBy(user -> {
String id = user.getId();
return (StringUtils.isEmpty(id)) ? "empty" : "notEmpty"; // 如果為 null,返回empty,不為空notEmpty
}));到此這篇關(guān)于Java的stream流分組的文章就介紹到這了,更多相關(guān)Java stream流分組內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Java 8 對 ArrayList 元素進行排序的操作方法
Java8提供了多種方式對ArrayList元素進行排序,包括使用Collections.sort()方法、Collections.reverseOrder()實現(xiàn)降序排序、使用Lambda表達式進行自定義排序、使用StreamAPI對ArrayList進行排序及按對象屬性排序,本文通過示例代碼介紹的非常詳細,感興趣的朋友一起看看吧2024-11-11
Spring Boot中的WebSocketMessageBrokerConfigurer接口使用
在SpringBoot中,我們可以使用 WebSocketMessageBrokerConfigurer接口來配置WebSocket消息代理,以實現(xiàn)實時通信,具有一定的參考價值,感興趣的可以了解一下2023-11-11
Mybatis-plus新版本分頁失效PaginationInterceptor過時的問題
這篇文章主要介紹了Mybatis-plus新版本分頁失效,PaginationInterceptor過時問題,本文給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下2020-11-11
面試與實戰(zhàn)必備:掌握Java并發(fā)編程關(guān)鍵知識點(線程池/CAS/性能優(yōu)化)
本文從工程視角系統(tǒng)梳理Java并發(fā)編程的關(guān)鍵知識點,主要內(nèi)容包括:并發(fā)問題的本質(zhì)、Java內(nèi)存模型、volatile和synchronized、Lock與AQS、線程池、Future與CompletableFuture、CAS與原子類、并發(fā)容器、死鎖與線上排查、并發(fā)性能優(yōu)化思路等一些常用代碼片段2026-05-05
SpringBoot中實現(xiàn)JWT登錄授權(quán)+無感刷新全流程
在當今的分布式系統(tǒng)和前后端分離架構(gòu)盛行的時代,傳統(tǒng)的基于?Session?的認證方式逐漸暴露出諸多弊端,而?JWT的出現(xiàn),猶如一道曙光,為這些問題提供了完美的解決方案,本文將詳細地為大家講解?Spring?Boot?整合?JWT?實現(xiàn)登錄認證與接口授權(quán)的全流程2026-04-04

