Optional 详解
程序员文章站
2022-03-04 11:49:20
...
目录
5、map、flatMap:以不解包的方式组合两个 Optional 对象
Java 8 实战:用 Optional 取代 null
-
Optional类设计时没考虑将其作为类的字段使用,所以并未实现 Serializable接口,因此如果应用使用了某些要求序列化的库或者框架,在域模型中使用Optional,有可能引发应用程序故障
-
可以将Optional看成最多包含一个元素的Stream对象
-
可用返回Optional对象的方式替换包装返回null、抛异常的方法
-
不推荐使用基础类型的Optional,因为基础类型的Optional不支持map、flatMap以及filter方法
1、创建 Optional 对象
Optional<T> opt=Optional.empty(); // 返回空Optional
Optional<T> opt=Optional.of(value); // value不可为null,否则抛异常
Optional<T> opt=Optional.ofNullable(value) // value可为null
例子:Person、Car、Insurance
public class Person {
private Optional<Car> car;
public Optional<Car> getCar() { return car; }
}
public class Car {
private Optional<Insurance> insurance;
public Optional<Insurance> getInsurance() { return insurance; }
}
public class Insurance {
private String name;
public String getName() { return name; }
}
2、map 从Optional中提取、转换值
Optional<Insurance> optInsurance = Optional.ofNullable(insurance);
Optional<String> name = optInsurance.map(Insurance::getName); // optInsurance非null时返回其name,否则返回不包含值的Optional<String>类型对象
3、flatMap 链接 Optional 对象
public String getCarInsuranceName(Optional<Person> person) {
return person.flatMap(Person::getCar) // Person -> Optional<Car> 直接返回
.flatMap(Car::getInsurance) // Car -> Optional<Insurance> 直接返回
.map(Insurance::getName) // Insurance -> String 打包为 Optional<String> 返回
.orElse("Unknown"); // 当调用链路上任何一个方法返回空Optional时,返回默认值“Unkonwn”
}
4、读取 Optional 实例中的变量值
get(); // 不安全,值不存在时会抛异常
orElse(); // 值不存在时可提供默认值(已经创建好的默认值)
orElseGet(); // 值不存在时才创建默认值
orElseThrow(); // 值不存在时抛异常,可定制异常类型
ifPresent(); // 值存在时才执行入参提供的方法
5、map、flatMap:以不解包的方式组合两个 Optional 对象
Public Optional<Insurance> nullSafeFindCheapestInsurance(Optional<Person> person,Optional<Car> car){
return person.flatMap(p->car.map(c->findCheapestInsurance(p,c)));
} // person 为空时,p->() 语句不会执行,函数返回空Optional,person 非空时 p->() 语句返回 Optional<Insurance> ;
// car 为空时 c->()返回空Optional,函数返回空Optional,car和person都非空时,函数调用findCheapestInsurance返回 Optional<Insurance>
6、filter:剔除特定值
Optional<Insurance> optInsurance = ...;
optInsurance.filter(insurance ->"CambridgeInsurance".equals(insurance.getName())) // filter 返回满足条件的 Optional
.ifPresent(x -> System.out.println("ok"));
Optional 源码
public final class Optional<T> {
private static final Optional<?> EMPTY = new Optional<>(); // 创建空 Optional 对象
private final T value; // value==null 时表示不存在value
private Optional() { this.value = null;} // 内部调用的构造器
private Optional(T value) { this.value = Objects.requireNonNull(value);} // 内部调用的构造器,value为null时抛NullPointerException
// public
public static<T> Optional<T> empty() { // 返回空Optional实例
@SuppressWarnings("unchecked")
Optional<T> t = (Optional<T>) EMPTY;
return t;
}
public static <T> Optional<T> of(T value) { // 返回指定value的Optional对象,value为null时抛NullPointerException异常(用非空value创建Optional)
return new Optional<>(value);
}
public static <T> Optional<T> ofNullable(T value) { // value非空时返回包含value的Optional对象,否则返回空Optional对象(允许用空值创建Optional)
return value == null ? empty() : of(value);
}
public T get() { // Optional中包含非空value时返回value,否则抛NoSuchElementException异常
if (value == null) {
throw new NoSuchElementException("No value present");
}
return value;
}
public boolean isPresent() { // Optional实例中存在非空value时返回true
return value != null;
}
public void ifPresent(Consumer<? super T> consumer) { // value非空时触发入参consumer指定的操作
if (value != null)
consumer.accept(value);
}
public Optional<T> filter(Predicate<? super T> predicate) { // value不为空且符合predicate条件时,返回包含此value的Optional实例,否则返回空Optional
Objects.requireNonNull(predicate);
if (!isPresent())
return this; // value为空返回空Optional本身
else
return predicate.test(value) ? this : empty();
}
// 可用于对optional实例的后处理,无须显式检查返回值的状态
public<U> Optional<U> map(Function<? super T, ? extends U> mapper) { // value非空时,对其应用mapper映射,返回value映射结果的Optional实例
Objects.requireNonNull(mapper);
if (!isPresent())
return empty();
else {
return Optional.ofNullable(mapper.apply(value)); // T->U:apply返回的U会被打包为Optional<U>,作为map的返回值
}
}
// 类似于map,但入参mapper的返回已经是Optional类型,触发flatMap中的apply操作时,无须再将其打包为Optional
public<U> Optional<U> flatMap(Function<? super T, Optional<U>> mapper) { // value非空时返回其映射后的值,否则返回空Optional
Objects.requireNonNull(mapper);
if (!isPresent())
return empty();
else {
return Objects.requireNonNull(mapper.apply(value)); // T->Optional<U>:apply返回的就是Optional<U>,flatMap无须打包直接返回
}
}
public T orElse(T other) { // value非空时返回value,否则返回other
return value != null ? value : other;
}
public T orElseGet(Supplier<? extends T> other) { // value非空时返回value,否则返回other
return value != null ? value : other.get();
}
public <X extends Throwable> T orElseThrow(Supplier<? extends X> exceptionSupplier) throws X { // value非空时返回value,否则抛出入参提供的异常
if (value != null) {
return value;
} else {
throw exceptionSupplier.get();
}
}
上一篇: Optional详解