如何为对象链制作flatMap链?

时间:2019-06-10 09:31:49

标签: java java-8 optional flatmap

我的课堂定义如下。

Insurance.java

package Chapter10;

public class Insurance {

    private String name;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }
}

Car.java

package Chapter10;

import java.util.Optional;

public class Car {

    private Optional<Insurance> insurance;

    public Optional<Insurance> getInsurance() {
        return insurance;
    }

    public void setInsurance(Optional<Insurance> insurance) {
        this.insurance = insurance;
    }
}

Person.java

package Chapter10;

import java.util.Optional;

public class Person {

    private Optional<Car> car;

    public Optional<Car> getCar() {
        return car;
    }

    public void setCar(Optional<Car> car) {
        this.car = car;
    }
}

现在,我有下面的主类,但是我收到了NullPoinerException 为人p。

package Chapter10;

import java.util.Optional;

public class OptionalTester {

    public static String getCarInsuranceName(Optional<Person> person) {
        return person.flatMap(Person::getCar)
                .flatMap(Car::getInsurance)
                .map(Insurance::getName)
                .orElse("Unknown");
    }

    public static void main(String[] args) {

        Insurance iffco = new Insurance();
        iffco.setName("IFFCO TOKIO");

        Insurance argo = new Insurance();
        argo.setName("HDFC ARGO");

        Car i10 = new Car();
        i10.setInsurance(Optional.of(iffco));

        Car santro = new Car();

        Person p = new Person();
        p.setCar(Optional.of(santro));

        Person p1 = new Person();
        p1.setCar(Optional.of(i10));

        System.out.println("---------------FROM PERSON GET INSURANCE----------------------");

        Optional<Insurance> optInsurance = Optional.ofNullable(argo);
        Optional<String> name = optInsurance.map(Insurance::getName);


        System.out.println(getCarInsuranceName(Optional.of(p1)));
        System.out.println(getCarInsuranceName(Optional.of(p)));

    }
}

我在Optional.of(p)行中获得了NPE,我知道p1有一辆汽车,那辆汽车有保险,因此可以正常工作。

在p的情况下,没有保险,所以我得到了NPE。 但是,如果我使用Optional.empty()执行此操作,则可以正确获取 Unknown 作为输出。

如何更概括地说,如果发生任何问题,我会得到未知

3 个答案:

答案 0 :(得分:1)

基本上,简短的回答是“你不能”。原因是Optional应该是monad(一个高阶对象,可以使您将某些操作包装在一个特定的容器中,简称),但是在Java中则不是。因此,flatMap无法正确链接。对于更长的讨论,您可能希望查看https://www.sitepoint.com/how-optional-breaks-the-monad-laws-and-why-it-matters/

答案 1 :(得分:0)

在Santro中,汽车保险无效。

import java.util.Optional;

公共类OptionalTester {

public static String getCarInsuranceName(Optional<Person> person) {
    return person.flatMap(Person::getCar)
            .flatMap(Car::getInsurance)
            .map(Insurance::getName)
            .orElse("Unknown");
}

public static void main(String[] args) {

    Insurance iffco = new Insurance();
    iffco.setName("IFFCO TOKIO");

    Insurance argo = new Insurance();
    argo.setName("HDFC ARGO");

    Car i10 = new Car();
    i10.setInsurance(Optional.of(iffco));

    Car santro = new Car();
    santro.setInsurance(Optional.of(argo)); \\ Insurence was null.

    Person p = new Person();
    p.setCar(Optional.of(santro));

    Person p1 = new Person();
    p1.setCar(Optional.of(i10));

    System.out.println("---------------FROM PERSON GET INSURANCE----------------------");

    Optional<Insurance> optInsurance = Optional.ofNullable(argo);
    Optional<String> name = optInsurance.map(Insurance::getName);


    System.out.println(getCarInsuranceName(Optional.of(p1)));
    System.out.println(getCarInsuranceName(Optional.of(p)));

}

}

答案 2 :(得分:0)

换车应该可以。

公共课车{

    private Insurance insurance;

    public Optional<Insurance> getInsurance() {
       return Optional.ofNullable(insurance);
    }

    public void setInsurance(Optional<Insurance> insurance) {
        this.insurance = insurance.orElse(null);
    }
}