Optional简化空值判断,减少代码中的if-else代码块

为了防止空指针异常的出现,Java8中引入了一个新类Optional,对于它之前我们已经进行了简单的实现。其本质就是通过Optional类对值进行封装, 当有值的时候,会把该值封装到Optional类中。如果没有值的话,则会在该类封装一个Empty

创建Optional对象

//empty()会直接返回一个空的Optional实例,内部不会存在任何值。
Optional<Student> studentOptional = Optional.empty();

//of()会返回一个存在值的Optional对象,并且该值不允许null的存在。如果调用该方法时传入参数是null,则立刻抛出NullPointerException,而不是等到你用这个对象时才抛出,相当于进行了立即检查。
Optional<Student> studentOptional = Optional.of(student);

//ofNullable()同样也会返回一个存在值的Optional对象,但是它和of()最大的不同在于,它会对传入的值进行判断,如果传入的值为null,其会调用empty()返回一个不包含内容的Optional,如果不为null,则会调用of()返回一个包含内容的Optional
Optional<Student> studentOptional = Optional.ofNullable(student);

isPresent()与ifPresent()应用

public class PresentDemo {
    public static void getStudentName(Student student){
        Optional<Student> studentOptional = Optional.ofNullable(student);
		//isPresent()只会单纯做判断
        if (studentOptional.isPresent()){
//存在
            System.out.println("student存在");
        }else {
            System.out.println("student不存在");
        }
//该方法在执行时,接收一个consumer函数式接口,如果value不为null,则通过consumer中的accept方法获取该值。
        studentOptional.ifPresent((x)-> System.out.println("存在"));

    }
    public static void main(String[] args) {
        Student student = new Student();
        getStudentName(student);
    }
}

get()与orElseThrow()应用

get()的使用非常简单,但不安全,因为其在获取值的时候,如果值存在,则直接返回封装在Optional中的值,如果不存在,则抛出NoSuchElementException。因此它的使用前提是已经确定Optional中有值,否则没有使用意义。

orElseThrow()当Optional中没有值时,get()会直接抛出NoSuchElementException,这样的话,就存在了一定的局限性,因为有时可能需要抛出自定义异常。此时就可以使用orElseThrow(),它在取值时,如果Optional中没有值时,可以抛出自定义异常。

public class MyException extends Throwable {
public MyException() {
super();
}
public MyException(String message) {
super(message);
}
@Override
public String getMessage() {
return "exception message";
}
}
public class OrElseThrowDemo {
public static void getStudentInfo(Student student) {
Optional<Student> studentOptional = Optional.ofNullable(student);
try {
Student student1 = studentOptional.orElseThrow(MyException::new);
} catch (MyException e) {
e.printStackTrace();
}
}
public static void main(String[] args) {
Student student = null;
getStudentInfo(student);
}
}

map()与flatMap()应用

//map的作用就是直接取值
if (studentOptional.isPresent()){
Optional<String> nameOptional = studentOptional.map(Student::getName);
}

在学生类中加新的属性

//Student类添加Job属性
private Optional<Job> job;
//Job类添加Company属性
private Optional<ComPany> comPany;

如果想拿到上述的值,通过连环的map是拿不到的,因为每一次在调用的时候,都会对Optional的泛型进行改变,最终产生多层Optional嵌套的结构,这时就需要用到flatMap()

Optional<String> nameOptional =
studentOptional.flatMap(Student::getJob).flatMap(Job::getCompany).map(Company::getName);

filter()应用

对应着以前使用的equals方法,就是匹配

//传统写法
Company company = optional().get();
if("test".equals(company.getName)){
sout(company);


Optional<Company> company = companyOptional.filter(c ‐> "test".equals(c.getName()));
}

orElse()与orElseGet()应用

在取值的时候,如果值不存在,有时我们会考虑返回一个默认值。该需求就可以通过orElse()实现。其内部会判断值是否为null,如果不为null,则返回该值,如果为null,则返回传入的默认值。
orElseGet()也是用于当Optional中没有值时,返回默认值的方法。但是它与orElse()的区别在于,它是延迟加载的。只有当Optional中没有值是才会被调用。

public class Demo1 {
public static void getCompanyName(Student student) {
Optional<Student> studentOptional = Optional.ofNullable(student);
if (studentOptional.isPresent()) {
String value1 =
studentOptional.flatMap(Student::getJob).flatMap(Job::getCompany).map(Company::getName).orElse(g
et("a"));
String value2 =
studentOptional.flatMap(Student::getJob).flatMap(Job::getCompany).map(Company::getName).orElseGe
t(()>get("b"));
System.out.println("a: "+value1);
System.out.println("b: "+value2);
}
}
public static String get(String name) {
System.out.println(name + "执行了方法");
return "exec";
}
public static void main(String[] args) {
Company company = new Company();
//company.setName("test");
Optional<Company> companyOptional = Optional.of(company);
Job job = new Job();
job.setName("pm");
job.setCompany(companyOptional);
Optional<Job> jobOptional = Optional.of(job);
Student s1 = new Student();
s1.setName("张三");
s1.setJob(jobOptional);
getCompanyName(s1);
}
}
a执行了方法
b执行了方法
a: exec
b: exec
public class Demo1 {
public static void getCompanyName(Student student) {
Optional<Student> studentOptional = Optional.ofNullable(student);
if (studentOptional.isPresent()) {
String value1 =
studentOptional.flatMap(Student::getJob).flatMap(Job::getCompany).map(Company::getName).orElse(g
et("a"));
String value2 =
studentOptional.flatMap(Student::getJob).flatMap(Job::getCompany).map(Company::getName).orElseGe
t(()>get("b"));
System.out.println("a: "+value1);
System.out.println("b: "+value2);
}
}
public static String get(String name) {
System.out.println(name + "执行了方法");
return "exec";
}
public static void main(String[] args) {
Company company = new Company();
company.setName("test");
Optional<Company> companyOptional = Optional.of(company);
Job job = new Job();
job.setName("pm");
job.setCompany(companyOptional);
Optional<Job> jobOptional = Optional.of(job);
Student s1 = new Student();
s1.setName("张三");
s1.setJob(jobOptional);
getCompanyName(s1);
}
}
a执行了方法
a: test
b: test
已标记关键词 清除标记
©️2020 CSDN 皮肤主题: 游动-白 设计师:上身试试 返回首页