文章目录
- [269. Java Stream API - Map-Filter-Reduce算法模型](#269. Java Stream API - Map-Filter-Reduce算法模型)
-
- [🧾 示例背景:计算十月销售总额](#🧾 示例背景:计算十月销售总额)
- [🧮 用传统方式求出十月的销售总额](#🧮 用传统方式求出十月的销售总额)
-
- [✅ 输出:](#✅ 输出:)
- [🧠 拆解这个处理过程:Map - Filter - Reduce](#🧠 拆解这个处理过程:Map - Filter - Reduce)
- [🚀 使用 Stream API 实现相同逻辑](#🚀 使用 Stream API 实现相同逻辑)
- [📘 和 SQL 的类比更清晰](#📘 和 SQL 的类比更清晰)
- [🛠️ 额外练习(可课堂互动)](#🛠️ 额外练习(可课堂互动))
- [✨ 小结:Map-Filter-Reduce 模型优势](#✨ 小结:Map-Filter-Reduce 模型优势)
269. Java Stream API - Map-Filter-Reduce算法模型
在深入学习 Java Stream API 之前,我们先来了解它背后的经典思想:Map - Filter - Reduce 算法模型。
这是一种非常通用且高效的数据处理模式,特别适合用在数据转换、筛选与聚合的场景中 ------ 类似数据库中的查询操作。
🧾 示例背景:计算十月销售总额
我们有一个简单的 Sale 类,记录了某个商品在某一天的销售额。为了代码简洁,我们使用 Java 14+ 引入的 Record 类型来定义它:
java
public record Sale(String product, LocalDate date, int amount) {
// 自动生成构造方法、访问器、equals、hashCode、toString
}
然后我们构造一个销售记录列表:
java
List<Sale> sales = List.of(
new Sale("Orange", LocalDate.of(2022, Month.JANUARY, 2), 4),
new Sale("Pumpkin", LocalDate.of(2022, Month.OCTOBER, 18), 12),
new Sale("Butternut", LocalDate.of(2022, Month.OCTOBER, 3), 6),
new Sale("Apple", LocalDate.of(2022, Month.AUGUST, 28), 3)
);
🧮 用传统方式求出十月的销售总额
java
int amountSoldInOctober = 0;
for (Sale sale : sales) {
if (sale.date().getMonth() == Month.OCTOBER) { // 筛选条件
amountSoldInOctober += sale.amount(); // 累加金额
}
}
System.out.println("Amount sold in October: " + amountSoldInOctober);
✅ 输出:
java
Amount sold in October: 18
🧠 拆解这个处理过程:Map - Filter - Reduce
这个例子其实包含了我们处理数据时常见的三步流程:
| 步骤 | 名称 | 动作描述 |
|---|---|---|
| 第一步 | Filter | 筛选出日期在十月的销售记录 |
| 第二步 | Map | 从每个 Sale 对象中提取出 amount |
| 第三步 | Reduce | 把所有 amount 相加,得到总销售额 |
🎯 总结一句话:从集合中找出需要的对象 → 转换成数值 → 聚合为一个结果
🚀 使用 Stream API 实现相同逻辑
java
int amountSoldInOctober = sales.stream()
.filter(sale -> sale.date().getMonth() == Month.OCTOBER) // Filter
.mapToInt(Sale::amount) // Map to int
.sum(); // Reduce
System.out.println("Amount sold in October: " + amountSoldInOctober);
📌
.mapToInt()是将对象转换成int类型流,便于后续的.sum()操作。
📘 和 SQL 的类比更清晰
你可以把这段逻辑类比成如下 SQL 查询:
java
SELECT SUM(amount)
FROM Sales
WHERE EXTRACT(MONTH FROM date) = 10;
这样学员能快速对照记忆 Stream 的每一步,特别适合有 SQL 背景的同学。
🛠️ 额外练习(可课堂互动)
- 计算销售总额大于
5的记录数量 - 统计每个月份的总销售额(用
Collectors.groupingBy) - 找出金额最大的销售记录(用
.max())
✨ 小结:Map-Filter-Reduce 模型优势
- ✅ 结构清晰,便于组合操作
- ✅ 适用于大多数数据处理任务
- ✅ 与
SQL思维接近,上手快 - ✅ 可与
Lambda表达式无缝结合,实现函数式风格