commons-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From pste...@apache.org
Subject svn commit: r743688 - in /commons/proper/math/trunk/src: java/org/apache/commons/math/stat/correlation/ site/xdoc/ test/R/ test/org/apache/commons/math/stat/correlation/
Date Thu, 12 Feb 2009 11:21:55 GMT
Author: psteitz
Date: Thu Feb 12 11:21:54 2009
New Revision: 743688

URL: http://svn.apache.org/viewvc?rev=743688&view=rev
Log:
Added correlation package, Covariance class.  JIRA: MATH-114

Added:
    commons/proper/math/trunk/src/java/org/apache/commons/math/stat/correlation/
    commons/proper/math/trunk/src/java/org/apache/commons/math/stat/correlation/Covariance.java
  (with props)
    commons/proper/math/trunk/src/test/R/covarianceTestCases
    commons/proper/math/trunk/src/test/org/apache/commons/math/stat/correlation/
    commons/proper/math/trunk/src/test/org/apache/commons/math/stat/correlation/CovarianceTest.java
  (with props)
Modified:
    commons/proper/math/trunk/src/site/xdoc/changes.xml
    commons/proper/math/trunk/src/test/R/testAll

Added: commons/proper/math/trunk/src/java/org/apache/commons/math/stat/correlation/Covariance.java
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/java/org/apache/commons/math/stat/correlation/Covariance.java?rev=743688&view=auto
==============================================================================
--- commons/proper/math/trunk/src/java/org/apache/commons/math/stat/correlation/Covariance.java
(added)
+++ commons/proper/math/trunk/src/java/org/apache/commons/math/stat/correlation/Covariance.java
Thu Feb 12 11:21:54 2009
@@ -0,0 +1,205 @@
+/*
+ * 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.correlation;
+
+import org.apache.commons.math.MathRuntimeException;
+import org.apache.commons.math.linear.RealMatrix;
+import org.apache.commons.math.linear.DenseRealMatrix;
+import org.apache.commons.math.stat.descriptive.moment.Mean;
+import org.apache.commons.math.stat.descriptive.moment.Variance;
+
+/**
+ * Computes covariances for pairs of arrays or columns of a matrix.
+ * 
+ * <p>The constructors that take <code>RealMatrix</code> or 
+ * <code>double[][]</code> arguments generate correlation matrices.  The
+ * columns of the input matrices are assumed to represent variable values.</p>
+ * 
+ * <p>The constructor argument <code>biasCorrected</code> determines whether
or
+ * not computed covariances are bias-corrected.</p>
+ * 
+ * <p>Unbiased covariances are given by the formula</p>
+ * <code>cov(X, Y) = &Sigma;[(x<sub>i</sub> - E(X))(y<sub>i</sub>
- E(Y))] / (n - 1)</code>
+ * where <code>E(x)</code> is the mean of <code>X</code> and <code>E(Y)</code>
+ * is the mean of the <code>Y</code> values.
+ * 
+ * <p>Non-bias-corrected estimates use <code>n</code> in place of <code>n
- 1</code>
+ * 
+ * @version $Revision$ $Date$
+ * @since 2.0
+ */
+public class Covariance {
+    
+    /** covariance matrix */
+    private final RealMatrix covarianceMatrix;
+    
+    public Covariance() {
+        super();
+        covarianceMatrix = null;
+    }
+    
+    /**
+     * Create a Covariance matrix from a rectangular array
+     * whose columns represent covariates.
+     * 
+     * <p>The <code>biasCorrected</code> parameter determines whether or
not
+     * covariance estimates are bias-corrected.</p>
+     * 
+     * <p>The input array must be rectangular with at least two columns
+     * and two rows.</p>
+     * 
+     * @param data rectangular array with columns representing covariates
+     * @param biasCorrected true means covariances are bias-corrected
+     * @throws IllegalArgumentException if the input data array is not
+     * rectangular with at least two rows and two columns.
+     */
+    public Covariance(double[][] data, boolean biasCorrected) {
+        this(new DenseRealMatrix(data), biasCorrected);
+    }
+    
+    /**
+     * Create a Covariance matrix from a rectangular array
+     * whose columns represent covariates.
+     * 
+     * <p>The input array must be rectangular with at least two columns
+     * and two rows</p>
+     * 
+     * @param data rectangular array with columns representing covariates
+     * @throws IllegalArgumentException if the input data array is not
+     * rectangular with at least two rows and two columns.
+     */
+    public Covariance(double[][] data) {
+        this(data, true);
+    }
+    
+    /**
+     * Create a covariance matrix from a matrix whose columns
+     * represent covariates.
+     * 
+     * <p>The <code>biasCorrected</code> parameter determines whether or
not
+     * covariance estimates are bias-corrected.</p>
+     * 
+     * <p>The matrix must have at least two columns and two rows</p>
+     * 
+     * @param matrix matrix with columns representing covariates
+     * @param biasCorrected true means covariances are bias-corrected
+     * @throws IllegalArgumentException if the input matrix does not have
+     * at least two rows and two columns
+     */
+    public Covariance(RealMatrix matrix, boolean biasCorrected) {
+       checkSufficientData(matrix);
+       covarianceMatrix = computeCovariance(matrix, biasCorrected);
+    }
+    
+    /**
+     * Create a covariance matrix from a matrix whose columns
+     * represent covariates.
+     * 
+     * <p>The matrix must have at least two columns and two rows</p>
+     * 
+     * @param matrix matrix with columns representing covariates
+     * @throws IllegalArgumentException if the input matrix does not have
+     * at least two rows and two columns
+     */
+    public Covariance(RealMatrix matrix) {
+        this(matrix, true);
+    }
+    
+    /**
+     * Returns the covariance matrix
+     * 
+     * @return covariance matrix
+     */
+    public RealMatrix getCovarianceMatrix() {
+        return covarianceMatrix;
+    }
+    
+    /**
+     * Create a covariance matrix from a matrix whose columns represent
+     * covariates.
+     * 
+     * <p>The input matrix must have at least two columns and two rows</p>
+     * 
+     * <p>The <code>biasCorrected</code> parameter determines whether or
not
+     * covariance estimates are bias-corrected.</p>
+     * 
+     * @return covariance matrix
+     */
+    protected RealMatrix computeCovariance(RealMatrix matrix, boolean biasCorrected) {
+        int dimension = matrix.getColumnDimension();
+        Variance variance = new Variance(biasCorrected);
+        RealMatrix outMatrix = new DenseRealMatrix(dimension, dimension);
+        for (int i = 0; i < dimension; i++) {
+            for (int j = 0; j < i; j++) {
+              double cov = covariance(matrix.getColumn(i), matrix.getColumn(j), biasCorrected);
+              outMatrix.setEntry(i, j, cov);
+              outMatrix.setEntry(j, i, cov);
+            }
+            outMatrix.setEntry(i, i, variance.evaluate(matrix.getColumn(i)));
+        }
+        return outMatrix;
+    }
+    
+    /**
+     * Computes the covariance between the two arrays.
+     * 
+     * <p>Array lengths must match and the common length must be at least 2.</p>
+     *
+     * @param xArray first data array
+     * @param yArray second data array
+     * @param biasCorrected if true, returned value will be bias-corrected 
+     * @return returns the covariance for the two arrays 
+     * @throws  IllegalArgumentException if the arrays lengths do not match or
+     * there is insufficient data
+     */
+    public double covariance(final double[] xArray, final double[] yArray, boolean biasCorrected)

+        throws IllegalArgumentException {
+        Mean mean = new Mean();
+        double result = 0d;
+        long length = xArray.length;
+        if(length == yArray.length && length > 1) {
+            double xMean = mean.evaluate(xArray);
+            double yMean = mean.evaluate(yArray);
+            for (int i = 0; i < xArray.length; i++) {
+                double xDev = xArray[i] - xMean;
+                double yDev = yArray[i] - yMean;
+                result += (xDev * yDev - result) / (i + 1);
+            }
+        }
+        else {
+            throw MathRuntimeException.createIllegalArgumentException(
+               "Arrays must have the same length and both must have at " +
+               "least two elements. xArray has size {0}, yArray has {1} elements",
+                    new Object[] {xArray.length, yArray.length});
+        }
+        return biasCorrected ? result * ((double) length / (double)(length - 1)) : result;
+    }
+    
+    /**
+     * Throws IllegalArgumentException of the matrix does not have at least
+     * two columns and two rows
+     */
+    private void checkSufficientData(final RealMatrix matrix) {
+        int nRows = matrix.getRowDimension();
+        int nCols = matrix.getColumnDimension();
+        if (nRows < 2 || nCols < 2) {
+            throw MathRuntimeException.createIllegalArgumentException(
+                    "Insufficient data:  only {0} rows and {1} columns.",
+                    new Object[]{nRows, nCols});
+        }
+    }
+}

Propchange: commons/proper/math/trunk/src/java/org/apache/commons/math/stat/correlation/Covariance.java
------------------------------------------------------------------------------
    svn:eol-style = native

Modified: commons/proper/math/trunk/src/site/xdoc/changes.xml
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/site/xdoc/changes.xml?rev=743688&r1=743687&r2=743688&view=diff
==============================================================================
--- commons/proper/math/trunk/src/site/xdoc/changes.xml (original)
+++ commons/proper/math/trunk/src/site/xdoc/changes.xml Thu Feb 12 11:21:54 2009
@@ -39,9 +39,16 @@
   </properties>
   <body>
     <release version="2.0" date="TBD" description="TBD">
+      <action dev="psteitz" type="add" issue="MATH-114">
+        Added Covariance class to compute variance-covariance matrices in new
+        correlation package.
+      </action>
       <action dev="luc" type="fix" issue="MATH-216" due-to="Cyril Briquet">
         Improved fast Fourier transform efficiency.
       </action>
+      <action dev="billbarker" type="add">
+         Added a SparseRealVector class that implements a sparse vector for the RealVector
interface.
+      </action>
       <action dev="luc" type="add" >
         Added factory methods to create Chebyshev, Hermite, Laguerre and Legendre polynomials.
       </action> 
@@ -303,9 +310,6 @@
       <action dev="brentworden" type="fix" issue="MATH-204" due-to="Mick">
         Added root checks for the endpoints.
       </action>
-      <action dev="billbarker" type="add">
-         Added a SparseRealVector class that implements a sparse vector for the RealVector
interface.
-      </action>
     </release>
     <release version="1.2" date="2008-02-24"
     description="This release combines bug fixes and new features. Most notable

Added: commons/proper/math/trunk/src/test/R/covarianceTestCases
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/test/R/covarianceTestCases?rev=743688&view=auto
==============================================================================
--- commons/proper/math/trunk/src/test/R/covarianceTestCases (added)
+++ commons/proper/math/trunk/src/test/R/covarianceTestCases Thu Feb 12 11:21:54 2009
@@ -0,0 +1,146 @@
+# 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.
+#
+#------------------------------------------------------------------------------
+# R source file to validate covariance tests in
+# org.apache.commons.math.stat.correlation.CovarianceTest
+#
+# To run the test, install R, put this file and testFunctions
+# into the same directory, launch R from this directory and then enter
+# source("<name-of-this-file>")
+#
+#------------------------------------------------------------------------------
+tol <- 1E-9                       # error tolerance for tests
+#------------------------------------------------------------------------------
+# Function definitions
+
+source("testFunctions")           # utility test functions
+options(digits=16)	              # override number of digits displayed
+
+# function to verify covariance computations
+verifyCovariance <- function(matrix, expectedCovariance, name) {
+    covariance <- cov(matrix)
+    output <- c("Covariance test dataset = ", name)
+    if (assertEquals(expectedCovariance,covariance,tol,"Covariances")) {
+        displayPadded(output, SUCCEEDED, WIDTH)
+    } else {
+        displayPadded(output, FAILED, WIDTH)
+    }  
+}
+
+#--------------------------------------------------------------------------
+cat("Covariance test cases\n")
+
+# Longley
+
+longley <- matrix(c(60323,83.0,234289,2356,1590,107608,1947,
+                    61122,88.5,259426,2325,1456,108632,1948,
+                    60171,88.2,258054,3682,1616,109773,1949,
+                    61187,89.5,284599,3351,1650,110929,1950,
+                    63221,96.2,328975,2099,3099,112075,1951,
+                    63639,98.1,346999,1932,3594,113270,1952,
+                    64989,99.0,365385,1870,3547,115094,1953,
+                    63761,100.0,363112,3578,3350,116219,1954,
+                    66019,101.2,397469,2904,3048,117388,1955,
+                    67857,104.6,419180,2822,2857,118734,1956,
+                    68169,108.4,442769,2936,2798,120445,1957,
+                    66513,110.8,444546,4681,2637,121950,1958,
+                    68655,112.6,482704,3813,2552,123366,1959,
+                    69564,114.2,502601,3931,2514,125368,1960,
+                    69331,115.7,518173,4806,2572,127852,1961,
+                    70551,116.9,554894,4007,2827,130081,1962),
+                    nrow = 16, ncol = 7, byrow = TRUE)
+
+expectedCovariance <- matrix(c(
+         12333921.73333333246, 3.679666000000000e+04, 343330206.333333313,
+         1649102.666666666744, 1117681.066666666651, 23461965.733333334, 16240.93333333333248,
+         36796.66000000000, 1.164576250000000e+02, 1063604.115416667,
+         6258.666250000000, 3490.253750000000, 73503.000000000, 50.92333333333334,
+         343330206.33333331347, 1.063604115416667e+06, 9879353659.329166412,
+         56124369.854166664183, 30880428.345833335072, 685240944.600000024, 470977.90000000002328,
+         1649102.66666666674, 6.258666250000000e+03, 56124369.854166664,
+         873223.429166666698, -115378.762499999997, 4462741.533333333, 2973.03333333333330,
+         1117681.06666666665, 3.490253750000000e+03, 30880428.345833335,
+         -115378.762499999997, 484304.095833333326, 1764098.133333333, 1382.43333333333339,
+         23461965.73333333433, 7.350300000000000e+04, 685240944.600000024,
+         4462741.533333333209, 1764098.133333333302, 48387348.933333330, 32917.40000000000146,
+         16240.93333333333, 5.092333333333334e+01, 470977.900000000,
+         2973.033333333333, 1382.433333333333, 32917.40000000, 22.66666666666667),
+         nrow = 7, ncol = 7, byrow = TRUE)
+         
+ verifyCovariance(longley, expectedCovariance, "longley")
+ 
+ # Swiss Fertility
+ 
+ fertility <- matrix(c(80.2,17.0,15,12,9.96,
+  83.1,45.1,6,9,84.84,
+  92.5,39.7,5,5,93.40,
+  85.8,36.5,12,7,33.77,
+  76.9,43.5,17,15,5.16,
+  76.1,35.3,9,7,90.57,
+  83.8,70.2,16,7,92.85,
+  92.4,67.8,14,8,97.16,
+  82.4,53.3,12,7,97.67,
+  82.9,45.2,16,13,91.38,
+  87.1,64.5,14,6,98.61,
+  64.1,62.0,21,12,8.52,
+  66.9,67.5,14,7,2.27,
+  68.9,60.7,19,12,4.43,
+  61.7,69.3,22,5,2.82,
+  68.3,72.6,18,2,24.20,
+  71.7,34.0,17,8,3.30,
+  55.7,19.4,26,28,12.11,
+  54.3,15.2,31,20,2.15,
+  65.1,73.0,19,9,2.84,
+  65.5,59.8,22,10,5.23,
+  65.0,55.1,14,3,4.52,
+  56.6,50.9,22,12,15.14,
+  57.4,54.1,20,6,4.20,
+  72.5,71.2,12,1,2.40,
+  74.2,58.1,14,8,5.23,
+  72.0,63.5,6,3,2.56,
+  60.5,60.8,16,10,7.72,
+  58.3,26.8,25,19,18.46,
+  65.4,49.5,15,8,6.10,
+  75.5,85.9,3,2,99.71,
+  69.3,84.9,7,6,99.68,
+  77.3,89.7,5,2,100.00,
+  70.5,78.2,12,6,98.96,
+  79.4,64.9,7,3,98.22,
+  65.0,75.9,9,9,99.06,
+  92.2,84.6,3,3,99.46,
+  79.3,63.1,13,13,96.83,
+  70.4,38.4,26,12,5.62,
+  65.7,7.7,29,11,13.79,
+  72.7,16.7,22,13,11.22,
+  64.4,17.6,35,32,16.92,
+  77.6,37.6,15,7,4.97,
+  67.6,18.7,25,7,8.65,
+  35.0,1.2,37,53,42.34,
+  44.7,46.6,16,29,50.43,
+  42.8,27.7,22,29,58.33),
+  nrow = 47, ncol = 5, byrow = TRUE)
+   
+ expectedCovariance <- matrix(c(
+         156.0424976873265, 100.1691489361702, -64.36692876965772, -79.7295097132285, 241.5632030527289,
+         100.169148936170251, 515.7994172062905, -124.39283071230344, -139.6574005550416,
379.9043755781684,
+         -64.3669287696577, -124.3928307123034, 63.64662349676226, 53.5758556891767, -190.5606105457909,
+         -79.7295097132285, -139.6574005550416, 53.57585568917669, 92.4560592044403, -61.6988297872340,
+          241.5632030527289, 379.9043755781684, -190.56061054579092, -61.6988297872340, 1739.2945371877890),
+          nrow = 5, ncol = 5, byrow = TRUE)
+      
+ verifyCovariance(fertility, expectedCovariance, "swiss fertility")
+ 
+ displayDashes(WIDTH)
\ No newline at end of file

Modified: commons/proper/math/trunk/src/test/R/testAll
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/test/R/testAll?rev=743688&r1=743687&r2=743688&view=diff
==============================================================================
--- commons/proper/math/trunk/src/test/R/testAll (original)
+++ commons/proper/math/trunk/src/test/R/testAll Thu Feb 12 11:21:54 2009
@@ -47,6 +47,9 @@
 # multiple regression
 source("multipleOLSRegressionTestCases")
 
+# covariance
+source("covarianceTestCases")
+
 #------------------------------------------------------------------------------
 # if output has been diverted, change it back
 if (sink.number()) {

Added: commons/proper/math/trunk/src/test/org/apache/commons/math/stat/correlation/CovarianceTest.java
URL: http://svn.apache.org/viewvc/commons/proper/math/trunk/src/test/org/apache/commons/math/stat/correlation/CovarianceTest.java?rev=743688&view=auto
==============================================================================
--- commons/proper/math/trunk/src/test/org/apache/commons/math/stat/correlation/CovarianceTest.java
(added)
+++ commons/proper/math/trunk/src/test/org/apache/commons/math/stat/correlation/CovarianceTest.java
Thu Feb 12 11:21:54 2009
@@ -0,0 +1,225 @@
+/*
+ * 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.correlation;
+
+import org.apache.commons.math.TestUtils;
+import org.apache.commons.math.linear.RealMatrix;
+import org.apache.commons.math.linear.RealMatrixImpl;
+import org.apache.commons.math.stat.descriptive.moment.Variance;
+
+import junit.framework.TestCase;
+
+public class CovarianceTest extends TestCase {
+    
+    protected final double[] longleyData = new double[] {
+            60323,83.0,234289,2356,1590,107608,1947,
+            61122,88.5,259426,2325,1456,108632,1948,
+            60171,88.2,258054,3682,1616,109773,1949,
+            61187,89.5,284599,3351,1650,110929,1950,
+            63221,96.2,328975,2099,3099,112075,1951,
+            63639,98.1,346999,1932,3594,113270,1952,
+            64989,99.0,365385,1870,3547,115094,1953,
+            63761,100.0,363112,3578,3350,116219,1954,
+            66019,101.2,397469,2904,3048,117388,1955,
+            67857,104.6,419180,2822,2857,118734,1956,
+            68169,108.4,442769,2936,2798,120445,1957,
+            66513,110.8,444546,4681,2637,121950,1958,
+            68655,112.6,482704,3813,2552,123366,1959,
+            69564,114.2,502601,3931,2514,125368,1960,
+            69331,115.7,518173,4806,2572,127852,1961,
+            70551,116.9,554894,4007,2827,130081,1962
+        };
+    
+    protected final double[] swissData = new double[] {
+            80.2,17.0,15,12,9.96,
+            83.1,45.1,6,9,84.84,
+            92.5,39.7,5,5,93.40,
+            85.8,36.5,12,7,33.77,
+            76.9,43.5,17,15,5.16,
+            76.1,35.3,9,7,90.57,
+            83.8,70.2,16,7,92.85,
+            92.4,67.8,14,8,97.16,
+            82.4,53.3,12,7,97.67,
+            82.9,45.2,16,13,91.38,
+            87.1,64.5,14,6,98.61,
+            64.1,62.0,21,12,8.52,
+            66.9,67.5,14,7,2.27,
+            68.9,60.7,19,12,4.43,
+            61.7,69.3,22,5,2.82,
+            68.3,72.6,18,2,24.20,
+            71.7,34.0,17,8,3.30,
+            55.7,19.4,26,28,12.11,
+            54.3,15.2,31,20,2.15,
+            65.1,73.0,19,9,2.84,
+            65.5,59.8,22,10,5.23,
+            65.0,55.1,14,3,4.52,
+            56.6,50.9,22,12,15.14,
+            57.4,54.1,20,6,4.20,
+            72.5,71.2,12,1,2.40,
+            74.2,58.1,14,8,5.23,
+            72.0,63.5,6,3,2.56,
+            60.5,60.8,16,10,7.72,
+            58.3,26.8,25,19,18.46,
+            65.4,49.5,15,8,6.10,
+            75.5,85.9,3,2,99.71,
+            69.3,84.9,7,6,99.68,
+            77.3,89.7,5,2,100.00,
+            70.5,78.2,12,6,98.96,
+            79.4,64.9,7,3,98.22,
+            65.0,75.9,9,9,99.06,
+            92.2,84.6,3,3,99.46,
+            79.3,63.1,13,13,96.83,
+            70.4,38.4,26,12,5.62,
+            65.7,7.7,29,11,13.79,
+            72.7,16.7,22,13,11.22,
+            64.4,17.6,35,32,16.92,
+            77.6,37.6,15,7,4.97,
+            67.6,18.7,25,7,8.65,
+            35.0,1.2,37,53,42.34,
+            44.7,46.6,16,29,50.43,
+            42.8,27.7,22,29,58.33
+        };
+ 
+    
+    /**
+     * Test Longley dataset against R.
+     * Data Source: J. Longley (1967) "An Appraisal of Least Squares
+     * Programs for the Electronic Computer from the Point of View of the User"
+     * Journal of the American Statistical Association, vol. 62. September,
+     * pp. 819-841.
+     * 
+     * Data are from NIST:
+     * http://www.itl.nist.gov/div898/strd/lls/data/LINKS/DATA/Longley.dat
+     */
+    public void testLongly() {  
+        RealMatrix matrix = createRealMatrix(longleyData, 16, 7);
+        RealMatrix covarianceMatrix = new Covariance(matrix).getCovarianceMatrix();
+        double[] rData = new double[] {
+         12333921.73333333246, 3.679666000000000e+04, 343330206.333333313,
+         1649102.666666666744, 1117681.066666666651, 23461965.733333334, 16240.93333333333248,
+         36796.66000000000, 1.164576250000000e+02, 1063604.115416667,
+         6258.666250000000, 3490.253750000000, 73503.000000000, 50.92333333333334,
+         343330206.33333331347, 1.063604115416667e+06, 9879353659.329166412,
+         56124369.854166664183, 30880428.345833335072, 685240944.600000024, 470977.90000000002328,
+         1649102.66666666674, 6.258666250000000e+03, 56124369.854166664,
+         873223.429166666698, -115378.762499999997, 4462741.533333333, 2973.03333333333330,
+         1117681.06666666665, 3.490253750000000e+03, 30880428.345833335,
+         -115378.762499999997, 484304.095833333326, 1764098.133333333, 1382.43333333333339,
+         23461965.73333333433, 7.350300000000000e+04, 685240944.600000024,
+         4462741.533333333209, 1764098.133333333302, 48387348.933333330, 32917.40000000000146,
+         16240.93333333333, 5.092333333333334e+01, 470977.900000000,
+         2973.033333333333, 1382.433333333333, 32917.40000000, 22.66666666666667
+        };
+        
+        TestUtils.assertEquals("covariance matrix", createRealMatrix(rData, 7, 7), covarianceMatrix,
10E-9);
+
+    }
+    
+    /**
+     * Test R Swiss fertility dataset against R.
+     * Data Source: R datasets package
+     */
+    public void testSwissFertility() {
+         RealMatrix matrix = createRealMatrix(swissData, 47, 5);
+         RealMatrix covarianceMatrix = new Covariance(matrix).getCovarianceMatrix();
+         double[] rData = new double[] {
+           156.0424976873265, 100.1691489361702, -64.36692876965772, -79.7295097132285, 241.5632030527289,
+           100.169148936170251, 515.7994172062905, -124.39283071230344, -139.6574005550416,
379.9043755781684,
+           -64.3669287696577, -124.3928307123034, 63.64662349676226, 53.5758556891767, -190.5606105457909,
+           -79.7295097132285, -139.6574005550416, 53.57585568917669, 92.4560592044403, -61.6988297872340,
+            241.5632030527289, 379.9043755781684, -190.56061054579092, -61.6988297872340,
1739.2945371877890
+         };
+         
+         TestUtils.assertEquals("covariance matrix", createRealMatrix(rData, 5, 5), covarianceMatrix,
10E-13);
+    }
+    
+    /**
+     * Constant column
+     */
+    public void testConstant() {
+        double[] noVariance = new double[] {1, 1, 1, 1};
+        double[] values = new double[] {1, 2, 3, 4};
+        assertEquals(0d, new Covariance().covariance(noVariance, values, true), Double.MIN_VALUE);
+        assertEquals(0d, new Covariance().covariance(noVariance, noVariance, true), Double.MIN_VALUE);
+    }
+    
+    
+    /**
+     * Insufficient data
+     */
+    public void testInsufficientData() {
+        double[] one = new double[] {1};
+        double[] two = new double[] {2};
+        try {
+            new Covariance().covariance(one, two, false);
+            fail("Expecting IllegalArgumentException");
+        } catch (IllegalArgumentException ex) {
+            // Expected
+        }
+        RealMatrix matrix = new RealMatrixImpl(new double[][] {{0},{1}});
+        try {
+            new Covariance(matrix);
+            fail("Expecting IllegalArgumentException");
+        } catch (IllegalArgumentException ex) {
+            // Expected
+        }
+    }
+    
+    /**
+     * Verify that diagonal entries are consistent with Variance computation and matrix matches
+     * column-by-column covariances
+     */
+    public void testConsistency() {
+        RealMatrix matrix = createRealMatrix(swissData, 47, 5);
+        RealMatrix covarianceMatrix = new Covariance(matrix).getCovarianceMatrix();
+        
+        // Variances on the diagonal
+        Variance variance = new Variance();
+        for (int i = 0; i < 5; i++) {
+            assertEquals(variance.evaluate(matrix.getColumn(i)), covarianceMatrix.getEntry(i,i),
10E-14);
+        }
+        
+        // Symmetry, column-consistency
+        assertEquals(covarianceMatrix.getEntry(2, 3), 
+                new Covariance().covariance(matrix.getColumn(2), matrix.getColumn(3), true),
10E-14);
+        assertEquals(covarianceMatrix.getEntry(2, 3), covarianceMatrix.getEntry(3, 2), Double.MIN_VALUE);
+        
+        // All columns same -> all entries = column variance
+        RealMatrix repeatedColumns = new RealMatrixImpl(47, 3);
+        for (int i = 0; i < 3; i++) {
+            repeatedColumns.setColumnMatrix(i, matrix.getColumnMatrix(0));
+        }
+        covarianceMatrix = new Covariance(repeatedColumns).getCovarianceMatrix();
+        double columnVariance = variance.evaluate(matrix.getColumn(0));
+        for (int i = 0; i < 3; i++) {
+            for (int j = 0; j < 3; j++) {
+                assertEquals(columnVariance, covarianceMatrix.getEntry(i, j), 10E-14);
+            }
+        }
+        
+    }
+    
+    protected RealMatrix createRealMatrix(double[] data, int nRows, int nCols) {
+        double[][] matrixData = new double[nRows][nCols];
+        int ptr = 0;
+        for (int i = 0; i < nRows; i++) {
+            System.arraycopy(data, ptr, matrixData[i], 0, nCols);
+            ptr += nCols;
+        }
+        return new RealMatrixImpl(matrixData); 
+    }
+}

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



Mime
View raw message