接上篇Guava之Joiner和Splitter,本篇将介绍Guava的另外一个有用的对象Optional,这在Java中Google Guava首先给我们提出可空对象模型的。在其他语言如c#这是已经存在很久的模式,并包含在.net类库中Nullable(Int?也是一个可空类型)。

Null sucks

回到本文主题Optional。在我日常编程中NullPointerException是肯定是大家遇见最多的异常错误:

为此Doug Lea曾说过:

Null sucks.

Sir C. A. R. Hoare也曾说过:

I call it my billion-dollar mistake.

从上面我们能够足以看出NullPointerExceptiond的出现频率和可恨之处。因此在GOF的设计模式中我们也专门提出了空对象模式(或称特例模式)来应对这可恶的NullPointerExceptiond。空对象模式主要以返回一些无意义并不影响处理逻辑的特定对象来替代null对象,从而避免没必要的null对象的判断。 例如在计算一组员工的总共薪资的时候,对于返回的null对象则我们可以返回默认值为了0薪资的员工对象,那么我们就不需要做任何null的判断。

员工薪资问题

那么在Guava的Optional又该怎么解决呢?在讲解Optional之前,让我们仍然以计算一组员工的总共薪资为例用原生java代码将来看看:

 
@Test
public void should_get_total_age_for_all_employees() throws Exception {
final List<Employee> list = Lists.newArrayList(new Employee("em1", 30), new Employee("em2", 40), null, new Employee("em4", 18));
int sum = 0;
for (Employee employee : list) {
if (employee != null) {
sum += employee.getAge();
}
}
System.out.println(sum);
}
private class Employee {
private final String name;
private final int age;
public Employee(String name, int age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public int getAge() {
return age;
}
}

如果换成Guava Optional将如何:

 
 @Test
public void should_get_total_age_for_all_employees() throws Exception {
final List<Employee> list = Lists.newArrayList(new Employee("em1", 30),
new Employee("em2", 40),
null,
new Employee("em4", 18));
int sum = 0;
for (Employee employee : list) {
sum += Optional.fromNullable(employee).or(new Employee("dummy", 0)).getAge();
}
System.out.println(sum);
}

从上面可以清晰看出,我们不在担心对象对空了,利用Optional的fromNullable创建了一个可空对象,并将其or上一个dummy的员工信息,所以在这里我们不在担心NullPointerExceptiond。

也许你会说和利用三目运算 ( _?:_)没什么差别,在此例子中功能是的确是没多大差距,但是个人觉得Guava更有语义,更通用一些,而且满足很多空对象模式使用的场景。

Optional API

*. OptionalObject.isPresent(): 返回对象是否有值。

*. Optional.absent(): 返回一个空Optional对象,isPresent() 将会返回false

*. Optional.of(): 创Optional对象,输入参数不能为null

*. Optional.fromNullable(): 创Optional对象,输入可以为null

*. OptionalObject.asSet(): 和Optional对象值合并,如果为null则返回size为0的Set

*. OptionalObject.or(): 和Optional对象值合并,如果为null为空加则返回or参数作为默认值

*. OptionalObject.orNull(): 和Optional对象值合并,如果为null为空加则返回Null作为默认值

上面的api都是我们在使用Optional的时候最常用的方法属性方法,注意如果我们创建了Optional对象,但是没有判断isPresent()是否存在,就直接get这是会抛异常的,这属于乱用Optional情况,和直接用Null并没什么差别。

 
final Optional<Object> obj = Optional.fromNullable(null);
final Object o = obj.get();

同样Optional为空对象模式,可以添加默认值,null不会影响我们的处理,如果为null我们无法继续程序处理的情况,需要抛异常或者中断的的,还是需要抛异常、中断,利用Preconditions.checkNotNull等,而不是继续套一层Optional对象,这也属于乱用Optional之列。

Guava-Optional可空类型的更多相关文章

  1. guava学习--Optional可空类型

    转载:http://www.cnblogs.com/whitewolf/p/4231783.html Null sucks 回到本文主题Optional.在我日常编程中NullPointerExcep ...

  2. Java8 Optional && Guava Optional

    Java8 -- Optional boolean isPresent():与obj != null()一样:调用get()前要调用isPresent()检查,不然会报错 Optional的三种构造方 ...

  3. 四、可空类型Nullable<T>到底是什么鬼

    值类型为什么不可以为空 首先我们都知道引用类型默认值都是null,而值类型的默认值都有非null. 为什么引用类型可以为空?因为引用类型变量都是保存一个对象的地址引用(就像一个url对应一个页面),而 ...

  4. C#可空类型

    C#创建可空类型对于有些可选类型的时候特别好用.创建可空类型用法直接上图. 执行效果 用法 运行效果

  5. 【C#】可空类型(Nullable)

    C# 可空类型(Nullable) C# 提供了一个特殊的数据类型,nullable 类型(可空类型),可空类型可以表示其基础值类型正常范围内的值,再加上一个 null 值. 例如,Nullable& ...

  6. C#可空类型的速度和GC Alloc测试

    在Unity中进行速度和GC Alloc的测试 测试脚本: using UnityEngine; using System; using System.Collections; using Syste ...

  7. swift_枚举 | 可为空类型 | 枚举关联值 | 枚举递归 | 树的概念

    ***************可为空的类型 var demo2 :we_demo = nil 上面这个代码串的语法是错的 为什么呢, 在Swift中,所有的类型定义出来的属性的默认值都不可以是nil ...

  8. [C#] 可空类型的实现原理

    int? 是可为null的值类型.只比int多一个值就是null. 思考: 同样的内存空间,怎么实现的多一个值的?都是4字节,32位,int?靠什么存在一个null值的. 发现: 分析一下内存,看看如 ...

  9. 07.C#泛型的限制和可空类型的简单说明(三章3.5-四章4.1)

    自己在写文章的同时,也是在学习,对于书中的语句很多其实没有太好的理解,读一本书,要消化!!!三章都是讲泛型的,最后写一下泛型的限制,对于本章学习的完结,one end,one begin. 看下面的代 ...

随机推荐

  1. DIV+CSS常用的网页布局代码

    单行一列以下是引用片段:body { margin: 0px; padding: 0px; text-align: center; }#content { margin-left:auto; marg ...

  2. DIV页面布局,开局代码

    DIV页面布局,开局代码 主要是style部分和body部分 <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN ...

  3. 如何辨别具体的一种SaaS是否安全?

    如何辨别具体的一种SaaS是否安全,需要把握以下几点: 1.传输协议加密 首先,要看SaaS产品提供使用的协议,是https://还是一般的http://,别小看这个s,这表明所有的数据在传输过程中都 ...

  4. sql server 2000数据库 最近经常出现某进程一直占用资源,阻塞?死锁?

    OA的数据库最近多次出现某进程一直占用资源,导致其他进程无法执行.使用sp_who2 和 sql server profiler跟踪查询,发现有以下几个语句常常占用资源: 1.declare @P1 ...

  5. PHP 增删改查

    <h1>主页面family</h1> <table width="100%" border="1px" cellpadding=& ...

  6. Mac 系统下的环境变量

    1.查看电脑环境变量   -->echo $PATH 2. 新建环境变量   sudo vim ~/.bash_profile  输入密码 3. 按 I ,编辑新的环境变量地址,保存 退出 :w ...

  7. Tomcat7下出现The requested resource(/)is not available

    1首先确保你的localhost是否正常运行解决方案:1观察项目是否部署2重新将tomcat7导入 2确保你的项目名后跟index.jsp是否正常运行解决方案:1右键项目名,web进行查询,观察部署的 ...

  8. 【转】25个必须记住的SSH命令

    1.复制SSH密钥到目标主机,开启无密码SSH登录 ssh-copy-id user@host 如果还没有密钥,请使用ssh-keygen命令生成. 2.从某主机的80端口开启到本地主机2001端口的 ...

  9. 使用html2canvas实现批量生成条形码

    /*前台代码*/ <%@ Page Language="C#" AutoEventWireup="true" CodeFile="Generat ...

  10. noip2008-t3

    [题目描述] 小渊和小轩是好朋友也是同班同学,他们在一起总有谈不完的话题.一次素质拓展活动中,班上同学安排做成一个m行n 列的矩阵,而小渊和小轩被安排在矩阵对角线的两端,因此,他们就无法直接交谈了.幸 ...