3

Suppose, however, that the result container used in this reduction was a concurrently modifiable collection -- such as a ConcurrentHashMap. In that case, the parallel invocations of the accumulator could actually deposit their results concurrently into the same shared result container, eliminating the need for the combiner to merge distinct result containers. This potentially provides a boost to the parallel execution performance. We call this a concurrent reduction.

also

A Collector that supports concurrent reduction is marked with the Collector.Characteristics.CONCURRENT characteristic. However, a concurrent collection also has a downside. If multiple threads are depositing results concurrently into a shared container, the order in which results are deposited is non-deterministic.

from the document

this means the collect method with supplier(Concurrent-thread-safe)should have Collector.Characteristics.CONCURRENT. and thus should not maintain any order.

but my code

List<Employee> li=Arrays.asList(Employee.emparr());
        System.out.println("printing concurrent result "+li.stream().parallel().unordered().map(s->s.getName()).collect(() -> new ConcurrentLinkedQueue<>(),
                (c, e) -> c.add(e.toString()),
                (c1, c2) -> c1.addAll(c2))
                                                  .toString());

always prints the result in the encountered order. does this mean my Collector.Characteristics is not CONCURRENT ? how to check and set this characteristics ?

Stefan Zobel
  • 3,182
  • 7
  • 28
  • 38
amarnath harish
  • 945
  • 7
  • 24
  • 2
    Why would the result not be printed in the encountered order? Parallel just means that it's not guaranteed that the encountered order will be retained, not that it's guaranteed that the resulting order will be different. – daniu Aug 28 '18 at 09:09
  • Why do you think your example is collected in a concurrent manner? – Flown Aug 28 '18 at 09:11
  • because i used concurrent container. – amarnath harish Aug 28 '18 at 09:12
  • You can only define `CONCURRENT` when you create a `Collector::of` with the flag. – Flown Aug 28 '18 at 09:13

1 Answers1

6

Your Collector does not know that you use a concurrent collection provided by Supplier, just add the characteristic and see that it is executed the way you want to; for example:

String s = Stream.of(1, 2, 3, 4).parallel()
            .unordered()
            .collect(
                    Collector.of(
                            () -> new ConcurrentLinkedQueue<>(),
                            (c, e) -> c.add(e.toString()),
                            (c1, c2) -> {
                                c1.addAll(c2);
                                return c1;
                            },
                            Characteristics.CONCURRENT))
Eugene
  • 117,005
  • 15
  • 201
  • 306
  • Then the combiner function will never be called. – Flown Aug 28 '18 at 09:13
  • @Flown of course, but that is entire different story on how `Concurrent` collectors work – Eugene Aug 28 '18 at 09:14
  • so these characteristics are not inferred from the type of supplier? what would happen if i use arraylist and set concurrent characteristics ? – amarnath harish Aug 28 '18 at 09:14
  • I only wanted to mention it. This is the definition of a concurrent `Collector`. – Flown Aug 28 '18 at 09:15
  • 2
    @amarnathharish you will get in trouble... you would effectively say that `ArrayList` is more that OK to be updated from multiple threads and things will break. How will they break? Well you could get an Exception, null entries or not all entries in the result List – Eugene Aug 28 '18 at 09:16
  • @flown why combiner never called? – amarnath harish Aug 28 '18 at 09:20
  • @amarnathharish you should also read Flown comment here - a concurrent collect will not call the combiner, and only call the `Supplier` once. https://stackoverflow.com/questions/40888262/what-is-the-difference-between-collectors-toconcurrentmap-and-converting-a-map-t/40888456#40888456 – Eugene Aug 28 '18 at 09:20
  • 1
    Perhaps, [this one](https://stackoverflow.com/a/41045442/2711488) will also help… – Holger Aug 28 '18 at 13:25