guava – Optional
过多的使用null可能会导致大量的bugs,Google code 底层代码中,95%的集合类默认不接受null值。对null值,使用快速失败拒绝null比默认接受更好。
另外,null本身的含义很模糊。例如,对于null返回值,如Map.get(key)返回null,可能因为和key对应的值为null,也可能map中根本没有该key。null也可以用以表示失败或成功,可能代表任何事物。使用其他值而不是null可以使代码含义表达的更清楚。
尽管如此,有些地方还是应该使用null。在内存和速度方面,null是廉价的,并且在对象数组中是不可避免的。
基于以上原因,Guava大部分工具对null都设计为快速失败。另外,Guava提供了一些方便使用null的工具。
实际案例
不要在Set中使用null,也不要将null作为Map的key值,使用特殊值代替null可以让查找的语义更清晰。
如果你想把null作为Map的value,更好的办法不是将该条目放入Map中,而是应该以一个单独的Set维护“值为null”的键集合。因为Map中某个键对应的值为null和Map中没有某个键值很容易混淆。
如果需要在List中使用null,并且这个List是稀疏的,则使用Map<Integer, E>可能更好。
如果确实需要null,但null值不能和Guava的集合一起工作,则只能选择其他方式,如JDK中的Collections.unmodifiableList代替Guava中的ImmutableList。
Optional
Guava设计Optional来解决null问题,Optional<T>表示可能为null的T类型的引用。Optional实例要么包含一个非null的引用,要么什么都不包含(absent),从不会包含null值引用。在需要使用null的时候,可以用Optional代替。
Optional除了赋予null意义外,增加可读性,还在于它是一种傻瓜式的防护。Optional 迫使你积极思考引用确实的情况,因为你必须显式地从Optional 获取引用。
Optional 的可能应用方面:
- 作为方法返回值,用于取代使用null作为返回值的情况。
- 用于区分“unknow”(如Map不包含)和“known to have no value”(如Map包含该键,值为Optional.absent())。
- 用于包装null引用,从而在不支持null的集合中使用。
创建Optional(均为静态方法)
| Optional.of(T) | 创建指定引用的Optional实例,对null值抛出NullPointException。建议直接传递常量参数。 |
| Optional.absent() | 创建引用缺失的Optional实例 |
| Optional.fromNullable(T) | 创建指定引用的Optional实例,若引用为null则表示缺失 |
assertEquals("training", Optional.of("training").get());
Optional<String> optionalName = Optional.absent();
assertFalse(optionalName.isPresent());
// Non-null instance
Optional<String> optionalName = Optional.fromNullable("bob");
assertEquals("bob", optionalName.get());
// null instance
assertSame(Optional.absent(), Optional.fromNullable(null));
查询方法(均为非静态方法)
| boolean isPresent() | 如果该Optional 包含非null引用,返回true。 |
| T get() | 返回Optional 所包含的引用,若引用缺失,则抛出IllegalStateException。 |
| T or(T) | 返回Optional 所包含的引用,若引用缺失,返回默认值。 |
| T orNull() | 返回Optional 所包含的引用,若引用缺失,返回null。 |
| Set<T> asSet() | 返回Optional所包含的singleton不可变集合,若为空,返回空集合。 |
public void testIsPresent_no() {
assertFalse(Optional.absent().isPresent());
}
public void testIsPresent_yes() {
assertTrue(Optional.of("training").isPresent());
}
public void testGet_absent() {
Optional<String> optional = Optional.absent();
try {
optional.get();
fail();
} catch (IllegalStateException expected) {
}
}
public void testGet_present() {
assertEquals("training", Optional.of("training").get());
}
public void testOr_T_present() {
assertEquals("a", Optional.of("a").or("default"));
}
public void testOr_T_absent() {
assertEquals("default", Optional.absent().or("default"));
}
public void testOrNull_present() {
assertEquals("a", Optional.of("a").orNull());
}
public void testOrNull_absent() {
assertNull(Optional.absent().orNull());
}
public void testAsSet_present() {
Set<String> expected = Collections.singleton("a");
assertEquals(expected, Optional.of("a").asSet());
}
public void testAsSet_absent() {
assertTrue("Returned set should be empty", Optional.absent().asSet().isEmpty());
}
public void testAsSet_presentIsImmutable() {
Set<String> presentAsSet = Optional.of("a").asSet();
try {
presentAsSet.add("b");
fail();
} catch (UnsupportedOperationException expected) {
}
}
public void testAsSet_absentIsImmutable() {
Set<Object> absentAsSet = Optional.absent().asSet();
try {
absentAsSet.add("foo");
fail();
} catch (UnsupportedOperationException expected) {
}
}
guava – Optional的更多相关文章
- Java8 Optional && Guava Optional
Java8 -- Optional boolean isPresent():与obj != null()一样:调用get()前要调用isPresent()检查,不然会报错 Optional的三种构造方 ...
- guava学习--Optional可空类型
转载:http://www.cnblogs.com/whitewolf/p/4231783.html Null sucks 回到本文主题Optional.在我日常编程中NullPointerExcep ...
- 还在重复写空指针检查代码?考虑使用 Optional 吧!
一.前言 如果要给 Java 所有异常弄个榜单,我会选择将 NullPointerException 放在榜首.这个异常潜伏在代码中,就像个遥控炸弹,不知道什么时候这个按钮会被突然按下(传入 null ...
- 【Java 8】Optional 使用
一.前言 如果要给 Java 所有异常弄个榜单,我会选择将 NullPointerException 放在榜首.这个异常潜伏在代码中,就像个遥控炸弹,不知道什么时候这个按钮会被突然按下(传入 null ...
- Guava-Optional可空类型
接上篇Guava之Joiner和Splitter,本篇将介绍Guava的另外一个有用的对象Optional,这在Java中Google Guava首先给我们提出可空对象模型的.在其他语言如c#这是已经 ...
- 摘抄JPA官方文档原文 防呆
Spring Data JPA - Reference Documentation Oliver GierkeThomas DarimontChristoph StroblMark PaluchVer ...
- Spring Data Commons 官方文档学习
Spring Data Commons 官方文档学习 -by LarryZeal Version 1.12.6.Release, 2017-07-27 为知笔记版本在这里,带格式. Table o ...
- Guava学习笔记(1):Optional优雅的使用null
转自:http://www.cnblogs.com/peida/archive/2013/06/14/Guava_Optional.html 参考:[Google Guava] 1.1-使用和避免nu ...
- Guava API学习之Optional 判断对象是否为null
java.lang.NullPointerException,只要敢自称Java程序员,那对这个异常就再熟悉不过了.为了防止抛出这个异常,我们经常会写出这样的代码: Person person = p ...
随机推荐
- requestAnimationFrame
(function() { var lastTime = 0; var vendors = ['webkit', 'moz']; for(var x = 0; x < vendors.lengt ...
- 对冲的艺术——delta中性交易
delta中性交易 delta中性交易——外行话 delta中性交易就是构造一个含有期权头寸的组合,使其不受标的股票或指数价格小幅变动的影响.换句话讲,无论标的价格是涨还是跌,组合的市值始终保持不变. ...
- OpenGL角轴
概述 轴旋转 角轴 概述 OpenGL旋转矩阵 旋转角度直接影响OpenGL GL_MODELVIEW矩阵的前三列,准确地说是向左.向上与向前三轴元素.例如,如果一沿X轴的单位向量(1,0,0)与任一 ...
- php区分new static 和new self
关键点在于一个是静态绑定,一个是延迟绑定 <?php class A{ public function __construct() { } public function createObjSt ...
- winform中固定界面大小的方法
Step1: MaximizeBox : False MinimizeBox : False Step2: FormBoarderStyle : FixedSingle
- linux下利用GPRS模块发短信、打电话
一.开发环境 内核版本:linux-3.0 开发板:FL2440(nandflash:K9F1G08 128M) GPRS模块:SIM900 二.与发短信和拨号相关的 AT 指 ...
- python统计元素重复次数
python统计元素重复次数 # !/usr/bin/python3.4 # -*- coding: utf-8 -*- from collections import Counter arr = [ ...
- Zookeeper基本配置
前面两篇文章介绍了Zookeeper是什么和可以干什么,那么接下来我们就实际的接触一下Zookeeper这个东西,看看具体如何使用,有个大体的感受,后面再描述某些地方的时候也能在大脑中有具体的印象.本 ...
- python virtualenv 安装运行saltstack
需求产生场景: 1.python的virtualenv虚拟环境非常的好用. 2.saltstack作为运维自动化的一个重要组件也挺好用的. 但是: 1.saltsatck ...
- 为Asp.net WebApi 添加跨域支持
Nuget安装包:microsoft.aspnet.webapi.cors 原文地址:https://www.asp.net/web-api/overview/security/enabling-cr ...