我阅读了 IntStream::noneMatch 的 Javadoc 。
它说:
Returns whether no elements of this stream match the provided predicate. May not evaluate the predicate on all elements if not necessary for determining the result. If the stream is empty then true is returned and the predicate is not evaluated.
我想知道是否存在一个实际场景,其中 noneMatch
不会评估流中所有元素上的谓词并返回 true(在 noneMatch
返回的情况下) false,很明显,谓词仅在元素上求值,直到找到第一个匹配项。
我能想到的唯一场景是,如果流管道有一个过滤器,其谓词是 noneMatch
谓词的精确负数,那么 noneMatch
可能会返回无需测试任何元素即可为真。
但是,当使用以下代码进行测试时:
boolean out = IntStream.range(1, 10000)
.filter(i -> i % 2 == 0)
.peek(System.out::println)
.noneMatch(i -> i % 2 == 1);
System.out.println(out);
我得到从 2 到 9998 的偶数输出:
2
4
6
...
9998
true
这意味着即使过滤器仅返回偶数整数,也对整个流进行了评估,而 noneMatch
的谓词要求找不到奇数整数,因此它应该能够在不评估的情况下返回 true任何元素。
那么,当 Javadoc 说可能不会对所有元素进行计算
时,它是否仅指 noneMatch
返回 false 的情况?
编辑:
我只是想澄清一下,我的问题不是为什么我发布的代码会评估整个流。我的问题是是否存在这样一种情况:noneMatch
返回true而不评估整个流。
最佳答案
so it should be able to return true without evaluating any elements
不,为了检查没有元素匹配,它必须检查所有。换句话说,如果它返回 true
那么它肯定会查看所有内容。换句话说 - 你的逻辑依赖于谓词的作用,那么它如何在不评估任何元素的情况下返回,这意味着谓词永远不会被应用?
它可以在不评估所有元素的情况下返回 true
的唯一方法是它是否可以仅通过流的类型和有关谓词的信息来判断。例如,如果流“知道”它是 UUID
引用流,并且谓词是“匹配字符串”,那么它不需要评估事物 - 但我怀疑是否有任何东西尝试进行此类优化。
但是,如果(且仅当)它找到确实与谓词匹配的内容时,它可以返回false
而不查看其余项目。
例如,如果您将代码更改为:
boolean out = IntStream.range(1,10000)
.peek(System.out::println)
.noneMatch(i->i%4==3);
System.out.println(out);
然后你会得到以下输出:
1
2
3
false
关于java - IntStream::noneMatch 不能评估流中所有元素的谓词吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27636711/