Optional 类
Java 8 引入了 Optional 类,用于解决可能出现的 NullPointerException 问题。Optional 是一个可以包含或不包含值的容器对象,这样在处理可能为空的对象时,可以显式地表示该对象是否有值,而不是直接使用 null。
1. Optional 的创建
可以通过几种方式创建 Optional 对象。
import java.util.Optional;
public class OptionalExample {
public static void main(String[] args) {
// 创建一个空的 Optional 对象
Optional<String> emptyOptional = Optional.empty(); // 空的 Optional 对象
// 通过非空值创建 Optional 对象
String name = "John";
Optional<String> optionalWithValue = Optional.of(name); // 包含值的 Optional 对象
// 通过可能为空的值创建 Optional 对象
String nullableName = null;
Optional<String> optionalWithNullable = Optional.ofNullable(nullableName); // 允许 null 的 Optional 对象
}
}
2. 检查值的存在
Optional 提供了多种方法来检查值是否存在。
import java.util.Optional;
public class OptionalCheckExample {
public static void main(String[] args) {
Optional<String> optional = Optional.of("Hello");
// isPresent: 检查值是否存在
if (optional.isPresent()) {
System.out.println("Value is present: " + optional.get()); // 如果值存在,获取并打印
}
// ifPresent: 如果值存在,执行指定操作
optional.ifPresent(value -> System.out.println("Value: " + value)); // 如果值存在,打印值
}
}
3. 获取值
Optional 提供了多种方式来获取值或提供默认值。
import java.util.Optional;
public class OptionalGetExample {
public static void main(String[] args) {
Optional<String> optional = Optional.ofNullable(null);
// get: 获取值,如果值不存在则抛出 NoSuchElementException
try {
String value = optional.get(); // 尝试获取值
} catch (Exception e) {
System.out.println("Exception: " + e.getMessage()); // 捕获并打印异常信息
}
// orElse: 如果值不存在,返回默认值
String defaultValue = optional.orElse("Default Value"); // 值不存在,返回默认值
System.out.println("Value: " + defaultValue);
// orElseGet: 如果值不存在,调用指定的 Supplier 接口来生成默认值
String valueOrElseGet = optional.orElseGet(() -> "Generated Value"); // 通过 Supplier 获取默认值
System.out.println("Value: " + valueOrElseGet);
// orElseThrow: 如果值不存在,抛出指定的异常
try {
String valueOrElseThrow = optional.orElseThrow(() -> new IllegalArgumentException("Value is absent"));
} catch (Exception e) {
System.out.println("Exception: " + e.getMessage()); // 捕获并打印异常信息
}
}
}
4. 转换值
Optional 提供了转换值的方法,例如 map 和 flatMap,可以在 Optional 对象上应用函数。
import java.util.Optional;
public class OptionalMapExample {
public static void main(String[] args) {
Optional<String> optional = Optional.of("Hello");
// map: 转换值
Optional<String> upperCaseOptional = optional.map(String::toUpperCase); // 将值转换为大写
System.out.println("Upper case value: " + upperCaseOptional.orElse("No value"));
// flatMap: 转换并返回 Optional 对象
Optional<Integer> lengthOptional = optional.flatMap(value -> Optional.of(value.length())); // 获取字符串的长度
System.out.println("Length: " + lengthOptional.orElse(0));
}
}
5. 过滤值
Optional 还提供了 filter 方法,可以根据指定的条件过滤值。
import java.util.Optional;
public class OptionalFilterExample {
public static void main(String[] args) {
Optional<String> optional = Optional.of("Hello");
// filter: 过滤值
Optional<String> filteredOptional = optional.filter(value -> value.startsWith("H")); // 检查值是否以 "H" 开头
System.out.println("Filtered value: " + filteredOptional.orElse("No match")); // 如果匹配,则返回值,否则返回默认值
}
}
6. 使用 Optional 作为方法返回值
将 Optional 作为方法的返回值,可以明确表示返回值可能为空,避免返回 null。
import java.util.Optional;
public class OptionalReturnExample {
public static void main(String[] args) {
Optional<String> name = findNameById(1);
// 检查值是否存在并处理
name.ifPresentOrElse(
value -> System.out.println("Name found: " + value), // 如果值存在,打印值
() -> System.out.println("Name not found") // 如果值不存在,打印信息
);
}
public static Optional<String> findNameById(int id) {
// 模拟根据 ID 查找名称
if (id == 1) {
return Optional.of("John"); // 返回包含值的 Optional
}
return Optional.empty(); // 返回空的 Optional
}
}
总结
Java 8 的 Optional 提供了一种优雅的方式来处理可能为 null 的值,避免 NullPointerException。通过合理使用 Optional,可以使代码更加健壮和易于维护。