jdk1.8 -- optional 的使用
一.optional的介绍
Optional 是个容器:它可以保存类型T的值,或者仅仅保存null。Optional提供很多有用的方法,这样我们就不用显式进行空值检测。
Optional 类的引入很好的解决空指针异常。

本文将从三方面来讲解optional:
1.Optional的构建
2.Optional的获取
3.Optional的复合操作
下面先讲解在没有Optional之前我们是如何对null值进行判断的
class Persion{
private Car car;
public Car getCar() {
return this.car;
}
}
class Car{
private Brand insurance;
public Brand getInsurance() {
return this.insurance;
}
}
class Brand {
private String name;
public String getName() {
return this.name;
}
}
public class BeforeOptional {
public static void main(String[] args) {
getBrandName(new Persion());
getBrandNameDefault(new Persion());
}
private static String getBrandName(Persion persion) {
if(null !=persion.getCar()) {
Car car = persion.getCar();
if(null !=car.getInsurance()) {
Brand insurance = car.getInsurance();
if(null !=insurance.getName()) {
return insurance.getName();
}
}
}
return "";
}
private static String getBrandNameDefault(Persion persion) {
String defaultValue = "UNKNOW";
if(null ==persion)
return defaultValue;
Car car = persion.getCar();
if(null == car)
return defaultValue;
Brand insurance = car.getInsurance();
if(null == insurance)
return defaultValue;
return insurance.getName();
}
}
显然,我们需要通过代码来硬编码实现对象引用变量的判断
二.Optional API的操作
//********************** 1. Optional 的构建**********************
//1.1创建一个空的optional(内部new了一个空的optional),不支持get方法,会报异常NoSuchElementException
Optional<Brand> empty = Optional.<Brand>empty();
empty.get();
//1.2创建一个optional,传入的值不能为null,返回Optional<Object>,为null时会报NullPointerException
Optional<Brand> of = Optional.of(new Brand());
System.out.println(of.get());
//1.3创建一个可空可有的optional,对前2种的总结(如果传null,走empty方法,非null,走of方法)
Optional<Brand> brand = Optional.ofNullable(new Brand());
Optional<Object> ofNullable2 = Optional.ofNullable(null);
//********************** 2. Optional 的获取操作**********************
//2.1 如果当前有值,返回这个值,否则报NoSuchElementException("No value present");
brand.get();
//2.2 如果有值,会传出insurance实例,如果没值,会给出传入的参数;(参数是supplier)
brand.orElseGet(Brand::new);
//2.3 如果有值,会传出insurance实例,如果没值,会给出传入的参数;(参数是Insurance 实例)
brand.orElse(new Brand());
//2.4 如果有值,会传出insurance实例,如果没值,可以抛出异常
brand.orElseThrow(RuntimeException::new);
brand.orElseThrow(()->new RuntimeException("not have reference"));
//********************** 3. Optional 的复合操作**********************
//3.1 返回一个boolean值
brand.isPresent();
//3.2 如果有值,有值时可以进行操作(consumer操作)
brand.ifPresent(System.out::println);
//3.3 filter操作,它会通过predicate操作,对brand 以及表达式进行非空的验证,通过后,方能得到结果
brand.filter(b->b.getName() == null).get();
//3.4 map操作:同filter,不同之处在于map会改变get到的类型
brand.map(b->b.getName()).get();
//3.5 flatMap 得到复合操作后的Optional<flatMap参数得到的值的optional>
Optional<Per> per = Optional.ofNullable(new Per());
Optional<Optional<Car2>> map = per.map(Per::getCar); //这个是对Optional<optional<Car2>进行了再一次的封装
Optional<Car2> flatMap = per.flatMap(Per::getCar); //这个得到的还是原来的Optional<Object>
我们回过头来解决开篇中的方法
class Persion2{
private Optional<Car2> car; //注意这里要加上Optional的改写
public Optional<Car2> getCar() {
return car;
}
}
class Car2{
private Optional<Brand2> Brand2; //注意这里要加上Optional的改写
public Optional<Brand2> getBrand2() {
return Brand2;
}
}
class Brand2{
private String name;
public String getName() {
return this.name;
}
}
public static String getInsuranceName(Persion2 per) {
return Optional.ofNullable(per).flatMap(Persion2::getCar).flatMap(Car2::getBrand2).map(b->b.getName()).orElse("Unknown"); //是不是一行代码就搞定了
}
jdk1.8 -- optional 的使用的更多相关文章
- JDK1.8新特性——Optional类
JDK1.8新特性——Optional类 摘要:本文主要学习了JDK1.8新增加的Optional类. 部分内容来自以下博客: https://www.cnblogs.com/1ning/p/9140 ...
- JDK1.8新特性之Optional
概念 Optional 是JDK1.8中出现的一个容器类,代表一个值存在或者不存在.原来使用null表示一个值不存在,现在Optional可以更好的表达这个概念.并且可以避免空指针异常. 场景分析 需 ...
- Linux配置JDK1.7和Resin4.0
1.安装JDK1.7 (1)下载 官网下载路径:http://www.oracle.com/technetwork/java/javase/downloads/jdk7-downloads-18802 ...
- JDK各个版本的新特性jdk1.5-jdk8
JDK各个版本的新特性 对于很多刚接触java语言的初学者来说,要了解一门语言,最好的方式就是要能从基础的版本进行了解,升级的过程,以及升级的新特性,这样才能循序渐进的学好一门语言.今天先为大家介绍一 ...
- JAVA 8 Optional类介绍及其源码
什么是Optional对象 Java 8中所谓的Optional对象,即一个容器对象,该对象可以包含一个null或非null值.如果该值不为null,则调用isPresent()方法将返回true,且 ...
- JAVA JDK1.5-1.9新特性
1.51.自动装箱与拆箱:2.枚举(常用来设计单例模式)3.静态导入4.可变参数5.内省 1.61.Web服务元数据2.脚本语言支持3.JTable的排序和过滤4.更简单,更强大的JAX-WS5.轻量 ...
- jdk各个版本的新特性(jdk1.7,1.8,1.9)
用了这么久的jdk,应该会有很多人和我一样,不知道各个版本的jdk的一些新特性,这里简单总结一下.. jdk1.7新特性: 1.在Switch中可以用String字符串 2.对Java集合(Colle ...
- 【新特性】JDK1.8
一.简介 毫无疑问,Java 8是Java自Java 5(发布于2004年)之后的最重要的版本.这个版本包含语言.编译器.库.工具和JVM等方面的十多个新特性.在本文中我们将学习这些新特性,并用实际的 ...
- 学习笔记 Optional
今天学习到的一种新的防止空指针的方法下面是我自己写的一个例子:节省空间,bean的get set 省略... /** * 类目 * @author 唐 * @date 2018/5/6 17:45 * ...
随机推荐
- 014_STM32程序移植之_L298N电机驱动模块
更改注意: STM32程序移植之L298N电机驱动模块 引脚连接图 STM32引脚 L298N引脚 功能 PA6 ENA 马达A的PWM PA7 ENB 马达B的PWM PA2 IN1 控制马达A P ...
- Oracle 体系结构图
Oracle体系结构图 详细图
- GitHub 更新fork的代码
转载地址:http://blog.csdn.net/do_it__/article/details/7836513 一.前提 本文的前提是你已经在github上fork了别人的分支,并且弄好了跟git ...
- idea快捷方式2
IntelliJ Idea 常用快捷键列表 Ctrl+Shift + Enter,语句完成“!”,否定完成,输入表达式时按 “!”键Ctrl+E,最近的文件Ctrl+Shift+E,最近更改的文件Sh ...
- SQL SERVER可重复执行建表、建字段语句
/*问题:type in (N'U') 中的N和U是什么意思? 答案:N是指Unicode编码,防止乱码:U是指用户表*/IF NOT EXISTS (SELECT * FROM sys.object ...
- PHP 之实现按日期进行分组、分页
一.效果图 二.原始数据 array(6) { [0]=> array(8) { ["id"]=> string(1) "6" ["use ...
- 一个 TCP 连接可以发多少个 HTTP 请求
第一个问题 第二个问题 第三个问题 第四个问题 第五个问题 曾经有这么一道面试题:从 URL 在浏览器被被输入到页面展现的过程中发生了什么? 相信大多数准备过的同学都能回答出来,但是如果继续问:收到的 ...
- cxf报错 Cannot find any registered HttpDestinationFactory from the Bus.
错误信息:Cannot find any registered HttpDestinationFactory from the Bus. 报错主要是因为缺少jetty依赖 一般添加如下依赖即可 < ...
- matplotlib画图报错This figure includes Axes that are not compatible with tight_layout, so results might be incorrect.
之前用以下代码将实验结果用matplotlib show出来 plt.plot(np.arange(len(aver_reward_list)), aver_reward_list) plt.ylab ...
- android: Android 权限管理小结
一. 概述 感谢郭神,自从Android6.0发布以来,在权限上做出了很大的变动,不再是之前的只要在manifest设置就可以任意获取权限,而是更加的注重用户的隐私和体验,不会再强迫用户因拒绝不该拥有 ...