我有以下内容:
LinkedList<Integer> ints = new LinkedList();
//fill it with some ints
Stream<Integer> stream = ints.stream();
//process the stream in some way
我的问题是,是否保证流的处理顺序是基础LinkedList
的顺序?我读了documentation,但没有关于订购的任何信息。
就我而言,维护订单至关重要。
答案 0 :(得分:2)
Streams可能有也可能没有已定义的遭遇顺序。是否 一个流有一个遭遇顺序取决于源和 中间操作。某些流源(例如List或 数组)本质上是有序的,而其他的(如HashSet) 不是。某些中间操作(例如sorted())可能会强制执行 在其他无序流上遇到订单,其他人可能会 渲染无序的有序流,例如BaseStream.unordered()。 此外,一些终端操作可以忽略遭遇顺序,例如 的forEach()。
如果订购了流,则大多数操作都被限制为可以进行操作 他们遭遇顺序中的元素;如果流的来源是 列表包含[1,2,3],然后执行map的结果(x - &gt; x * 2) 必须是[2,4,6]。但是,如果源没有定义的遭遇 顺序,那么值[2,4,6]的任何排列都是有效的 结果
对于顺序流,是否存在遭遇订单 不影响表现,只影响决定论。如果订购了流, 在相同的流程上重复执行相同的流管道 源将产生相同的结果;如果没有订购, 重复执行可能会产生不同的结果。
对于并行流,有时可以放宽排序约束 实现更高效的执行...
另外,正如您所说,处理顺序对您很重要,请参阅here:
流管道结果可能是不确定的或不正确的 流操作的行为参数是有状态的......
最好的方法是避免有状态的行为参数流式传输 完全运作;通常有一种重组流的方法 管道,以避免有状态。
另请参阅此问题的答案:How to ensure order of processing in java8 streams?
简而言之,如果您使用顺序流(在一个线程中执行的流),并且您对forEach()
等操作非常谨慎,则看起来您可以保留顺序。然而,这可能不是一个好主意。
答案 1 :(得分:1)
取决于您应用于流的处理...尤其是使用parallel()
import java.util.LinkedList;
import java.util.function.Consumer;
import java.util.stream.Stream;
public class Streaming {
public static void main(String[] args) {
LinkedList<Integer> ints = new LinkedList();
for(int i = 0 ; i < 100; i++) {
ints.add(i);
}
Stream<Integer> stream = ints.stream();
// will not be ordered
stream.parallel().forEach(new Consumer<Integer>() {
@Override
public void accept(Integer t) {
System.out.println(t);
}
});
stream = ints.stream();
// will be ordered
stream.parallel().forEachOrdered(new Consumer<Integer>() {
@Override
public void accept(Integer t) {
System.out.println(t);
}
});
}
}