为什么 Spliterator<?> 将 NONNULL 定义为特征?

Why does Spliterator<?> defines NONNULL as a characteristic?

javadoc of Spliterator(如果我理解正确的话,这基本上就是 Stream 背后真正的东西)定义了许多有意义的特征,例如 SIZEDCONCURRENT , IMMUTABLE

但是它也定义了NONNULL;为什么?

我认为用户有责任确保这一点,例如,如果开发人员试图 .sort() 一个非 SORTED 流,其中有空元素 he/she 理应受到 NPE 的欢迎...

但后来这个特点就存在了。为什么? Spliterator 的 javadoc 本身没有提到它的任何实际用法,java.util.stream 包的 package-info.java 也没有提到...

我在枚举 StreamOpFlag 的代码中发现了以下注释。

// The following Spliterator characteristics are not currently used but a
// gap in the bit set is deliberately retained to enable corresponding
// stream flags if//when required without modification to other flag values.
//
// 4, 0x00000100 NONNULL(4, ...
// 5, 0x00000400 IMMUTABLE(5, ...
// 6, 0x00001000 CONCURRENT(6, ...
// 7, 0x00004000 SUBSIZED(7, ...

来自 Spliterator 的文档:

A Spliterator also reports a set of characteristics() of its structure, source, and elements from among ORDERED, DISTINCT, SORTED, SIZED, NONNULL, IMMUTABLE, CONCURRENT, and SUBSIZED. These may be employed by Spliterator clients to control, specialize or simplify computation.

请注意,它没有提到 NullPointerException 的预防。如果您对可能包含 null 值的 Stream 进行排序,它 您的责任提供可以处理 nullComparator

第二句也明确表示,使用这些标志只是一个选项,不是“Spliterator clients”的要求,不限于Streams的使用。


因此,无论 Stream API 的当前实现是否使用它,是否有可能利用有关 NONULL 特性的知识?

我也这么认为。实现可以分支到非 null Spliterator 的专用代码,以利用 null 表示特定状态,例如缺少值或处理第一个元素之前的初始值等。实际上,处理可能包含 null Stream 的实际实现代码是 复杂的.但是当然,你总是要权衡一个案例的简化是否值得代码重复。

但有时简化就像知道没有 null 值一样简单,这意味着您可以使用不允许 nullConcurrent… 集合之一, 内部。