AbstractStorelessUnivariateStatistic.java

  1. /*
  2.  * Licensed to the Apache Software Foundation (ASF) under one or more
  3.  * contributor license agreements.  See the NOTICE file distributed with
  4.  * this work for additional information regarding copyright ownership.
  5.  * The ASF licenses this file to You under the Apache License, Version 2.0
  6.  * (the "License"); you may not use this file except in compliance with
  7.  * the License.  You may obtain a copy of the License at
  8.  *
  9.  *      http://www.apache.org/licenses/LICENSE-2.0
  10.  *
  11.  * Unless required by applicable law or agreed to in writing, software
  12.  * distributed under the License is distributed on an "AS IS" BASIS,
  13.  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  14.  * See the License for the specific language governing permissions and
  15.  * limitations under the License.
  16.  */
  17. package org.apache.commons.math4.legacy.stat.descriptive;

  18. import org.apache.commons.math4.legacy.exception.MathIllegalArgumentException;
  19. import org.apache.commons.math4.legacy.exception.NullArgumentException;
  20. import org.apache.commons.math4.legacy.exception.util.LocalizedFormats;
  21. import org.apache.commons.math4.legacy.core.MathArrays;
  22. import org.apache.commons.numbers.core.Precision;

  23. /**
  24.  * Abstract base class for implementations of the
  25.  * {@link StorelessUnivariateStatistic} interface.
  26.  * <p>
  27.  * Provides default {@code evaluate(double[],...)} and {@code incrementAll(double[])}
  28.  * implementations.
  29.  * <p>
  30.  * <strong>Note that these implementations are not synchronized.</strong>
  31.  */
  32. public abstract class AbstractStorelessUnivariateStatistic
  33.     implements StorelessUnivariateStatistic {

  34.     /**
  35.      * This default implementation creates a copy of this {@link StorelessUnivariateStatistic}
  36.      * instance, calls {@link #clear} on it, then calls {@link #incrementAll} with the specified
  37.      * portion of the input array, and then uses {@link #getResult} to compute the return value.
  38.      * <p>
  39.      * Note that this implementation does not change the internal state of the statistic.
  40.      * <p>
  41.      * Implementations may override this method with a more efficient and possibly more
  42.      * accurate implementation that works directly with the input array.
  43.      * <p>
  44.      * If the array is null, a MathIllegalArgumentException is thrown.
  45.      *
  46.      * @param values input array
  47.      * @return the value of the statistic applied to the input array
  48.      * @throws MathIllegalArgumentException if values is null
  49.      * @see org.apache.commons.math4.legacy.stat.descriptive.UnivariateStatistic#evaluate(double[])
  50.      */
  51.     @Override
  52.     public double evaluate(final double[] values) throws MathIllegalArgumentException {
  53.         if (values == null) {
  54.             throw new NullArgumentException(LocalizedFormats.INPUT_ARRAY);
  55.         }
  56.         return evaluate(values, 0, values.length);
  57.     }

  58.     /**
  59.      * This default implementation creates a copy of this {@link StorelessUnivariateStatistic}
  60.      * instance, calls {@link #clear} on it, then calls {@link #incrementAll} with the specified
  61.      * portion of the input array, and then uses {@link #getResult} to compute the return value.
  62.      * <p>
  63.      * Note that this implementation does not change the internal state of the statistic.
  64.      * <p>
  65.      * Implementations may override this method with a more efficient and possibly more
  66.      * accurate implementation that works directly with the input array.
  67.      * <p>
  68.      * If the array is null or the index parameters are not valid, an
  69.      * MathIllegalArgumentException is thrown.
  70.      *
  71.      * @param values the input array
  72.      * @param begin the index of the first element to include
  73.      * @param length the number of elements to include
  74.      * @return the value of the statistic applied to the included array entries
  75.      * @throws MathIllegalArgumentException if the array is null or the indices are not valid
  76.      * @see org.apache.commons.math4.legacy.stat.descriptive.UnivariateStatistic#evaluate(double[], int, int)
  77.      */
  78.     @Override
  79.     public double evaluate(final double[] values, final int begin, final int length)
  80.         throws MathIllegalArgumentException {

  81.         if (MathArrays.verifyValues(values, begin, length)) {
  82.             final StorelessUnivariateStatistic stat = copy();
  83.             stat.clear();
  84.             stat.incrementAll(values, begin, length);
  85.             return stat.getResult();
  86.         }
  87.         return Double.NaN;
  88.     }

  89.     /**
  90.      * {@inheritDoc}
  91.      */
  92.     @Override
  93.     public abstract StorelessUnivariateStatistic copy();

  94.     /**
  95.      * {@inheritDoc}
  96.      */
  97.     @Override
  98.     public abstract void clear();

  99.     /**
  100.      * {@inheritDoc}
  101.      */
  102.     @Override
  103.     public abstract double getResult();

  104.     /**
  105.      * {@inheritDoc}
  106.      */
  107.     @Override
  108.     public abstract void increment(double d);

  109.     /**
  110.      * This default implementation just calls {@link #increment} in a loop over
  111.      * the input array.
  112.      * <p>
  113.      * Throws IllegalArgumentException if the input values array is null.
  114.      *
  115.      * @param values values to add
  116.      * @throws MathIllegalArgumentException if values is null
  117.      * @see StorelessUnivariateStatistic#incrementAll(double[])
  118.      */
  119.     @Override
  120.     public void incrementAll(double[] values) throws MathIllegalArgumentException {
  121.         if (values == null) {
  122.             throw new NullArgumentException(LocalizedFormats.INPUT_ARRAY);
  123.         }
  124.         incrementAll(values, 0, values.length);
  125.     }

  126.     /**
  127.      * This default implementation just calls {@link #increment} in a loop over
  128.      * the specified portion of the input array.
  129.      * <p>
  130.      * Throws IllegalArgumentException if the input values array is null.
  131.      *
  132.      * @param values  array holding values to add
  133.      * @param begin   index of the first array element to add
  134.      * @param length  number of array elements to add
  135.      * @throws MathIllegalArgumentException if values is null
  136.      * @see StorelessUnivariateStatistic#incrementAll(double[], int, int)
  137.      */
  138.     @Override
  139.     public void incrementAll(double[] values, int begin, int length) throws MathIllegalArgumentException {
  140.         if (MathArrays.verifyValues(values, begin, length)) {
  141.             int k = begin + length;
  142.             for (int i = begin; i < k; i++) {
  143.                 increment(values[i]);
  144.             }
  145.         }
  146.     }

  147.     /**
  148.      * Returns true iff <code>object</code> is the same type of
  149.      * {@link StorelessUnivariateStatistic} (the object's class equals this
  150.      * instance) returning the same values as this for <code>getResult()</code>
  151.      * and <code>getN()</code>.
  152.      *
  153.      * @param object object to test equality against.
  154.      * @return true if object returns the same value as this
  155.      */
  156.     @Override
  157.     public boolean equals(Object object) {
  158.         if (object == this ) {
  159.             return true;
  160.         }
  161.         if (object == null || object.getClass() != this.getClass()) {
  162.             return false;
  163.         }
  164.         StorelessUnivariateStatistic stat = (StorelessUnivariateStatistic) object;
  165.         return Precision.equalsIncludingNaN(stat.getResult(), this.getResult()) &&
  166.                Precision.equalsIncludingNaN(stat.getN(), this.getN());
  167.     }

  168.     /**
  169.      * Returns hash code based on getResult() and getN().
  170.      *
  171.      * @return hash code
  172.      */
  173.     @Override
  174.     public int hashCode() {
  175.         return 31 * (31 + Double.hashCode(getResult())) + Double.hashCode(getN());
  176.     }
  177. }