Stream<T>
基于Spliterator<T>
提供的内部迭代方法,而该方法又将boolean tryAdvance(Consumer<? super T> action)
实现的委派委托给了。简单地说:Stream<T>
---->
Spliterator<T>
---->
boolean tryAdvance(Consumer<T>)
因此,我想使用某种实用程序,允许从Stream<T>
创建Function<Consumer<T>, Boolean>
。请注意,Function<Consumer<T>, Boolean>
具有与boolean tryAdvance(Consumer<T>)
相同的描述符,即Consumer<T> -> Boolean
。
我正在寻找辅助功能,例如(根据@shmosel的comment更新):
static <T> Stream<T> stream(Predicate<Consumer<? super T>> moveNext) {
Spliterator<T> iter = new AbstractSpliterator<T>(Long.MAX_VALUE, 0) {
@Override
public boolean tryAdvance(Consumer<? super T> action) {
return moveNext.test(action);
}
};
return StreamSupport.stream(iter, false);
}
这是我发现实现该实现的最简洁的方法。但是,我仍然不喜欢使用匿名内部类。有没有最简单的选择?
最佳答案
由于没有内置功能接受函数,因此不必创建类型,尽管它不必是内部类。例如。
public interface SingleFuncStream<T> extends Spliterator<T> {
public static <T> Stream<T> stream(SingleFuncStream<T> f) {
return StreamSupport.stream(f, false);
}
@Override default public Spliterator<T> trySplit() { return null; }
@Override default public long estimateSize() { return Long.MAX_VALUE; }
@Override default public int characteristics() { return ORDERED; }
}
可以这样使用
ListIterator<String> i = Arrays.asList("foo", "bar", "baz").listIterator(3);
SingleFuncStream.<String>stream(c -> {
if(!i.hasPrevious()) return false;
c.accept(i.previous());
return true;
}).forEach(System.out::println);
但是,既然您已经阐明了要实现自定义中间操作的目的,那么上述解决方案就不合适了。最好使用内部类的另一个替代方法,即专用的顶级类。
其中大多数操作(如您提到的示例)都带有状态,或者必须指定特征或更复杂的估算值,而您无法使用单个函数来表达这些估算值。
关于java - 从函数创建流的最简单方法,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/42997456/