You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@commons.apache.org by ps...@apache.org on 2007/12/08 03:48:40 UTC

svn commit: r602304 - in /commons/proper/math/trunk: src/java/org/apache/commons/math/stat/descriptive/ src/test/org/apache/commons/math/stat/descriptive/ xdocs/

Author: psteitz
Date: Fri Dec  7 18:48:39 2007
New Revision: 602304

URL: http://svn.apache.org/viewvc?rev=602304&view=rev
Log:
Deprecated abstract factory methods and made SummaryStatistics
a concrete classes. Pushed implementations up from SummaryStatisticsImpl.
Made implementations of statistics configurable via setters.

Added:
    commons/proper/math/trunk/src/test/org/apache/commons/math/stat/descriptive/SummaryStatisticsTest.java   (with props)
Modified:
    commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatistics.java
    commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatisticsImpl.java
    commons/proper/math/trunk/xdocs/changes.xml

Modified: commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatistics.java
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatistics.java?rev=602304&r1=602303&r2=602304&view=diff
==============================================================================
--- commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatistics.java (original)
+++ commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatistics.java Fri Dec  7 18:48:39 2007
@@ -19,24 +19,50 @@
 import java.io.Serializable;
 
 import org.apache.commons.discovery.tools.DiscoverClass;
+import org.apache.commons.math.stat.descriptive.moment.GeometricMean;
+import org.apache.commons.math.stat.descriptive.moment.Mean;
+import org.apache.commons.math.stat.descriptive.moment.SecondMoment;
+import org.apache.commons.math.stat.descriptive.moment.Variance;
+import org.apache.commons.math.stat.descriptive.rank.Max;
+import org.apache.commons.math.stat.descriptive.rank.Min;
+import org.apache.commons.math.stat.descriptive.summary.Sum;
+import org.apache.commons.math.stat.descriptive.summary.SumOfLogs;
+import org.apache.commons.math.stat.descriptive.summary.SumOfSquares;
 import org.apache.commons.math.util.MathUtils;
 
 /**
- * Abstract factory class for univariate statistical summaries.
+ * <p>Computes summary statistics for a stream of data values added using the 
+ * {@link #addValue(double) addValue} method. The data values are not stored in
+ * memory, so this class can be used to compute statistics for very large
+ * data streams.</p>
+ * 
+ * <p>The {@link StorelessUnivariateStatistic} instances used to maintain
+ * summary state and compute statistics are configurable via setters.
+ * For example, the default implementation for the variance can be overridden by
+ * calling {@link #setVarianceImpl(StorelessUnivariateStatistic)}. Actual
+ * parameters to these methods must implement the 
+ * {@link StorelessUnivariateStatistic} interface and configuration must be
+ * completed before <code>addValue</code> is called. No configuration is
+ * necessary to use the default, commons-math provided implementations.</p>
+ * 
+ * <p>Note: This class is not thread-safe. Use 
+ * {@link SynchronizedSummaryStatistics} if concurrent access from multiple
+ * threads is required.</p>
  *
  * @version $Revision$ $Date$
  */
-public abstract class SummaryStatistics implements StatisticalSummary, Serializable {
+public class SummaryStatistics implements StatisticalSummary, Serializable {
 
     /** Serialization UID */
-    private static final long serialVersionUID = -6400596334135654825L;
+    private static final long serialVersionUID = -3346512372447011854L;
      
     /**
      * Create an instance of a <code>SummaryStatistics</code>
      * 
      * @param cls the type of <code>SummaryStatistics</code> object to
      *        create. 
-     * @return a new factory. 
+     * @return a new instance. 
+     * @deprecated to be removed in commons-math 2.0
      * @throws InstantiationException is thrown if the object can not be
      *            created.
      * @throws IllegalAccessException is thrown if the type's default
@@ -50,7 +76,8 @@
     /**
      * Create an instance of a <code>SummaryStatistics</code>
      * 
-     * @return a new SummaryStatistics instance. 
+     * @return a new SummaryStatistics instance.
+     * @deprecated to be removed in commons-math 2.0 
      */
     public static SummaryStatistics newInstance() {
         SummaryStatistics instance = null;
@@ -65,6 +92,51 @@
         return instance;
     }
     
+    /**
+     * Construct a SummaryStatistics instance
+     */
+    public SummaryStatistics() {
+    }
+    
+    /** count of values that have been added */
+    protected long n = 0;
+    
+    /** SecondMoment is used to compute the mean and variance */
+    protected SecondMoment secondMoment = new SecondMoment();
+    
+    /** sum of values that have been added */
+    protected Sum sum = new Sum();
+
+    /** sum of the square of each value that has been added */
+    protected SumOfSquares sumsq = new SumOfSquares();
+
+    /** min of values that have been added */
+    protected Min min = new Min();
+
+    /** max of values that have been added */
+    protected Max max = new Max();
+
+    /** sumLog of values that have been added */
+    protected SumOfLogs sumLog = new SumOfLogs();
+
+    /** geoMean of values that have been added */
+    protected GeometricMean geoMean = new GeometricMean();
+
+    /** mean of values that have been added */
+    protected Mean mean = new Mean();
+
+    /** variance of values that have been added */
+    protected Variance variance = new Variance();
+    
+    //  Statistics implementations - can be reset by setters 
+    private StorelessUnivariateStatistic sumImpl = sum;
+    private StorelessUnivariateStatistic sumsqImpl = sumsq;
+    private StorelessUnivariateStatistic minImpl = min;
+    private StorelessUnivariateStatistic maxImpl = max;
+    private StorelessUnivariateStatistic sumLogImpl = sumLog;
+    private StorelessUnivariateStatistic geoMeanImpl = geoMean;
+    private StorelessUnivariateStatistic meanImpl = mean;
+    private StorelessUnivariateStatistic varianceImpl = variance;
 
     /**
      * Return a {@link StatisticalSummaryValues} instance reporting current
@@ -78,75 +150,177 @@
     }
     
     /**
-     * Adds the value to the data to be summarized
-     * @param v the value to be added 
+     * Add a value to the data
+     * 
+     * @param value  the value to add
      */
-    public abstract void addValue(double v);
+    public void addValue(double value) {
+        sumImpl.increment(value);
+        sumsqImpl.increment(value);
+        minImpl.increment(value);
+        maxImpl.increment(value);
+        sumLogImpl.increment(value);
+        geoMean.increment(value);
+        secondMoment.increment(value);
+        // If mean or variance have been overridden,
+        // need to increment these, since they don't have secondMoment
+        if (!(meanImpl instanceof Mean)) {
+                meanImpl.increment(value);
+        }
+        if (!(varianceImpl instanceof Variance)) {
+            varianceImpl.increment(value);
+        }
+        n++;
+    }
 
     /** 
-     * Returns the <a href="http://www.xycoon.com/arithmetic_mean.htm">
-     * arithmetic mean </a> of the available values 
-     * @return The mean or Double.NaN if no values have been added.
+     * Returns the number of available values
+     * @return The number of available values
      */
-    public abstract double getMean();
+    public long getN() {
+        return n;
+    }
 
-    /** 
-     * Returns the <a href="http://www.xycoon.com/geometric_mean.htm">
-     * geometric mean </a> of the available values
-     * @return The geometricMean, Double.NaN if no values have been added, 
-     * or if the productof the available values is less than or equal to 0.
+    /**
+     * Returns the sum of the values that have been added
+     * @return The sum or <code>Double.NaN</code> if no values have been added
      */
-    public abstract double getGeometricMean();
+    public double getSum() {
+        return sumImpl.getResult();
+    }
 
-    /** 
-     * Returns the variance of the available values.
-     * @return The variance, Double.NaN if no values have been added 
-     * or 0.0 for a single value set.  
+    /**
+     * Returns the sum of the squares of the values that have been added.
+     * <p>
+     *  Double.NaN is returned if no values have been added.</p>
+     * 
+     * @return The sum of squares
      */
-    public abstract double getVariance();
+    public double getSumsq() {
+        return sumsqImpl.getResult();
+    }
 
-    /** 
-     * Returns the standard deviation of the available values.
-     * @return The standard deviation, Double.NaN if no values have been added 
-     * or 0.0 for a single value set. 
+    /**
+     * Returns the mean of the values that have been added.
+     * <p>
+     *  Double.NaN is returned if no values have been added.</p>
+     * 
+     * @return the mean
      */
-    public abstract double getStandardDeviation();
-    
-    /** 
-     * Returns the maximum of the available values
-     * @return The max or Double.NaN if no values have been added.
+    public double getMean() {
+      if (mean == meanImpl) {
+          return new Mean(secondMoment).getResult();
+      } else {
+          return meanImpl.getResult();
+      }
+    }
+
+    /**
+     * Returns the standard deviation of the values that have been added.
+     * <p>
+     *  Double.NaN is returned if no values have been added.</p>
+     * 
+     * @return the standard deviation
      */
-    public abstract double getMax();
+    public double getStandardDeviation() {
+        double stdDev = Double.NaN;
+        if (getN() > 0) {
+            if (getN() > 1) {
+                stdDev = Math.sqrt(getVariance());
+            } else {
+                stdDev = 0.0;
+            }
+        }
+        return (stdDev);
+    }
 
-    /** 
-    * Returns the minimum of the available values
-    * @return The min or Double.NaN if no values have been added.
-    */
-    public abstract double getMin();
+    /**
+     * Returns the variance of the values that have been added.
+     * <p>
+     *  Double.NaN is returned if no values have been added.</p>
+     *
+     * @return the variance 
+     */
+    public double getVariance() {
+        if (varianceImpl == variance) {
+            return new Variance(secondMoment).getResult();
+        } else {
+            return varianceImpl.getResult();
+        }
+    }
 
-    /** 
-     * Returns the number of available values
-     * @return The number of available values
+    /**
+     * Returns the maximum of the values that have been added.
+     * <p>
+     *  Double.NaN is returned if no values have been added.</p>
+     *
+     * @return the maximum  
      */
-    public abstract long getN();
+    public double getMax() {
+        return maxImpl.getResult();
+    }
 
     /**
-     * Returns the sum of the values that have been added to Univariate.
-     * @return The sum or Double.NaN if no values have been added
+     * Returns the minimum of the values that have been added.
+     * <p>
+     *  Double.NaN is returned if no values have been added.</p>
+     *
+     * @return the minimum  
      */
-    public abstract double getSum();
+    public double getMin() {
+        return minImpl.getResult();
+    }
 
     /**
-     * Returns the sum of the squares of the available values.
-     * @return The sum of the squares or Double.NaN if no 
-     * values have been added.
+     * Returns the geometric mean of the values that have been added.
+     * <p>
+     *  Double.NaN is returned if no values have been added.</p>
+     *
+     * @return the geometric mean  
      */
-    public abstract double getSumsq();
+    public double getGeometricMean() {
+        return geoMeanImpl.getResult();
+    }
+    
+    /**
+     * Generates a text report displaying
+     * summary statistics from values that
+     * have been added.
+     * @return String with line feeds displaying statistics
+     */
+    public String toString() {
+        StringBuffer outBuffer = new StringBuffer();
+        outBuffer.append("SummaryStatistics:\n");
+        outBuffer.append("n: " + getN() + "\n");
+        outBuffer.append("min: " + getMin() + "\n");
+        outBuffer.append("max: " + getMax() + "\n");
+        outBuffer.append("mean: " + getMean() + "\n");
+        outBuffer.append("geometric mean: " + getGeometricMean() + "\n");
+        outBuffer.append("variance: " + getVariance() + "\n");
+        outBuffer.append("sum of squares: " + getSumsq() + "\n");
+        outBuffer.append("standard deviation: " + getStandardDeviation() + "\n");
+        return outBuffer.toString();
+    }
 
     /** 
-     * Resets all statistics
+     * Resets all statistics and storage
      */
-    public abstract void clear();
+    public void clear() {
+        this.n = 0;
+        minImpl.clear();
+        maxImpl.clear();
+        sumImpl.clear();
+        sumLogImpl.clear();
+        sumsqImpl.clear();
+        geoMeanImpl.clear();
+        secondMoment.clear();
+        if (meanImpl != mean) {
+            meanImpl.clear();
+        }
+        if (varianceImpl != variance) {
+            varianceImpl.clear();
+        }
+    }
     
     /**
      * Returns true iff <code>object</code> is a <code>SummaryStatistics</code>
@@ -189,6 +363,222 @@
         result = result * 31 + MathUtils.hash(getSumsq());
         result = result * 31 + MathUtils.hash(getVariance());
         return result;
+    }
+
+    // Getters and setters for statistics implementations
+    /**
+     * Returns the currently configured Sum implementation
+     * 
+     * @return the StorelessUnivariateStatistic implementing the sum
+     */
+    public synchronized StorelessUnivariateStatistic getSumImpl() {
+        return sumImpl;
+    }
+
+    /**
+     * <p>Sets the implementation for the Sum.</p>
+     * <p>This method must be activated before any data has been added - i.e.,
+     * before {@link #addValue(double) addValue} has been used to add data; 
+     * otherwise an IllegalStateException will be thrown.</p>
+     * 
+     * @param sumImpl the StorelessUnivariateStatistic instance to use
+     * for computing the Sum
+     * @throws IllegalStateException if data has already been added
+     *  (i.e if n > 0)
+     */
+    public synchronized void setSumImpl(StorelessUnivariateStatistic sumImpl) {
+        checkEmpty();
+        this.sumImpl = sumImpl;
+    }
+
+    /**
+     * Returns the currently configured sum of squares implementation
+     * 
+     * @return the StorelessUnivariateStatistic implementing the sum of squares
+     */
+    public synchronized StorelessUnivariateStatistic getSumsqImpl() {
+        return sumsqImpl;
+    }
+
+    /**
+     * <p>Sets the implementation for the sum of squares.</p>
+     * <p>This method must be activated before any data has been added - i.e.,
+     * before {@link #addValue(double) addValue} has been used to add data; 
+     * otherwise an IllegalStateException will be thrown.</p>
+     * 
+     * @param sumsqImpl the StorelessUnivariateStatistic instance to use
+     * for computing the sum of squares
+     * @throws IllegalStateException if data has already been added
+     *  (i.e if n > 0)
+     */
+    public synchronized void setSumsqImpl(
+            StorelessUnivariateStatistic sumsqImpl) {
+        checkEmpty();
+        this.sumsqImpl = sumsqImpl;
+    }
+
+    /**
+     * Returns the currently configured minimum implementation
+     * 
+     * @return the StorelessUnivariateStatistic implementing the minimum
+     */
+    public synchronized StorelessUnivariateStatistic getMinImpl() {
+        return minImpl;
+    }
+
+    /**
+     * <p>Sets the implementation for the minimum.</p>
+     * <p>This method must be activated before any data has been added - i.e.,
+     * before {@link #addValue(double) addValue} has been used to add data; 
+     * otherwise an IllegalStateException will be thrown.</p>
+     * 
+     * @param minImpl the StorelessUnivariateStatistic instance to use
+     * for computing the minimum
+     * @throws IllegalStateException if data has already been added
+     *  (i.e if n > 0)
+     */
+    public synchronized void setMinImpl(StorelessUnivariateStatistic minImpl) {
+        checkEmpty();
+        this.minImpl = minImpl;
+    }
+
+    /**
+     * Returns the currently configured maximum implementation
+     * 
+     * @return the StorelessUnivariateStatistic implementing the maximum
+     */
+    public synchronized StorelessUnivariateStatistic getMaxImpl() {
+        return maxImpl;
+    }
+
+    /**
+     * <p>Sets the implementation for the maximum.</p>
+     * <p>This method must be activated before any data has been added - i.e.,
+     * before {@link #addValue(double) addValue} has been used to add data; 
+     * otherwise an IllegalStateException will be thrown.</p>
+     * 
+     * @param maxImpl the StorelessUnivariateStatistic instance to use
+     * for computing the maximum
+     * @throws IllegalStateException if data has already been added
+     *  (i.e if n > 0)
+     */
+    public synchronized void setMaxImpl(StorelessUnivariateStatistic maxImpl) {
+        checkEmpty();
+        this.maxImpl = maxImpl;
+    }
+
+    /**
+     * Returns the currently configured sum of logs implementation
+     * 
+     * @return the StorelessUnivariateStatistic implementing the log sum
+     */
+    public synchronized StorelessUnivariateStatistic getSumLogImpl() {
+        return sumLogImpl;
+    }
+
+    /**
+     * <p>Sets the implementation for the sum of logs.</p>
+     * <p>This method must be activated before any data has been added - i.e.,
+     * before {@link #addValue(double) addValue} has been used to add data; 
+     * otherwise an IllegalStateException will be thrown.</p>
+     * 
+     * @param sumLogImpl the StorelessUnivariateStatistic instance to use
+     * for computing the log sum
+     * @throws IllegalStateException if data has already been added 
+     *  (i.e if n > 0)
+     */
+    public synchronized void setSumLogImpl(
+            StorelessUnivariateStatistic sumLogImpl) {
+        checkEmpty();
+        this.sumLogImpl = sumLogImpl;
+    }
+
+    /**
+     * Returns the currently configured geometric mean implementation
+     * 
+     * @return the StorelessUnivariateStatistic implementing the geometric mean
+     */
+    public synchronized StorelessUnivariateStatistic getGeoMeanImpl() {
+        return geoMeanImpl;
+    }
+
+    /**
+     * <p>Sets the implementation for the geometric mean.</p>
+     * <p>This method must be activated before any data has been added - i.e.,
+     * before {@link #addValue(double) addValue} has been used to add data; 
+     * otherwise an IllegalStateException will be thrown.</p>
+     * 
+     * @param geoMeanImpl the StorelessUnivariateStatistic instance to use
+     * for computing the geometric mean
+     * @throws IllegalStateException if data has already been added
+     *  (i.e if n > 0)
+     */
+    public synchronized void setGeoMeanImpl(
+            StorelessUnivariateStatistic geoMeanImpl) {
+        checkEmpty();
+        this.geoMeanImpl = geoMeanImpl;
+    }
+
+    /**
+     * Returns the currently configured mean implementation
+     * 
+     * @return the StorelessUnivariateStatistic implementing the mean
+     */
+    public synchronized StorelessUnivariateStatistic getMeanImpl() {
+        return meanImpl;
+    }
+
+    /**
+     * <p>Sets the implementation for the mean.</p>
+     * <p>This method must be activated before any data has been added - i.e.,
+     * before {@link #addValue(double) addValue} has been used to add data; 
+     * otherwise an IllegalStateException will be thrown.</p>
+     * 
+     * @param meanImpl the StorelessUnivariateStatistic instance to use
+     * for computing the mean
+     * @throws IllegalStateException if data has already been added
+     *  (i.e if n > 0)
+     */
+    public synchronized void setMeanImpl(
+            StorelessUnivariateStatistic meanImpl) {
+        checkEmpty();
+        this.meanImpl = meanImpl;
+    }
+
+    /**
+     * Returns the currently configured variance implementation
+     * 
+     * @return the StorelessUnivariateStatistic implementing the variance
+     */
+    public synchronized StorelessUnivariateStatistic getVarianceImpl() {
+        return varianceImpl;
+    }
+
+    /**
+     * <p>Sets the implementation for the variance.</p>
+     * <p>This method must be activated before any data has been added - i.e.,
+     * before {@link #addValue(double) addValue} has been used to add data; 
+     * otherwise an IllegalStateException will be thrown.</p>
+     * 
+     * @param varianceImpl the StorelessUnivariateStatistic instance to use
+     * for computing the variance
+     * @throws IllegalStateException if data has already been added
+     *  (i.e if n > 0)
+     */
+    public synchronized void setVarianceImpl(
+            StorelessUnivariateStatistic varianceImpl) {
+        checkEmpty();
+        this.varianceImpl = varianceImpl;
+    }
+    
+    /**
+     * Throws IllegalStateException if n > 0.
+     */
+    private void checkEmpty() {
+        if (n > 0) {
+            throw new IllegalStateException(
+                "Implementations must be configured before values are added.");
+        }
     }
 
 }

Modified: commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatisticsImpl.java
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatisticsImpl.java?rev=602304&r1=602303&r2=602304&view=diff
==============================================================================
--- commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatisticsImpl.java (original)
+++ commons/proper/math/trunk/src/java/org/apache/commons/math/stat/descriptive/SummaryStatisticsImpl.java Fri Dec  7 18:48:39 2007
@@ -17,218 +17,27 @@
 package org.apache.commons.math.stat.descriptive;
 
 import java.io.Serializable;
-import org.apache.commons.math.stat.descriptive.moment.SecondMoment;
-import org.apache.commons.math.stat.descriptive.moment.GeometricMean;
-import org.apache.commons.math.stat.descriptive.moment.Mean;
-import org.apache.commons.math.stat.descriptive.moment.Variance;
-import org.apache.commons.math.stat.descriptive.rank.Max;
-import org.apache.commons.math.stat.descriptive.rank.Min;
-import org.apache.commons.math.stat.descriptive.summary.Sum;
-import org.apache.commons.math.stat.descriptive.summary.SumOfLogs;
-import org.apache.commons.math.stat.descriptive.summary.SumOfSquares;
 
 /**
  * Provides a default {@link SummaryStatistics} implementation.
- *
+ * 
+ * @deprecated to be removed in commons math 2.0.  Use {@link SummaryStatistics}.
  * @version $Revision$ $Date$  
  */
 public class SummaryStatisticsImpl extends SummaryStatistics implements Serializable {
 
     /** Serializable version identifier */
-    private static final long serialVersionUID = 8787174276883311692L;
-
-    /** count of values that have been added */
-    protected long n = 0;
-    
-    /** SecondMoment is used to compute the mean and variance */
-    protected SecondMoment secondMoment = null;
-    
-    /** sum of values that have been added */
-    protected Sum sum = null;
-
-    /** sum of the square of each value that has been added */
-    protected SumOfSquares sumsq = null;
-
-    /** min of values that have been added */
-    protected Min min = null;
-
-    /** max of values that have been added */
-    protected Max max = null;
-
-    /** sumLog of values that have been added */
-    protected SumOfLogs sumLog = null;
-
-    /** geoMean of values that have been added */
-    protected GeometricMean geoMean = null;
-
-    /** mean of values that have been added */
-    protected Mean mean = null;
-
-    /** variance of values that have been added */
-    protected Variance variance = null;
+    private static final long serialVersionUID = 8528794411480425963L;
 
     /**
      * Construct a SummaryStatistics
      */
     public SummaryStatisticsImpl() {
-        sum = new Sum();
-        sumsq = new SumOfSquares();
-        min = new Min();
-        max = new Max();
-        sumLog = new SumOfLogs();
-        geoMean = new GeometricMean();
-        secondMoment = new SecondMoment();
-    }
-
-    /**
-     * Add a value to the data
-     * 
-     * @param value  the value to add
-     */
-    public void addValue(double value) {
-        sum.increment(value);
-        sumsq.increment(value);
-        min.increment(value);
-        max.increment(value);
-        sumLog.increment(value);
-        geoMean.increment(value);
-        secondMoment.increment(value);
-        n++;
-    }
-
-    /** 
-     * Returns the number of available values
-     * @return The number of available values
-     */
-    public long getN() {
-        return n;
-    }
-
-    /**
-     * Returns the sum of the values that have been added to Univariate.
-     * @return The sum or Double.NaN if no values have been added
-     */
-    public double getSum() {
-        return sum.getResult();
-    }
-
-    /**
-     * Returns the sum of the squares of the values that have been added.
-     * <p>
-     *  Double.NaN is returned if no values have been added.</p>
-     * 
-     * @return The sum of squares
-     */
-    public double getSumsq() {
-        return sumsq.getResult();
-    }
-
-    /**
-     * Returns the mean of the values that have been added.
-     * <p>
-     *  Double.NaN is returned if no values have been added.</p>
-     * 
-     * @return the mean
-     */
-    public double getMean() {
-      return new Mean(secondMoment).getResult();
-    }
-
-    /**
-     * Returns the standard deviation of the values that have been added.
-     * <p>
-     *  Double.NaN is returned if no values have been added.</p>
-     * 
-     * @return the standard deviation
-     */
-    public double getStandardDeviation() {
-        double stdDev = Double.NaN;
-        if (getN() > 0) {
-            if (getN() > 1) {
-                stdDev = Math.sqrt(getVariance());
-            } else {
-                stdDev = 0.0;
-            }
-        }
-        return (stdDev);
-    }
-
-    /**
-     * Returns the variance of the values that have been added.
-     * <p>
-     *  Double.NaN is returned if no values have been added.</p>
-     *
-     * @return the variance 
-     */
-    public double getVariance() {
-        return new Variance(secondMoment).getResult();
-    }
-
-    /**
-     * Returns the maximum of the values that have been added.
-     * <p>
-     *  Double.NaN is returned if no values have been added.</p>
-     *
-     * @return the maximum  
-     */
-    public double getMax() {
-        return max.getResult();
-    }
-
-    /**
-     * Returns the minimum of the values that have been added.
-     * <p>
-     *  Double.NaN is returned if no values have been added.</p>
-     *
-     * @return the minimum  
-     */
-    public double getMin() {
-        return min.getResult();
-    }
-
-    /**
-     * Returns the geometric mean of the values that have been added.
-     * <p>
-     *  Double.NaN is returned if no values have been added.</p>
-     *
-     * @return the geometric mean  
-     */
-    public double getGeometricMean() {
-        return geoMean.getResult();
+        super();
     }
     
-    /**
-     * Generates a text report displaying
-     * summary statistics from values that
-     * have been added.
-     * @return String with line feeds displaying statistics
-     */
-    public String toString() {
-        StringBuffer outBuffer = new StringBuffer();
-        outBuffer.append("SummaryStatistics:\n");
-        outBuffer.append("n: " + getN() + "\n");
-        outBuffer.append("min: " + getMin() + "\n");
-        outBuffer.append("max: " + getMax() + "\n");
-        outBuffer.append("mean: " + getMean() + "\n");
-        outBuffer.append("geometric mean: " + getGeometricMean() + "\n");
-        outBuffer.append("variance: " + getVariance() + "\n");
-        outBuffer.append("sum of squares: " + getSumsq() + "\n");
-        outBuffer.append("standard deviation: " + getStandardDeviation() + "\n");
-        return outBuffer.toString();
-    }
-
-    /** 
-     * Resets all statistics and storage
-     */
     public void clear() {
-        this.n = 0;
-        min.clear();
-        max.clear();
-        sum.clear();
-        sumLog.clear();
-        sumsq.clear();
-        geoMean.clear();
-        secondMoment.clear();
+        super.clear();
     }
 
 }

Added: commons/proper/math/trunk/src/test/org/apache/commons/math/stat/descriptive/SummaryStatisticsTest.java
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/test/org/apache/commons/math/stat/descriptive/SummaryStatisticsTest.java?rev=602304&view=auto
==============================================================================
--- commons/proper/math/trunk/src/test/org/apache/commons/math/stat/descriptive/SummaryStatisticsTest.java (added)
+++ commons/proper/math/trunk/src/test/org/apache/commons/math/stat/descriptive/SummaryStatisticsTest.java Fri Dec  7 18:48:39 2007
@@ -0,0 +1,108 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License.  You may obtain a copy of the License at
+ * 
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.apache.commons.math.stat.descriptive;
+
+
+import junit.framework.Test;
+import junit.framework.TestCase;
+import junit.framework.TestSuite;
+
+import org.apache.commons.math.TestUtils;
+import org.apache.commons.math.stat.descriptive.moment.Mean;
+/**
+ * Test cases for the {@link SummaryStatistics} class.
+ * When SummaryStatisticsImpl is removed in math 2.0, test cases from
+ * SummaryStatisticsImplTest should be merged into this class.
+ *
+ * @version $Revision: 566833 $ $Date: 2007-08-16 13:36:33 -0700 (Thu, 16 Aug 2007) $
+ */
+
+public final class SummaryStatisticsTest extends TestCase {
+    
+    protected SummaryStatistics u = null;
+    
+    public SummaryStatisticsTest(String name) {
+        super(name);
+    }
+    
+    public void setUp() {  
+        u = new SummaryStatistics();
+    }
+    
+    public static Test suite() {
+        TestSuite suite = new TestSuite(SummaryStatisticsTest.class);
+        suite.setName("SummaryStatistics tests");
+        return suite;
+    }
+    
+    public void testSetterInjection() throws Exception {
+        u.setMeanImpl(new sumMean());
+        u.addValue(1);
+        u.addValue(3);
+        assertEquals(4, u.getMean(), 1E-14);
+        u.clear();
+        u.addValue(1);
+        u.addValue(2);
+        assertEquals(3, u.getMean(), 1E-14);
+        u.clear();
+        u.setMeanImpl(new Mean()); // OK after clear
+    }
+    
+    public void testSetterIllegalState() throws Exception {
+        u.addValue(1);
+        u.addValue(3);
+        try {
+            u.setMeanImpl(new sumMean());
+            fail("Expecting IllegalStateException");
+        } catch (IllegalStateException ex) {
+            // expected
+        }
+    }
+    
+    /**
+     * Bogus mean implementation to test setter injection.
+     * Returns the sum instead of the mean.
+     */
+    class sumMean implements StorelessUnivariateStatistic {   
+        private double sum = 0;
+        private long n = 0;
+        public double evaluate(double[] values, int begin, int length) {
+            return 0;
+        }
+        public double evaluate(double[] values) {
+            return 0;
+        }
+        public void clear() {
+          sum = 0; 
+          n = 0;
+        }
+        public long getN() {
+            return n;
+        }
+        public double getResult() {
+            return sum;
+        }
+        public void increment(double d) {
+            sum += d;
+            n++;
+        }
+        public void incrementAll(double[] values, int start, int length) {
+        }
+        public void incrementAll(double[] values) {
+        }   
+    }  
+}

Propchange: commons/proper/math/trunk/src/test/org/apache/commons/math/stat/descriptive/SummaryStatisticsTest.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: commons/proper/math/trunk/xdocs/changes.xml
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/xdocs/changes.xml?rev=602304&r1=602303&r2=602304&view=diff
==============================================================================
--- commons/proper/math/trunk/xdocs/changes.xml (original)
+++ commons/proper/math/trunk/xdocs/changes.xml Fri Dec  7 18:48:39 2007
@@ -107,10 +107,10 @@
         static factory method to Complex.
       </action>
       <action dev="psteitz" type="update">
-        Deprecated abstract factory methods and made DescriptiveStatistics a
-        concrete class. Pushed implementations up from DescriptiveStatisticsImpl
-        and deprecated this class. Made implementations of statistics
-        configurable via setters.
+        Deprecated abstract factory methods and made DescriptiveStatistics and
+        and SummaryStatistics concrete classes. Pushed implementations up
+        from DescriptiveStatisticsImpl, SummaryStatisticsImpl. Made
+        implementations of statistics configurable via setters.
       </action>    
     </release>
     <release version="1.1" date="2005-12-17"