有没有办法阻止Stream.generate从它的Lambda闭包?

use*_*023 7 java lambda java-8

我刚刚开始玩Java 8和Lambda Expression,我很好奇我是否可以通过返回特定值(如null)来停止Lambda中的Stream生成.Stream.generate()有可能吗?

private int counter;

private void generate()
{
    System.out.println(Stream.generate(() -> {
        if (counter < 10) {
            counter++;
            return RandomUtils.nextInt(100);
        } else {
            return null;
        }
    }).count());
}
Run Code Online (Sandbox Code Playgroud)

不幸的是,这段代码没有终止,因此只需返回null就不会退出流.

wum*_*mpz 24

更新(2017年):

Java 9将包含这种新方法:

Stream<T> takeWhile(Predicate<? super T> predicate); 
Run Code Online (Sandbox Code Playgroud)

按条件限制流.因此,不再需要下面的解决方法了.

原版的:

随着Stream.generate这是根据定义能够从一个lambda关闭.根据定义,它是无止境的.使用limit()您可以使您的流修复大小.但这对以下条件无济于事:

if random>10 then stop
Run Code Online (Sandbox Code Playgroud)

有可能通过条件限制潜在的无穷无尽的流.如果不知道尺寸,这是有用的.你的朋友是Spliterator,你的示例代码如下:

System.out.println( StreamSupport.stream(Spliterators.spliteratorUnknownSize(new Iterator<Integer>() {
    int counter = 0;

    @Override
    public boolean hasNext() {
        return counter < 10;
    }

    @Override
    public Integer next() {
        counter++;
        return RandomUtils.nextInt(100);
    }
}, Spliterator.IMMUTABLE), false).count());
Run Code Online (Sandbox Code Playgroud)

基本上你可以从Iterator构建一个Stream.我正在使用这个构造,例如来自Stax XML 的XMLEvents流- 解析.

我知道这不是由lambda构造完成的,但IHMO解决了这个缺乏的功能,即按条件停止流项生成.

我会非常感兴趣,如果有更好的方法来实现这一点(我的意思是这个流构造而不是XML处理;))或者如果以这种方式使用流存在根本缺陷.


kav*_*i77 6

对于Lamdas来说这是不可能的,你无法控制表达式内部的流量.甚至API文档都说Stream.generate会生成无限流.

但是,您可以使用limit()方法限制Stream并实现所需的功能:

System.out.println(Stream.generate(() -> RandomUtils.nextInt(100)).limit(10).count());
Run Code Online (Sandbox Code Playgroud)

  • 这不是真的。 (2认同)