All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.softicar.platform.common.core.thread.function.ParallelFunctionRunner Maven / Gradle / Ivy

Go to download

The SoftiCAR Platform is a lightweight, Java-based library to create interactive business web applications.

There is a newer version: 50.0.0
Show newest version
package com.softicar.platform.common.core.thread.function;

import com.softicar.platform.common.core.thread.collection.ThreadCollection;
import java.util.Collection;
import java.util.Map;
import java.util.Map.Entry;
import java.util.TreeMap;
import java.util.function.BiConsumer;
import java.util.function.Function;

public class ParallelFunctionRunner {

	private final Function function;
	private final Map inputValues;
	private final Map exceptions;
	private BiConsumer resultConsumer;
	private BiConsumer exceptionConsumer;
	private long millisPerTry;
	private long tryCount;

	public ParallelFunctionRunner(Function function) {

		this.function = function;
		this.inputValues = new TreeMap<>();
		this.exceptions = new TreeMap<>();
	}

	public ParallelFunctionRunner addInputValue(T values) {

		this.inputValues.put(inputValues.size(), values);
		return this;
	}

	public ParallelFunctionRunner addInputValues(Collection values) {

		values.stream().forEach(this::addInputValue);
		return this;
	}

	public ParallelFunctionRunner setResultConsumer(BiConsumer consumer) {

		this.resultConsumer = consumer;
		return this;
	}

	public ParallelFunctionRunner setExceptionConsumer(BiConsumer exceptionConsumer) {

		this.exceptionConsumer = exceptionConsumer;
		return this;
	}

	public ParallelFunctionRunner setMillisPerTry(long millisPerTry) {

		this.millisPerTry = millisPerTry;
		return this;
	}

	public ParallelFunctionRunner setTryCount(long tryCount) {

		this.tryCount = tryCount;
		return this;
	}

	public void apply() {

		if (resultConsumer == null) {
			throw new IllegalStateException("No result consumer defined.");
		}

		for (int i = 0; i < tryCount && !inputValues.isEmpty(); i++) {
			// create function threads
			Map> threads = new TreeMap<>();
			for (Entry entry: inputValues.entrySet()) {
				threads.put(entry.getKey(), new FunctionThread<>(function, entry.getValue()));
			}

			// run function threads
			new ThreadCollection<>(threads.values()).runAll(millisPerTry);

			// get result values from function threads
			for (Entry> entry: threads.entrySet()) {
				Integer index = entry.getKey();
				FunctionThread thread = entry.getValue();
				if (thread.getException() == null) {
					resultConsumer.accept(thread.getInput(), thread.getResult());
					inputValues.remove(index);
					exceptions.remove(index);
				} else {
					exceptions.put(index, thread.getException());
				}
			}
		}

		// provide exceptions if wanted
		if (exceptionConsumer != null) {
			for (Entry entry: exceptions.entrySet()) {
				T inputValue = inputValues.get(entry.getKey());
				exceptionConsumer.accept(inputValue, entry.getValue());
			}
		}
	}

	public Exception getException(T key) {

		return exceptions.get(key);
	}
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy