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

io.github.jonestimd.subset.BigDecimalSubsetPredicate Maven / Gradle / Ivy

package io.github.jonestimd.subset;

import java.math.BigDecimal;
import java.util.function.Function;

/**
 * An implementation of {@link SubsetPredicate} for {@link BigDecimal} values.
 * @param  the type of the collection items
 */
public class BigDecimalSubsetPredicate implements SubsetPredicate {
    private Function adapter;
    private BigDecimal total = BigDecimal.ZERO;
    private BigDecimal goalMinusError;
    private BigDecimal goalPlusError;
    private SubsetPredicateResult lowResult;
    private SubsetPredicateResult highResult;

    /**
     * @param adapter a function to extract {@link BigDecimal} values from the collection items
     * @param goal the target sum for the subsets
     */
    public BigDecimalSubsetPredicate(Function adapter, BigDecimal goal) {
        this(adapter, goal, BigDecimal.ZERO);
    }

    /**
     * @param adapter a function to extract {@link BigDecimal} values from the collection items
     * @param goal the target sum for the subsets
     * @param error margin of error for matching the target subset sum
     */
    public BigDecimalSubsetPredicate(Function adapter, BigDecimal goal, BigDecimal error) {
        this.adapter = adapter;
        this.goalMinusError = goal.subtract(error.abs());
        this.goalPlusError = goal.add(error.abs());
        this.lowResult = goal.signum() >= 0 ? SubsetPredicateResult.TOO_FEW : SubsetPredicateResult.TOO_MANY;
        this.highResult = goal.signum() >= 0 ? SubsetPredicateResult.TOO_MANY: SubsetPredicateResult.TOO_FEW;
    }

    public SubsetPredicateResult apply(T item) {
        total = adapter.apply(item).add(total);
        if (total.compareTo(goalMinusError) < 0) {
            return lowResult;
        }
        return total.compareTo(goalPlusError) > 0 ? highResult : SubsetPredicateResult.MATCH;
    }

    public void remove(T item) {
        total = total.subtract(adapter.apply(item));
    }

    public void reset() {
        total = BigDecimal.ZERO;
    }

    public String toString() {
        return "Total: " + total.toString() + " Goal: " + goalMinusError.toString() + " - " + goalPlusError.toString();
    }
}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy