如何确保java8流中的处理顺序?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/29216588/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to ensure order of processing in java8 streams?
提问by membersound
I want to process lists inside an XML
java object. I have to ensure processing all elements in order I received them.
我想处理XML
java 对象内的列表。我必须确保按顺序处理所有元素。
Should I therefore call sequential
on each stream
I use?
list.stream().sequential().filter().forEach()
因此sequential
,stream
我应该调用我使用的每一个吗?
list.stream().sequential().filter().forEach()
Or it it sufficient to just use the stream as long as I don't use parallelism?
list.stream().filter().forEach()
或者只要我不使用并行性就可以使用流?
list.stream().filter().forEach()
采纳答案by Holger
You are asking the wrong question. You are asking about sequential
vs. parallel
whereas you want to process items in order, so you have to ask about ordering. If you have an orderedstream and perform operations which guarantee to maintain the order, it doesn't matter whether the stream is processed in parallel or sequential; the implementation will maintain the order.
你问错了问题。您在询问sequential
vs.parallel
而您想按顺序处理项目,因此您必须询问订购。如果您有一个有序的流并执行保证保持顺序的操作,那么该流是并行处理还是顺序处理无关紧要;执行将维持秩序。
The ordered property is distinct from parallel vs sequential. E.g. if you call stream()
on a HashSet
the stream will be unordered while calling stream()
on a List
returns an ordered stream. Note that you can call unordered()
to release the ordering contract and potentially increase performance. Once the stream has no ordering there is no way to reestablish the ordering. (The only way to turn an unordered stream into an ordered is to call sorted
, however, the resulting order is not necessarily the original order).
有序属性不同于并行与顺序。例如,如果您调用stream()
aHashSet
流将是无序的,而调用stream()
aList
返回有序流。请注意,您可以调用unordered()
以释放订购合同并可能提高性能。一旦流没有排序,就无法重新建立排序。(将无序流转换为有序流的唯一方法是调用sorted
,但是,结果顺序不一定是原始顺序)。
See also the “Ordering” sectionof the java.util.stream
package documentation.
又见“订购”一节中的java.util.stream
包文档。
In order to ensure maintenance of ordering throughout an entire stream operation, you have to study the documentation of the stream's source, all intermediate operations and the terminal operation for whether they maintain the order or not (or whether the source has an ordering in the first place).
为了确保在整个流操作中保持排序,您必须研究流的源、所有中间操作和终端操作的文档,以确定它们是否维护顺序(或源是否在第一个中具有排序)地方)。
This can be very subtle, e.g. Stream.iterate(T,UnaryOperator)
creates an ordered stream while Stream.generate(Supplier)
creates an unorderedstream. Note that you also made a common mistake in your question as forEach
does notmaintain the ordering. You have to use forEachOrdered
if you want to process the stream's elements in a guaranteed order.
这可能非常微妙,例如,Stream.iterate(T,UnaryOperator)
在Stream.generate(Supplier)
创建无序流的同时创建有序流。请注意,您在问题中也犯了一个常见错误,因为不保持顺序。如果要以有保证的顺序处理流的元素,则必须使用。forEach
forEachOrdered
So if your list
in your question is indeed a java.util.List
, its stream()
method will return an orderedstream and filter
will not change the ordering. So if you call list.stream().filter() .forEachOrdered()
, all elements will be processed sequentially in order, whereas for list.parallelStream().filter().forEachOrdered()
the elements might be processed in parallel (e.g. by the filter) but the terminal action will still be called in order (which obviously will reduce the benefit of parallel execution).
因此,如果您list
在问题中确实是 a java.util.List
,则其stream()
方法将返回一个有序流并且filter
不会更改顺序。因此,如果您调用list.stream().filter() .forEachOrdered()
,所有元素将按顺序依次处理,而对于list.parallelStream().filter().forEachOrdered()
元素可能会并行处理(例如通过过滤器),但终端操作仍会按顺序调用(这显然会降低并行执行的好处) .
If you, for example, use an operation like
例如,如果您使用类似的操作
List<…> result=inputList.parallelStream().map(…).filter(…).collect(Collectors.toList());
the entire operation might benefit from parallel execution but the resulting list will always be in the right order, regardless of whether you use a parallel or sequential stream.
整个操作可能受益于并行执行,但结果列表将始终按正确顺序排列,无论您使用并行流还是顺序流。