![JAR search and dependency download from the Maven repository](/logo.png)
com.pivovarit.collectors.ParallelStreamCollector Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of parallel-collectors Show documentation
Show all versions of parallel-collectors Show documentation
Parallel collection processing with customizable thread pools
package com.pivovarit.collectors;
import java.util.ArrayList;
import java.util.Collections;
import java.util.EnumSet;
import java.util.List;
import java.util.Set;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.Executor;
import java.util.function.BiConsumer;
import java.util.function.BinaryOperator;
import java.util.function.Function;
import java.util.function.Supplier;
import java.util.stream.Collector;
import java.util.stream.Stream;
import java.util.stream.StreamSupport;
import static com.pivovarit.collectors.AsyncParallelCollector.requireValidParallelism;
import static java.util.Objects.requireNonNull;
/**
* @author Grzegorz Piwowarek
*/
class ParallelStreamCollector implements Collector>, Stream> {
private final Dispatcher dispatcher;
private final Function function;
private final Function>, Stream> processor;
private final Set characteristics;
private ParallelStreamCollector(
Function function,
Function>, Stream> processor,
Set characteristics,
Executor executor, int parallelism) {
this.processor = processor;
this.characteristics = characteristics;
this.dispatcher = new Dispatcher<>(executor, parallelism);
this.function = function;
}
private ParallelStreamCollector(
Function function,
Function>, Stream> processor,
Set characteristics,
Executor executor) {
this.characteristics = characteristics;
this.dispatcher = new Dispatcher<>(executor);
this.function = function;
this.processor = processor;
}
private void startConsuming() {
if (!dispatcher.isRunning()) {
dispatcher.start();
}
}
@Override
public Supplier>> supplier() {
return ArrayList::new;
}
@Override
public BiConsumer>, T> accumulator() {
return (acc, e) -> {
startConsuming();
acc.add(dispatcher.enqueue(() -> function.apply(e)));
};
}
@Override
public BinaryOperator>> combiner() {
return (left, right) -> {
left.addAll(right);
return left;
};
}
@Override
public Function>, Stream> finisher() {
return processor
.compose(i -> {
dispatcher.stop();
return i;
});
}
@Override
public Set characteristics() {
return characteristics;
}
static Collector> streaming(Function mapper, Executor executor) {
requireNonNull(executor, "executor can't be null");
requireNonNull(mapper, "mapper can't be null");
return new ParallelStreamCollector<>(mapper, streamInCompletionOrderStrategy(), EnumSet.of(Characteristics.UNORDERED), executor);
}
static Collector> streaming(Function mapper, Executor executor, int parallelism) {
requireNonNull(executor, "executor can't be null");
requireNonNull(mapper, "mapper can't be null");
requireValidParallelism(parallelism);
return new ParallelStreamCollector<>(mapper, streamInCompletionOrderStrategy(), EnumSet.of(Characteristics.UNORDERED), executor, parallelism);
}
static Collector> streamingOrdered(Function mapper, Executor executor) {
requireNonNull(executor, "executor can't be null");
requireNonNull(mapper, "mapper can't be null");
return new ParallelStreamCollector<>(mapper, streamOrderedStrategy(), Collections.emptySet(), executor);
}
static Collector> streamingOrdered(Function mapper, Executor executor, int parallelism) {
requireNonNull(executor, "executor can't be null");
requireNonNull(mapper, "mapper can't be null");
requireValidParallelism(parallelism);
return new ParallelStreamCollector<>(mapper, streamOrderedStrategy(), Collections.emptySet(), executor, parallelism);
}
private static Function>, Stream> streamInCompletionOrderStrategy() {
return futures -> StreamSupport.stream(new CompletionOrderSpliterator<>(futures), false);
}
private static Function>, Stream> streamOrderedStrategy() {
return futures -> futures.stream().map(CompletableFuture::join);
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy