好的阿杰,我给你做一个 通俗易懂、系统化的 Java Optional
教程,包括理解、学习和实际使用场景。
1️⃣ 什么是 Optional
Optional
是 Java 8 引入的一个容器类,用于防止 NullPointerException(NPE)。
核心思想:
- 让返回值显式地表示可能为空
- 避免
if (obj != null)
的繁琐判断 - 提高代码可读性与安全性
本质:Optional<T>
可以包含一个类型为 T 的对象,或者什么都不包含(empty)。
2️⃣ 创建 Optional 对象
import java.util.Optional;
public class OptionalDemo {
public static void main(String[] args) {
// 1. 创建空的 Optional
Optional<String> emptyOpt = Optional.empty();
// 2. 创建非空 Optional(如果传入 null,会抛异常)
Optional<String> nameOpt = Optional.of("阿杰");
// 3. 可空 Optional(可以为 null,不会抛异常)
Optional<String> nullableOpt = Optional.ofNullable(null);
}
}
3️⃣ 获取值的方法
1. get()
- 获取值,如果为空会抛
NoSuchElementException
String name = nameOpt.get(); // 阿杰
2. orElse()
- 如果值为空,返回默认值
String name = emptyOpt.orElse("默认值"); // 默认值
3. orElseGet()
- 懒加载默认值,用 Supplier 提供
String name = emptyOpt.orElseGet(() -> "懒加载默认值");
4. orElseThrow()
- 值为空时抛异常
String name = emptyOpt.orElseThrow(() -> new IllegalArgumentException("值不能为空"));
4️⃣ 判断 Optional 是否有值
if (nameOpt.isPresent()) {
System.out.println(nameOpt.get());
}
// Java 11 之后,可使用 ifPresentOrElse
nameOpt.ifPresentOrElse(
val -> System.out.println(val),
() -> System.out.println("值为空")
);
5️⃣ 常用组合操作
1. map()
- 对 Optional 中的值进行转换
Optional<Integer> length = nameOpt.map(String::length);
System.out.println(length.get()); // 2 (阿杰长度)
2. flatMap()
- 避免嵌套 Optional
Optional<Optional<String>> nestedOpt = Optional.of(Optional.of("阿杰"));
Optional<String> flat = nestedOpt.flatMap(o -> o);
3. filter()
- 根据条件过滤值
Optional<String> filtered = nameOpt.filter(s -> s.startsWith("阿"));
System.out.println(filtered.isPresent()); // true
6️⃣ 使用 Optional 的最佳实践
- 返回值使用 Optional
public Optional<User> findUserById(String id) { ... }
- 方法参数不要使用 Optional
// ❌ 不推荐
public void updateUser(Optional<User> user) { ... }
- 避免 overuse
- Optional 并不能替代所有 null
- 对于集合、数组等推荐直接返回空集合,而不是 Optional
- 链式调用
String city = userOpt
.map(User::getAddress)
.map(Address::getCity)
.orElse("未知城市");
7️⃣ Optional 的价值总结
特点 | 说明 |
---|---|
防止 NPE | 让空值显式化 |
提升可读性 | 链式调用代替 if (obj != null) |
函数式风格 | map / flatMap / filter 支持函数式编程 |
增强安全性 | 提醒调用者处理空值 |
发表回复