Optional
1.简介
java.util.Optional<T>
Optional主要用作方法返回类型,其中明确需要表示“无结果”,并且使用null可能导致错误。 类型为Optional变量本身不应该是null ; 它应始终指向Optional实例
注意:这是一个`value-based`类; 在`Optional`实例上使用身份敏感操作(包括引用相等( `==` ),标识哈希码或同步)可能会产生不可预测的结果,应该避免使用。
2.方法(来源于Jdk11开发文档)
3.常用方法demo演示
get()
如果存在值,则返回该值,否则抛出 NoSuchElementException。
使用方式可往下看其他方法的输出方式
of()
此处不能传入对象为null的数据,如果user为null的话会报空指针异常,如果传入的是一个""空字符串的话不会报错,不过输出内容什么都没有。
User user = new User();
Optional<User> result = Optional.of(user);
System.out.println(result.get());
输出结果:User(name=null, sex=null, time=null)
ofNullable()
返回描述给定值的 Optional ,如果 null ,否则返回空的 Optional,此时不能进行.get()操作。
User user = new User();
Optional<User> result = Optional.ofNullable(user);
System.out.println(result.get());
输出结果:User(name=null, sex=null, time=null)
isPresent()
如果存在值,则返回 true ,否则返回 false 。
User user = new User();
Optional<User> optional = Optional.ofNullable(user);
System.out.println(optional.isPresent());
输出结果:true
isEmpty()-->JDK11出现
如果值不存在,则返回 true ,否则返回 false 。
User user = new User();
user = null;
Optional<User> optional = Optional.ofNullable(user);
System.out.println(optional.isEmpty());
输出结果:true
ifPresent()
如果存在值,则使用值执行给定操作,否则不执行任何操作,如果下面给user赋值为null的话,下面则不会执行输出语句,也不会报错,输出内容什么都没有
User user = new User();
Optional<User> optional = Optional.ofNullable(user);
optional.ifPresent(e-> System.out.println("user"));
输出结果:user
ifPresentOrElse()-->JDK9出现
如果存在值,则使用值执行给定操作,否则执行给定的基于空的操作
User user = new User();
Optional<User> optional = Optional.ofNullable(user);
optional.ifPresentOrElse( x -> System.out.println("Value: " + x),() -> System.out.println("Not Present."));
optional = Optional.empty(); // 给optional对象赋空值
optional.ifPresentOrElse( x -> System.out.println("Value: " + x),() -> System.out.println("Not Present"));
输出结果:
Value: 1
Not Present
filter()
如果存在值,并且值与给定的词匹配,则返回描述该值的 Optional ,否则返回空 Optional 。
User user = new User().setName("aaa");
Optional<User> optional = Optional.ofNullable(user);
optional.filter(e->"aaa".equals(e.getName())).ifPresent(e-> System.out.println("aaa"));
输出结果:aaa
User user = new User().setName("aaa");
Optional<User> optional = Optional.ofNullable(user);
optional.filter(e->"bbb".equals(e.getName())).ifPresent(e-> System.out.println("aaa"));
输出结果:
其实就是结果啥都没有,有疑问可往上看ifPresent()方法
map()
如果值存在时,返回一个Optional描述(仿佛由ofNullable(T)(ofNullable(T)) )将所述给定的映射函数的值的结果,否则返回一个空Optional 。如果映射函数返回null结果,则此方法返回空Optional 。
User user = new User().setName("aaa");
Optional<User> optional = Optional.ofNullable(user);
System.out.println(optional.map(User::getName).get());
输出结果:aaa
flatMap()
如果存在值,则返回将给定的Optional mapping函数应用于该值的结果,否则返回空Optional 。
User user = new User().setName("aaa");
Optional<User> optional = Optional.ofNullable(user);
Optional<String> user1 = optional.flatMap(e -> Optional.ofNullable(e.getName()));
System.out.println(user1.get());
输出结果:aaa
User user = new User().setName("aaa");
Optional<User> optional = Optional.ofNullable(user);
Optional<String> user1 = optional.flatMap(e -> Optional.ofNullable(e.getSex()));
System.out.println(user1);//此处没有进行.get()方法,因为sex属性没有设置值,所以调用.get()方法会报错。有疑问可往上看ofNullable()方法
输出结果:Optional.empty
orElse()
如果存在值,则返回该值,否则返回 other.
User user = new User().setName("aaa");
Optional<User> optional = Optional.ofNullable(user);
System.out.println(optional.orElse(new User().setSex("男")));
输出结果:User(name=aaa, sex=null, time=null)
User user = new User().setName("aaa");
Optional<User> optional = Optional.ofNullable(user);
optional = Optional.empty();
System.out.println(optional.orElse(new User().setSex("男")));
输出结果:User(name=null, sex=男, time=null)
orElseGet()
如果存在值,则返回该值,否则返回由供应函数生成的结果。
User user = new User().setName("aaa");
Optional<User> optional = Optional.ofNullable(user);
User user1 = optional.orElseGet(() -> new User().setName("sss"));
System.out.println(user1);
输出结果:User(name=aaa, sex=null, time=null)
User user = new User().setName("aaa");
user = null;
Optional<User> optional = Optional.ofNullable(user);
User user1 = optional.orElseGet(() -> new User().setName("sss"));
System.out.println(user1);
输出结果:User(name=sss, sex=null, time=null)
orElseThrow()
如果存在值,则返回该值,否则抛出 NoSuchElementException。
User user = new User().setName("aaa");
Optional<User> optional = Optional.ofNullable(user);
User user1 = optional.orElseThrow(RuntimeException::new);
System.out.println(user1);
输出结果:User(name=aaa, sex=null, time=null)
User user = new User().setName("aaa");
user = null;
Optional<User> optional = Optional.ofNullable(user);
User user1 = optional.orElseThrow(RuntimeException::new);
System.out.println(user1);
结果:抛异常:RuntimeException
好了,大致就这些方法吧,还有一些其他的方法大家可自行前去尝试,下面有一些建议及优化案例
4.建议
1.尽量不要去使用Optional的get()方法
因为null或者是空的Optional对象调用.get()方法都会抛异常
改之前:
User user = new User().setName("aaa");
//user = null; 这里如果user为null的话,输出语句中的.get()方法就会报错~
Optional<User> optional = Optional.ofNullable(user);
System.out.println(optional.get() == null ? "name" : optional.get().getName());
改之后:
User user = new User().setName("aaa");
user = null;
Optional<User> optional = Optional.ofNullable(user);
System.out.println(optional.map(User::getName).orElse("name"));
2.尽量使用ofNullable()方法而不去用of()方法
因为当前面的对象为null的时候of方法调用会报错,使用ofNullable()方法的时候即使前面user对象为null,后面也会返回一个空的Optional对象而不是null。下面我们看代码输出结果吧!
of()方法
User user = new User().setName("aaa");
user = null;
Optional<User> optional = Optional.of(user);// 报错位置在这一行
System.out.println(optional);
运行结果:NullPointerException
ofNullable()方法
User user = new User().setName("aaa");
user = null;
Optional<User> optional = Optional.ofNullable(user);
System.out.println(optional.map(User::getName));
输出结果:Optional.empty
此时并没有报错,然后我们可以继续优化,加上orElse()方法预留替补方案
User user = new User().setName("aaa");
user = null;
Optional<User> optional = Optional.ofNullable(user);
System.out.println(optional.map(User::getName).orElse("sss"));
输出结果:sss
if嵌套代码优化demo
优化前
User user = new User().setName("aaa");
user.setPerson(new Person().setAge("25").setCat(new Cat().setCatName("小猫咪")));
if (Objects.nonNull(user)){
Person person = user.getPerson();
if (Objects.nonNull(person)){
Cat cat = person.getCat();
if (Objects.nonNull(cat)){
System.out.println(cat.getCatName());
}
}
}
优化后
User user = new User().setName("aaa");
user.setPerson(new Person().setAge("25").setCat(new Cat().setCatName("小猫咪")));
String catName = Optional.ofNullable(user)
.flatMap(user1 -> Optional.ofNullable(user1.getPerson()))
.flatMap(person -> Optional.ofNullable(person.getCat()))
.flatMap(cat -> Optional.ofNullable(cat.getCatName()))
.orElse("");
System.out.println(catName);