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

cdc.applic.expressions.content.AbstractRange Maven / Gradle / Ivy

There is a newer version: 0.13.3
Show newest version
package cdc.applic.expressions.content;

import java.util.Comparator;
import java.util.Objects;

import cdc.applic.expressions.IllegalOperationException;
import cdc.util.lang.Checks;

/**
 * Base range implementation.
 * 

* The minimum value can be greater than the maximum one. In that case, the range is empty.
* Two empty ranges are considered as equal, whatever the bounds are. *

* Warning: The comparison algorithm is intended for internal use. * * @author Damien Carbonne * * @param The value type. * @param The range type. */ public abstract class AbstractRange, R extends AbstractRange> implements Range, Comparable { private final V min; private final V max; protected AbstractRange(V min, V max) { this.min = min; this.max = max; } protected AbstractRange(V value) { this.min = value; this.max = value; } private static IllegalArgumentException nonCompliantRange(Range range) { return new IllegalArgumentException("Non compliant range: " + range); } protected abstract R self(); public abstract Domain getDomain(); /** * Creates a Comparator based on min values. * * @param The value type. * @param The range type. * @return A new Comparator based on min values. */ public static , R extends AbstractRange> Comparator minComparator() { return Comparator.comparing(R::getMin); } /** * Creates a Comparator based on max values. * * @param The value type. * @param The range type. * @return A new Comparator based on max values. */ public static , R extends AbstractRange> Comparator maxComparator() { return Comparator.comparing(R::getMax); } /** * Creates a Comparator based on min, then max values. * * @param The value type. * @param The range type. * @return A new Comparator based on min, then max values. */ public static , R extends AbstractRange> Comparator minMaxComparator() { return Comparator.comparing(R::getMin) .thenComparing(R::getMax); } @Override public final V getMin() { return min; } @Override public final V getMax() { return max; } @Override public final boolean isEmpty() { return min.compareTo(max) > 0; } @Override public final boolean isSingleton() { return min.equals(max); } @Override public V getSingletonValue() { if (!isSingleton()) { throw new IllegalOperationException("This range is not a singleton " + this); } return min; } public final boolean containsValue(V v) { return min.compareTo(v) <= 0 && max.compareTo(v) >= 0; } @Override public final boolean contains(Value value) { if (getDomain().getValueClass().isInstance(value)) { return containsValue(getDomain().getValueClass().cast(value)); } else { throw new IllegalArgumentException("Non compliant value: " + value); } } public final boolean containsRange(R r) { return (min.compareTo(r.getMin()) <= 0 && max.compareTo(r.getMax()) >= 0) || r.isEmpty(); } @Override public final boolean contains(Range range) { if (getDomain().getRangeClass().isInstance(range)) { return containsRange(getDomain().getRangeClass().cast(range)); } else { throw nonCompliantRange(range); } } public final boolean intersectsRange(R r) { return RangeUtils.intersected(self(), r); } @Override public final boolean intersects(Range range) { if (getDomain().getRangeClass().isInstance(range)) { return intersectsRange(getDomain().getRangeClass().cast(range)); } else { throw nonCompliantRange(range); } } public final R intersectionWith(R range) { return RangeUtils.intersection(getDomain(), self(), range); } @Override public final R intersectionWith(Range range) { if (getDomain().getRangeClass().isInstance(range)) { return intersectionWith(getDomain().getRangeClass().cast(range)); } else { throw nonCompliantRange(range); } } @Override public final String getNonEscapedLiteral() { if (getMin().equals(getMax())) { return getMin().toString(); } else { final StringBuilder builder = new StringBuilder(); builder.append(getMin()); builder.append(BOUNDS_SEPARATOR); builder.append(getMax()); return builder.toString(); } } @Override public final String getProtectedLiteral() { return getNonEscapedLiteral(); } @Override public int compareTo(R o) { Checks.isFalse(isEmpty(), "Can not compare empty range"); Checks.isFalse(o.isEmpty(), "Can not compare empty range"); if (ComparableUtils.lessThan(max, o.getMin())) { return -1; } else if (ComparableUtils.greaterThan(min, o.getMax())) { return 1; } else { return 0; } } @Override public boolean equals(Object object) { if (this == object) { return true; } if (!(object instanceof AbstractRange)) { return false; } final AbstractRange other = (AbstractRange) object; return min.equals(other.min) && max.equals(other.max) || isEmpty() && other.isEmpty(); } @Override public int hashCode() { return isEmpty() ? 0 : Objects.hash(min, max); } @Override public String toString() { return getProtectedLiteral(); } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy