Java Stream API 中常用方法复习及项目实战示例

在最近的练手项目中,对于stream流的操作愈加频繁,我也越来越感觉stream流在处理数据是的干净利落,因此写博客用来记录最近常用的方法以便于未来的复习。

map() 方法

map()是一个中间操作(intermediate operation),用于将流中的每个元素按照给定的函数进行转换。
常见用法示例:

java 复制代码
// 在RoleController中,将Role对象转换为RoleDTO对象
List<RoleDTO> dtos = list.stream().map(Role::toDTO).collect(Collectors.toList());

// 在MenuController中,将Menu对象转换为MenuOptionVO对象
List<MenuOptionVO> menus = list.stream().map(MenuOptionVO::new).collect(Collectors.toList());

// 在CouponServiceImpl中,将bizId转换为CouponScope对象
List<CouponScope> newScopeList = newScopes.stream()
        .map(bizId -> new CouponScope()
                .setBizId(bizId)
                .setCouponId(couponId))
        .collect(Collectors.toList());

collect() 方法

collect()是一个终端操作(terminal operation),用于将流中的元素收集到集合或其他数据结构中。

**常见的收集器(Collectors)用法:

  1. Collectors.toList() - 收集到List中**
java 复制代码
// 收集为List
List<RoleDTO> dtoList = list.stream().map(Role::toDTO).collect(Collectors.toList());

2. Collectors.toSet() - 收集到Set中

java 复制代码
// 在PointsBoardServiceImpl中收集用户ID为Set
Set<Long> userIds = list.stream().map(PointsBoard::getUserId).collect(Collectors.toSet());

3. Collectors.toMap() - 收集到Map中

java 复制代码
// 在LearningLessonServiceImpl中,将课程信息收集为Map
Map<Long, CourseSimpleInfoDTO> cMap = cInfoList.stream()
        .collect(Collectors.toMap(CourseSimpleInfoDTO::getId, c -> c));

// 在PointsBoardServiceImpl中,将用户信息收集为Map
Map<Long, String> userMap = userDTOS.stream()
        .collect(Collectors.toMap(UserDTO::getId, UserDTO::getName));

// 在CartServiceImpl中,将课程信息收集为Map
Map<Long, CourseSimpleInfoDTO> courseMap = courseSimpleInfos.stream()
        .collect(Collectors.toMap(CourseSimpleInfoDTO::getId, c -> c));

4. Collectors.groupingBy() - 按条件分组

java 复制代码
// 在CouponServiceImpl中,按优惠券ID分组并统计数量
Map<Long, Long> unUseMap = list.stream()
        .filter(userCoupon -> userCoupon.getStatus() == UserCouponStatus.UNUSED)
        .collect(Collectors.groupingBy(UserCoupon::getCouponId, Collectors.counting()));

// 在CourseCatalogueServiceImpl中,按媒资ID分组并统计引用次数
Map<Long, Long> mediaAndCount = courseCatalogues.stream()
        .collect(Collectors.groupingBy(
                CourseCatalogue::getMediaId, Collectors.counting()));

实际应用示例
让我们看一个更复杂的例子,来自CouponServiceImpl:

java 复制代码
// 统计当前用户针对每一个卷已领取且未使用的数量
//filter过滤得到未使用的
Map<Long, Long> unUseMap = list.stream()
        .filter(userCoupon -> userCoupon.getStatus() == UserCouponStatus.UNUSED)
        .collect(Collectors.groupingBy(UserCoupon::getCouponId, Collectors.counting()));

这个例子展示了:
使用filter()进行筛选(只保留未使用的优惠券)
使用collect()结合Collectors.groupingBy()进行分组
使用Collectors.counting()进行计数

=========================================================================

对于stream()的操作,个人认为主要是对于其中的参数难以灵活使用,根据个人使用情况得到以下总结:

map()方法参数选择:
①使用方法引用(如Role::toDTO)当转换逻辑已经在类中存在
②使用Lambda表达式(如bizId -> new CouponScope().setBizId(bizId))当需要创建新对象或进行复杂转换

collect()方法参数选择:
①Collectors.toList() - 当需要保持元素顺序的列表时
②Collectors.toSet() - 当需要去重元素时
③Collectors.toMap(keyMapper, valueMapper) - 当需要键值对结构时
④Collectors.groupingBy(classifier) - 当需要按条件分组时
⑤Collectors.groupingBy(classifier, downstream) - 当需要分组后进一步聚合时

相关推荐
Java陈序员8 小时前
轻量运维面板!一款现代化的服务器控制面板工具!
运维·服务器·python·react.js·github
彧azz8 小时前
Java学习语法篇:变量
java·学习
bosins8 小时前
WSL 迁移指南:如何将 Linux 环境完整复制到另一台电脑
linux·运维·服务器
繁星蓝雨8 小时前
C++的设计与演进大纲(如何从C语言一步步成长为C++)
c语言·开发语言·c++·c++历史·c++演进
程序员阿鹏8 小时前
为什么MySQL InnoDB选择B+树?
数据结构·数据库·b树·sql·mysql·算法·缓存
Evand J9 小时前
【MATLAB例程,图像降噪滤波9】自适应维纳滑动窗口滤波(Wiener)图像降噪、方法对比,有中文注释
开发语言·图像处理·计算机视觉·matlab·滑动窗口·滤波·降噪
杜大哥9 小时前
python程序:如何查看电脑【电池电量的剩余百分比】 和 【是否插入连接着充电器】?
开发语言·python
wuyk5559 小时前
Python网络爬虫入门到实战 第01章:爬虫到底是什么?原理、流程、合法性、风险全解析(零基础必看)
开发语言·爬虫·python
信誓旦旦的程序猿9 小时前
【量化系统从零构建 #04】存储设计:选型·建库·交易日历
java·人工智能·python·股票数据api·股票数据·股票数据api接口·股票api数据接口
yurenpai(27届找实习中)9 小时前
Java 10 的 var 为什么不能随便用?从订单汇总看懂类型推断与泛型陷阱
java·开发语言·java18