orelseget比orelse更适合懒加载,因为orelse接收已计算值会立即执行,而orelseget接收supplier仅在optional为空时才调用get()生成默认值,避免无谓开销。

orElseGet 用 Supplier 实现懒加载,默认值只在 Optional 为空时才执行创建逻辑,避免无谓开销。
为什么 orElseGet 比 orElse 更适合懒加载
orElse 接收的是一个**已计算好的值**,无论 Optional 是否为空,该值都会被立即构造;而 orElseGet 接收的是一个 Supplier
例如:构建一个大对象、查数据库、读文件等耗时操作,放在 orElse 里会白白执行;放在 orElseGet 的 Supplier 中,就能真正“按需触发”。
基本用法:传入 Lambda 或方法引用
最常见写法是用 Lambda 表达式包装默认值的创建逻辑:
Optional<string> opt = Optional.empty(); String result = opt.orElseGet(() -> expensiveDefault()); </string>
也可以用方法引用(当已有现成方法时):
String result = opt.orElseGet(this::createDefault); // 或静态方法 String result = opt.orElseGet(Helper::getDefaultString);
Supplier 内部可做复杂逻辑,但不能抛受检异常
Supplier 的 get() 方法签名是 T get(),它不声明抛出任何异常。因此:
- 如果默认值创建过程可能抛出受检异常(如 IOException),需要在 Supplier 内部 捕获并处理或转为运行时异常;
- 可以安全使用 try-catch、日志、条件判断等;
- 不建议在 Supplier 中做阻塞或长时间操作(虽可行,但会拖慢调用方)。
对比 orElse 和 orElseGet 的实际效果
System.out.println("Start");
Optional<string> opt = Optional.of("hello");
// orElse:always prints "Creating default..."
String a = opt.orElse(createDefault()); // ← 立即执行
// orElseGet:no print, because opt is present
String b = opt.orElseGet(() -> createDefault()); // ← 不执行
static String createDefault() {
System.out.println("Creating default...");
return "default";
}
</string>
输出结果:
Start Creating default...
可见 orElse 强制触发,orElseGet 真正“懒”。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











