Stream API 提取对象字段的核心链式调用是 stream() → map() → collect(),替代传统 for 循环,代码更简洁、语义更清晰、易于组合;需确保字段有 public getter,推荐方法引用如 User::getName 和 Collectors.toList()。

用 Stream API 提取对象字段,核心就一条链式调用:stream() → map() → collect()。它替代了传统 for 循环 + new ArrayList() + add() 的冗长写法,代码更短、语义更清晰、也更容易组合条件和转换逻辑。
提取所有对象的指定字段
这是最常见场景:把 List
- 确保目标字段有 public getter 方法,例如
getName()或getId() - 用方法引用写法最简洁:
.map(User::getName),比.map(u -> u.getName())更安全、可读性更好 - 收集结果推荐
Collectors.toList(),返回的是标准 List;如需明确是 ArrayList,可用Collectors.toCollection(ArrayList::new)
示例:
List<String> names = users.stream()
.map(User::getName)
.collect(Collectors.toList());
按条件筛选后再提取字段
先过滤再取值,比如“年龄大于 25 的用户姓名”。
立即学习“Java免费学习笔记(深入)”;
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
- filter 放在 map 前面,避免对不满足条件的对象做无谓的 getter 调用
- filter 接收 Predicate,例如
u -> u.getAge() > 25或u -> "admin".equals(u.getRole()) - 若只要第一个匹配项的字段值,用
.findAny().map(User::getName).orElse(null),返回 Optional 更安全
示例(提取符合条件的姓名列表):
List<String> adminNames = users.stream()
.filter(u -> "admin".equals(u.getRole()))
.map(User::getName)
.collect(Collectors.toList());
提取多个字段并组装新结构
单个字段不够用?可以 map 成新对象,比如 DTO 或记录类(record)。
- 定义一个轻量级容器,如
record UserSummary(String name, int age) {} - 在 map 中构造它:
.map(u -> new UserSummary(u.getName(), u.getAge())) - 也可用数组或 Map 临时组合,但类型安全性低,不推荐长期维护
示例:
List<UserSummary> summaries = users.stream()
.map(u -> new UserSummary(u.getName(), u.getAge()))
.collect(Collectors.toList());
空值与异常防护要点
实际数据常含 null,不处理容易抛 NullPointerException。
- 如果 List 本身可能为 null,先判空:
if (users != null) { ... } - 如果 List 中元素可能为 null,加 filter 过滤:
.filter(Objects::nonNull) - 如果 getter 返回可能为 null(如 String 字段),map 内部可做非空判断或默认值处理:
.map(u -> Optional.ofNullable(u).map(User::getName).orElse("")) - 避免在 map 中调用可能抛异常的方法;如必须,应在外层 try-catch 或改用自定义 Function 封装
不复杂但容易忽略。

















