为什么检查NULL的Optional.isEmpty()不被称为isNull()



这可能是个愚蠢的问题。

当我在代码中使用Optional.isEmpty()时,如下所示

Optional<List<String>> optional = Optional.of(new ArrayList<>());
optional.isEmpty(); // only checks if the value is NULL or not.

CCD_ 2方法仅检查值CCD_。

public boolean isEmpty() {
return value == null;
}

这个方法名称对我来说似乎不清楚。

我想知道为什么这个方法被命名为isEmpty()而不是isNull(),因为它在后台执行null检查?

这是因为null检查是实现细节,而不是方法逻辑上所做的。从逻辑上讲,该方法检查可选值是空的还是占用的。

从技术上,这可以通过多种方式实现,具体取决于Optional如何存储其值。JDK8的实现碰巧使用了一个带有null检查的引用对象,但其他实现可能会有不同的做法。将高级接口描述与其实现混淆是错误的。封装的全部目的是从用户那里抽象出实现细节。

您错过了要点。

Optional被设计为数据的容器,它本身永远不会是null,并且可以安全地与之交互。

可选是,而不是用于替代空检查。这意味着表示可为null的返回值,并且不应该为了隐藏null检查或链方法而创建(更多信息,请参阅此处和此处(。

如果你需要验证某个东西不是null,你可以使用方法Objects#requireNonNull()和它的风格或显式的空检查

可选的背后的想法是,它充当一个值的,你可以用它做很多工作,而不必关心框是否空。Optional为您提供了筛选到框filter()内的值、用另一个框or()替换空框、转换框map()内的值等方法。所有这些操作都可以通过流畅地链接方法来完成,而无需打开框。

方法isNull()/isNotNull()不适用于Optional API,因为它们与它的设计目标相矛盾,即提供一种有限的机制来表示可为null的返回值,以及以简单流畅的方式与目标值(围绕其包裹可选值(交互的平均值,无论其值是否为null

注意,检查isPresent()(JDK 8(和isEmpty()(JDK 11(是否存在是最后的手段。当你使用它们时要注意,因为很可能你没有充分利用Optional。

此外,请注意,将Optional包装在Collection或数组周围是没有意义的,因为它们也是数据的容器(像可选的一样(,并且可能也是空的,这表示缺少数据。

做这样的事既多余又不方便。

Optional<List<String>> optional = Optional.of(new ArrayList<>());

当集合不是isEmpty()0时(应该是这种情况,因为保留可为null的集合是一种反模式(,Collection.isEmpty()足以检查数据是否存在。同时,当您有可选的环绕集合时,可选集合中的集合并不意味着实际数据存在。

这是可选:的定义

一个容器对象,它可能包含也可能不包含非null值。

由于对象本身是一个容器,它可能包含也可能不包含值,因此isEmpty(或isPresent(指的是容器的状态,无论它是否包含某些内容。

isNull作为一个名称将表明Optional将是null,这将是一个错误的印象,因为Optional本身是一个适当存在的实例。

如果Optional不包含非空值,它是null吗?不,你可以检查

myOptional == null

你会发现它是假的(否则你甚至不能调用null0(。容器内的对象是否为null?如果isEmpty就是null,那么这是肯定的。因此,Optional要么是空的,要么里面有什么东西

这里有一种不同的实现Optional的方法,它通过对满实例和空实例使用不同的具体类来检查空性。

public interface MyOptional<T> {
boolean isEmpty();
T getOrDefault(T aDefault);
static <T> MyOptional<T> empty() {
return new MyOptional<T>() {
@Override
public boolean isEmpty() {
return true;
}
@Override
public T getOrDefault(T aDefault) {
return aDefault;
}
};
}
static <T> MyOptional<T> of(T t) {
return new MyOptional<T>() {
@Override
public boolean isEmpty() {
return false;
}
@Override
public T getOrDefault(T aDefault) {
return t;
}
};
}
public static void main(String[] args) {
MyOptional<String> optString = MyOptional.empty();
System.out.println(optString.isEmpty());
}
}

这与Java的Optional在语义上有区别:它可以在完整实例中包含null值,而Java不能。

最新更新