Optional API
java8在java.util
包中新发布了一个Optional<T>
的类,先来看一下它的javadoc:
/**
* A container object which may or may not contain a non-null value.
* If a value is present, {@code isPresent()} will return {@code true} and
* {@code get()} will return the value.
*
* <p>Additional methods that depend on the presence or absence of a contained
* value are provided, such as {@link #orElse(java.lang.Object) orElse()}
* (return a default value if value not present) and
* {@link #ifPresent(java.util.function.Consumer) ifPresent()} (execute a block
* of code if the value is present).
*
* <p>This is a <a href="../lang/doc-files/ValueBased.html">value-based</a>
* class; use of identity-sensitive operations (including reference equality
* ({@code ==}), identity hash code, or synchronization) on instances of
* {@code Optional} may have unpredictable results and should be avoided.
*
* @since 1.8
*/
public final class Optional<T> {
通过javadoc我们可以知道,这个类主要是用来对一个泛型值value
进行封装,提供一个isPresent()
方法来表示其中的value
是否是null
, 提供另外一个get()
方法来返回其中的value
。
接下来,我们一起看Optional<T>
的源代码,以此来窥探java8设计此类的主要思想。
成员变量
Optional
类有两个成员变量:
EMPTY
创建了一个空的
Optional
对象,其value
为null
值。
private static final Optional<?> EMPTY = new Optional<>();
value
没啥说的,就是
value
。
private final T value;
这两个成员变量均是不可变的,EMPTY
创建了一个空的Optional
对象,value
即你需要封装的泛型值。
构造函数
Optional
类有两个构造函数,无参构造函数和一个有参构造函数:
- 无参构造函数
private Optional() {
this.value = null;
}
无参构造函数中,给value
赋了一个null
。
- 有参构造函数
如果向该构造函数传入
null
值,则会抛出空指针异常。
private Optional(T value) {
this.value = Objects.requireNonNull(value);
}
有参构造函数将传进来的T
类型的值赋给value
这个成员变量,一旦赋值,就不能改变value
的值了。
这两个构造函数均为私有构造函数,被private
所修饰,这也意味着无法直接通过new
的方式来获得一个Optional
的实例。
实例的获取
获取Optional
类实例有三种方式:
Optional.empty()
public static<T> Optional<T> empty() {
@SuppressWarnings("unchecked")
Optional<T> t = (Optional<T>) EMPTY;
return t;
}
返回
EMPTY
成员变量,通过这个方法获取一个空的Optional
的实例
Optional.of(T value)
public static <T> Optional<T> of(T value) {
return new Optional<>(value);
}
获取一个
Optional
实例, 传入的value
不能为null
, 否则就会抛出空指针异常。
Optional.ofNullable(T value)
public static <T> Optional<T> ofNullable(T value) {
return value == null ? empty() : of(value);
}
获取一个
Optional
实例,传入的value
可以为null
,此时会将EMPTY
变量返回,即一个空的Optional
实例
Coding time
private static void getOptionalInstanceTest() {
// get an empty instance
Optional emptyInstance = Optional.empty();
emptyInstance.isPresent();// false
try {
emptyInstance.get(); // will throw an exception: NoSuchElementException
} catch (Exception e) {
System.out.println(e.getMessage());// will print 'No value present'
}
// get an instance with non-null value
String name = "jwenjian";
Optional<String> instanceWithNonNullValue = Optional.of(name);
instanceWithNonNullValue.isPresent(); // true
instanceWithNonNullValue.get(); // 'jwenjian'
instanceWithNonNullValue.get().equals(name); // true
// get an instance with null value
Optional instanceWithNullValue = Optional.ofNullable(null);
try {
Optional instance = Optional.of(null);// will throw NullPointerException
} catch (Exception e) {
System.out.println("can not get optional instance by call Optional.of(null)");
}
instanceWithNullValue.isPresent(); // false
try {
instanceWithNullValue.get(); // will throw an exception: NoSuchElementException
} catch (Exception e) {
System.out.println(e.getMessage());// will print 'No value present'
}
instanceWithNullValue.equals(emptyInstance); // true
}
to be continue...