第七章:用Optional取代null
7.1 如何为缺失的值建模
假如你需要你需要处理下面的嵌套对象
static class Person { private Car car; public Car getCar() { return car; } } class Car { private Insurance insurance; public Insurance getInsurance() { return insurance; } } class Insurance { private String name; public String getName() { return name; } }
那么下面的代码存在什么问题呢?
public static String getCarInsuranceName(Person person) { return person.getCar().getInsurance().getName(); }
这段代码看上去正常,可很容易报NullPointerException导致程序的运行终止。
解决方案:
采用防御式检查减少NullPointerException
public static String getCarInsuranceName(Person person) { if(person != null) { Car car = person.getCar(); if(car != null) { Insurance insurance = car.getInsurance(); if(insurance != null) { return insurance.getName(); } } } return "Unknown"; }
7.2 Optional类入门
7.2.1 使用Optional重新定义的数据模型
static class Person { private Optional<Car> car; public Optional<Car> getCar() { return car; } } class Car { private Optional<Insurance> insurance; public Optional<Insurance> getInsurance() { return insurance; } } class Insurance { private Optional<String> name; public Optional<String> getName() { return name; } }
7.2.2 创建Optional对象
1. 声明一个空的Optional
Optional<Car> car = Optional.empty();
2. 根据一个非空值创建一个Optional
Optional<Car> notNullCarOptional = Optional.of(notNullCar);
3. 可接受null的Optional
Optional<Car> ofNullableCarOptional = Optional.ofNullable(ofNullableCar);
7.2.3 使用map从Optional对象中提取和转换值
Optional提供了一个map方法(将实体类还原到 7.1 节的数据模型)
public static String getCarInsuranceName(Person person) { // 创建一个可接受null的Optional Optional<Person> ofNullable = Optional.ofNullable(person); return ofNullable.map(Person::getCar) .map(Car::getInsurance) .map(Insurance::getName) .orElse("Unknown"); }
Optional提供了一个flatMap方法(将实体类还原到 7.2.1 节的数据模型)
public static String getCarInsuranceName(Person person) { // 创建一个可接受null的Optional Optional<Person> ofNullable = Optional.ofNullable(person); return ofNullable.flatMap(Person::getCar) .flatMap(Car::getInsurance) .flatMap(Insurance::getName) .orElse("Unknown"); }
7.3 Optional类中的方法
| 方法 | 描述 |
| empty | 返回一个空的Optional实例 |
| filter | 如果值存在并且满足提供的谓词,就返回包含该值的Optional对象,否则返回一个空的Optional对象 |
| flatMap | 如果值存在,就对该值执行提供的mapping函数调用,返回一个Optional类型的值,否则就返回一个空的Optional对象 |
| get | 如果该值存在,将该值用Optional封装返回,否则抛出一个NoSuchElementException异常 |
| ifPresent | 如果值存在,就执行使用该值的方法调用,否则什么也不做 |
| isPresent | 如果值存在就范湖true,否则返回false |
| map | 如果值存在,就对该值执行提供的mapping函数调用 |
| of | 将指定值用Optional封装之后返回,如果该值为null,则抛出异常 |
| ofNullable | 将指定值用Optional封装之后返回,如果该值为null,则返回一个空的Optional对象 |
| orElse | 如果有值则将其返回,否则返回一个默认值 |
| orElseGet | 如果有值则将其返回,否则返回一个由指定的Supplier接口生成的值 |
| orElseThrow | 如果有值则将其返回,否则抛出一个由指定的Supplier接口生成的异常 |
备注:
摘自文献:《Java8实战》(中文版)《Java8 in Action》(英文版)
代码(GitHub地址): https://github.com/changlezhong/java8InAction
posted on 2018-06-16 19:29 changlezhong 阅读(140) 评论(0) 收藏 举报
浙公网安备 33010602011771号