# Class MeasurementRange<E extends Number & Comparable<? super E>>

Object
Range<E>
NumberRange<E>
MeasurementRange<E>

Type Parameters:
  `E` - the type of range elements as a subclass of `Number`.

All Implemented Interfaces:
  `Serializable`, `Formattable`, `CheckedContainer<E>`, `Emptiable`

public class MeasurementRange<E extends Number & Comparable<? super E>> extends NumberRange<E>
A range of numbers associated with a unit of measurement. All operations performed by this class (union, intersection, etc.) are performed in the unit of measurement of `this` range object - values of the range object given in argument are converted if needed before an operation is applied.

Other methods defined in this class:

- Convenience `create(…)` static methods for every floating point primitive types. Usage of `MeasurementRange` with integer types is possible, but no convenience method is provided for integers because they are usually not representative of the nature of physical measurements.
- `unit()` for getting the unit of measurement associated to this range.
- `convertTo(Unit)` for converting the unit of measurement.
- `castTo(Class)` for casting the range values to another type.

## Null unit of measurement

The unit of measurement should not be null, otherwise a `NumberRange` should be used instead of `MeasurementRange`. Nevertheless this class is tolerant to `null` units in order to support situations where a unit of measurement should be specified, but for some reason is unavailable. If the unit of measurement become known at a later stage, it can be specified by a call to `convertTo(Unit)`.

## Immutability and thread safety

This class is immutable and thus inherently thread-safe. Subclasses may or may not be immutable, at implementation choice. But implementers are encouraged to make sure that subclasses remain immutable for more predictable behavior.

Since:
  0.3
See Also:
  - `RangeFormat`
  - `RangeSet`
  - Serialized Form

- ## Constructor Summary

  Constructors
  Constructor
  Description
  `MeasurementRange(Class<E> type, E minValue, boolean isMinIncluded, E maxValue, boolean isMaxIncluded, Unit<?> unit)`
  Constructs a range of `Number` objects.
  `MeasurementRange(Class<E> type, ValueRange range, Unit<?> unit)`
  Constructs a range of the given type with values from the given annotation.
  `MeasurementRange(Range<E> range, Unit<?> unit)`
  Constructs a range with the same values as the specified range and the given unit.

- ## Method Summary

  Modifier and Type
  Method
  Description
  `<N extends Number & Comparable<? super N>>
  MeasurementRange<N>`
  `castTo(Class<N> type)`
  Casts this range to the specified type.
  `boolean`
  `contains(Range<? extends E> range)`
  Returns `true` if the supplied range is fully contained within this range.
  `MeasurementRange<E>`
  `convertTo(Unit<?> targetUnit)`
  Converts this range to the specified unit.
  `static MeasurementRange<Double>`
  `create(double minValue, boolean isMinIncluded, double maxValue, boolean isMaxIncluded, Unit<?> unit)`
  Constructs a range of `double` values.
  `static MeasurementRange<Float>`
  `create(float minValue, boolean isMinIncluded, float maxValue, boolean isMaxIncluded, Unit<?> unit)`
  Constructs a range of `float` values.
  `static MeasurementRange<?>`
  `createBestFit(Number minValue, boolean isMinIncluded, Number maxValue, boolean isMaxIncluded, Unit<?> unit)`
  Constructs a range using the smallest type of `Number` that can hold the given values.
  `static MeasurementRange<Double>`
  `createGreaterThan(double minValue, Unit<?> unit)`
  Constructs a range of `double` values greater than the given value.
  `boolean`
  `equals(Object object)`
  Compares this measurement range with the specified object for equality.
  `int`
  `hashCode()`
  Returns a hash code value for this measurement range.
  `Range<E>`
  `intersect(Range<E> range)`
  Returns the intersection between this range and the given range.
  `boolean`
  `intersects(Range<? extends E> range)`
  Returns `true` if this range intersects the given range.
  `Range<E>[]`
  `subtract(Range<E> range)`
  Returns the range of values that are in this range but not in the given range.
  `Range<E>`
  `union(Range<E> range)`
  Returns the union of this range with the given range.
  `Unit<?>`
  `unit()`
  Returns the unit of measurement, or `null` if unknown.

  ### Methods inherited from class NumberRange

  `castOrCopy, containsAny, containsAny, create, create, create, create, create, create, create, createBestFit, createBestFit, createLeftBounded, getMaxDouble, getMaxDouble, getMedian, getMinDouble, getMinDouble, getSpan, intersectAny, intersectsAny, subtractAny, transform, unionAny`

  ### Methods inherited from class Range

  `contains, formatTo, getElementType, getMaxValue, getMinValue, isBounded, isEmpty, isMaxIncluded, isMinIncluded, toString`

  ### Methods inherited from class Object

  `clone, finalize, getClass, notify, notifyAll, wait, wait, wait`

- ## Constructor Details

  - ### MeasurementRange

    public MeasurementRange(Range<E> range, Unit<?> unit)
    Constructs a range with the same values as the specified range and the given unit. This is a copy constructor, with the addition of a unit of measurement.
    Parameters:
      `range` - the range to copy. The elements must be `Number` instances.
      `unit` - the unit of measurement, or `null` if unknown.

  - ### MeasurementRange

    public MeasurementRange(Class<E> type, ValueRange range, Unit<?> unit) throws IllegalArgumentException
    Constructs a range of the given type with values from the given annotation. This constructor does not verify if the given type is wide enough for the values of the given annotation, because those information are usually static. If nevertheless the given type is not wide enough, then the values are truncated in the same way than the Java language casts primitive types.
    Parameters:
      `type` - the element type, restricted to one of `Byte`, `Short`, `Integer`, `Long`, `Float` or `Double`.
      `range` - the range of values.
      `unit` - the unit of measurement, or `null` if unknown.
    Throws:
      `IllegalArgumentException` - if the given type is not one of the primitive wrappers for numeric types.

  - ### MeasurementRange

    public MeasurementRange(Class<E> type, E minValue, boolean isMinIncluded, E maxValue, boolean isMaxIncluded, Unit<?> unit)
    Constructs a range of `Number` objects.
    Parameters:
      `type` - the element type, usually one of `Float` or `Double`.
      `minValue` - the minimal value, or `null` if none.
      `isMinIncluded` - `true` if the minimal value is inclusive, or `false` if exclusive.
      `maxValue` - the maximal value, or `null` if none.
      `isMaxIncluded` - `true` if the maximal value is inclusive, or `false` if exclusive.
      `unit` - the unit of measurement, or `null` if unknown.

- ## Method Details

  - ### create

    public static MeasurementRange<Float> create(float minValue, boolean isMinIncluded, float maxValue, boolean isMaxIncluded, Unit<?> unit)
    Constructs a range of `float` values. The minimum and maximum values cannot be NaN but can be infinite. If the minimum is greater than the maximum, then the range is empty. This method may return a shared instance, at implementation choice.
    Parameters:
      `minValue` - the minimal value, or `Float​.NEGATIVE_INFINITY` if none.
      `isMinIncluded` - `true` if the minimal value is inclusive, or `false` if exclusive.
      `maxValue` - the maximal value, or `Float​.POSITIVE_INFINITY` if none.
      `isMaxIncluded` - `true` if the maximal value is inclusive, or `false` if exclusive.
      `unit` - the unit of measurement, or `null` if unknown.
    Returns:
      the new range of numeric values for the given endpoints and unit of measurement.
    Throws:
      `IllegalArgumentException` - if `Float​.isNaN(float)` is `true` for a given value.

  - ### create

    public static MeasurementRange<Double> create(double minValue, boolean isMinIncluded, double maxValue, boolean isMaxIncluded, Unit<?> unit)
    Constructs a range of `double` values. The minimum and maximum values cannot be NaN but can be infinite. If the minimum is greater than the maximum, then the range is empty. This method may return a shared instance, at implementation choice.
    Parameters:
      `minValue` - the minimal value, or `Double​.NEGATIVE_INFINITY` if none.
      `isMinIncluded` - `true` if the minimal value is inclusive, or `false` if exclusive.
      `maxValue` - the maximal value, or `Double​.POSITIVE_INFINITY` if none.
      `isMaxIncluded` - `true` if the maximal value is inclusive, or `false` if exclusive.
      `unit` - the unit of measurement, or `null` if unknown.
    Returns:
      the new range of numeric values for the given endpoints and unit of measurement.
    Throws:
      `IllegalArgumentException` - if `Double​.isNaN(double)` is `true` for a given value.

  - ### createGreaterThan

    public static MeasurementRange<Double> createGreaterThan(double minValue, Unit<?> unit)
    Constructs a range of `double` values greater than the given value. The `minValue` is often zero for creating a range of strictly positive values. This method may return a shared instance, at implementation choice.
    Parameters:
      `minValue` - the minimal value (exclusive), or `Double​.NEGATIVE_INFINITY` if none.
      `unit` - the unit of measurement, or `null` if unknown.
    Returns:
      the new range of numeric values greater than the given value.
    Throws:
      `IllegalArgumentException` - if `Double​.isNaN(double)` is `true` for the given value.
    Since:
      0.6

  - ### createBestFit

    public static MeasurementRange<?> createBestFit(Number minValue, boolean isMinIncluded, Number maxValue, boolean isMaxIncluded, Unit<?> unit)
    Constructs a range using the smallest type of `Number` that can hold the given values. This method performs the same work as `NumberRange​.createBestFit(…)` with an additional `unit` argument.

    This method may return a shared instance, at implementation choice.

    Parameters:
      `minValue` - the minimal value, or `null` if none.
      `isMinIncluded` - `true` if the minimal value is inclusive, or `false` if exclusive.
      `maxValue` - the maximal value, or `null` if none.
      `isMaxIncluded` - `true` if the maximal value is inclusive, or `false` if exclusive.
      `unit` - the unit of measurement, or `null` if unknown.
    Returns:
      the new range, or `null` if both `minValue` and `maxValue` are `null`.
    See Also:
      - `NumberRange​.createBestFit(Number, boolean, Number, boolean)`

  - ### unit

    public Unit<?> unit()
    Returns the unit of measurement, or `null` if unknown. In principle the unit should never be null, otherwise a `NumberRange` should have been used instead of `MeasurementRange`. Nevertheless this method may return `null` if a unit should exist but for some reason is unavailable.
    Returns:
      the unit of measurement, or `null`.

  - ### convertTo

    public MeasurementRange<E> convertTo(Unit<?> targetUnit) throws IncommensurableException
    Converts this range to the specified unit. If this measurement range has null unit, then the specified target unit are simply assigned to the returned range with no other changes.
    Parameters:
      `targetUnit` - the target unit, or `null` for keeping the unit unchanged.
    Returns:
      the converted range, or `this` if no conversion is needed.
    Throws:
      `IncommensurableException` - if the target unit are not compatible with this range unit.

  - ### castTo

    public <N extends Number & Comparable<? super N>> MeasurementRange<N> castTo(Class<N> type)
    Casts this range to the specified type. If the cast from this range type to the given type is a narrowing conversion, then the cast is performed according the rules of the Java language: the high-order bytes are silently dropped.
    Overrides:
      `castTo` in class `NumberRange<E extends Number & Comparable<? super E>>`
    Type Parameters:
      `N` - the class to cast to.
    Parameters:
      `type` - the class to cast to. Must be one of `Byte`, `Short`, `Integer`, `Long`, `Float` or `Double`.
    Returns:
      the cast range, or `this` if this range already uses the specified type.

  - ### contains

    public boolean contains(Range<? extends E> range) throws IllegalArgumentException
    Returns `true` if the supplied range is fully contained within this range. If the given range is an instance of `MeasurementRange`, then this method converts the value of the other range to the unit of measurement of this range before to perform the operation.
    Overrides:
      `contains` in class `Range<E extends Number & Comparable<? super E>>`
    Parameters:
      `range` - the range to check for inclusion in this range.
    Returns:
      `true` if the given range is included in this range.
    Throws:
      `IllegalArgumentException` - if the given range is an instance of `MeasurementRange` using incommensurable unit of measurement.

  - ### intersects

    public boolean intersects(Range<? extends E> range) throws IllegalArgumentException
    Returns `true` if this range intersects the given range. If the given range is an instance of `MeasurementRange`, then this method converts the value of the other range to the unit of measurement of this range before to perform the operation.
    Overrides:
      `intersects` in class `Range<E extends Number & Comparable<? super E>>`
    Parameters:
      `range` - the range to check for intersection with this range.
    Returns:
      `true` if the given range intersects this range.
    Throws:
      `IllegalArgumentException` - if the given range is an instance of `MeasurementRange` using incommensurable unit of measurement.

  - ### intersect

    public Range<E> intersect(Range<E> range) throws IllegalArgumentException
    Returns the intersection between this range and the given range. If the given range is an instance of `MeasurementRange`, then this method converts the value of the other range to the unit of measurement of this range before to perform the operation.
    Overrides:
      `intersect` in class `Range<E extends Number & Comparable<? super E>>`
    Parameters:
      `range` - the range to intersect.
    Returns:
      the intersection of this range with the given range.
    Throws:
      `IllegalArgumentException` - if the given range is an instance of `MeasurementRange` using incommensurable unit of measurement.

  - ### union

    public Range<E> union(Range<E> range) throws IllegalArgumentException
    Returns the union of this range with the given range. If the given range is an instance of `MeasurementRange`, then this method converts the value of the other range to the unit of measurement of this range before to perform the operation.
    Overrides:
      `union` in class `Range<E extends Number & Comparable<? super E>>`
    Parameters:
      `range` - the range to add to this range.
    Returns:
      the union of this range with the given range.
    Throws:
      `IllegalArgumentException` - if the given range is an instance of `MeasurementRange` using incommensurable unit of measurement.

  - ### subtract

    public Range<E>[] subtract(Range<E> range) throws IllegalArgumentException
    Returns the range of values that are in this range but not in the given range. This method returns an array of length 0, 1 or 2:
    - If the given range contains fully this range, returns an array of length 0.
    - If the given range is in the middle of this range, then the subtraction results in two disjoint ranges which will be returned as two elements in the array.
    - Otherwise returns an array of length 1.
    If the given range is an instance of `MeasurementRange`, then this method converts the value of the other range to the unit of measurement of this range before to perform the operation.
    Overrides:
      `subtract` in class `Range<E extends Number & Comparable<? super E>>`
    Parameters:
      `range` - the range to subtract.
    Returns:
      this range without the given range, as an array of length 0, 1 or 2.
    Throws:
      `IllegalArgumentException` - if the given range is an instance of `MeasurementRange` using incommensurable unit of measurement.

  - ### equals

    public boolean equals(Object object)
    Compares this measurement range with the specified object for equality. Two `MeasurementRange` instances are considered equal if they met all conditions documented in the parent class and their `unit()` are equal in the sense of `Objects​.equals(Object, Object)`. Note that this comparison does not distinguish the various `Float​.NaN` or `Double​.NaN` bit patterns.
    Overrides:
      `equals` in class `Range<E extends Number & Comparable<? super E>>`
    Parameters:
      `object` - the object to compare with this range for equality.
    Returns:
      `true` if the given object is equal to this range.

  - ### hashCode

    public int hashCode()
    Returns a hash code value for this measurement range.
    Overrides:
      `hashCode` in class `Range<E extends Number & Comparable<? super E>>`
    Returns: