package net.ranides.assira.collection.query.support;

import lombok.experimental.UtilityClass;

import net.ranides.assira.functional.Consumers;
import net.ranides.assira.functional.Predicates;

import java.util.Collection;
import java.util.function.Consumer;
import java.util.function.Predicate;

/**
 * This is internal utility class not supposed to use by clients.
 * It has default implementations of query operations using only Collection contract.
 */
@UtilityClass
@SuppressWarnings("MissingJavadoc")
public class BaseCollection {

    public static <T> void forEach(Collection<T> that, boolean parallel, Consumer<? super T> consumer) {
        if(parallel) {
            that.parallelStream().forEach(consumer);
        } else {
            that.forEach(consumer);
        }
    }

    public static <T> void forEach(Collection<T> that, boolean parallel, Consumers.EachConsumer<? super T> consumer) {
        if(parallel) {
            BaseSpliteratorParalell.forEach(that.parallelStream().spliterator(), consumer);
        } else {
            BaseIterable.forEach(that, consumer);
        }
    }

    public static <T> boolean whileEach(Collection<T> that, boolean parallel, Predicate<? super T> consumer) {
        if(parallel) {
            return that.parallelStream().allMatch(consumer);
        } else {
            return BaseIterable.whileEach(that, consumer);
        }
    }

    public static <T> boolean whileEach(Collection<T> that, boolean parallel, Predicates.EachPredicate<? super T> consumer) {
        if(parallel) {
            return BaseSpliterator.whileEach(that.parallelStream().spliterator(), true, consumer);
        } else {
            return BaseIterable.whileEach(that, consumer);
        }
    }
}
