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.math.stat.inference;
18  
19  import junit.framework.Test;
20  import junit.framework.TestCase;
21  import junit.framework.TestSuite;
22  
23  /**
24   * Test cases for the ChiSquareTestImpl class.
25   *
26   * @version $Revision: 762087 $ $Date: 2009-04-05 10:20:18 -0400 (Sun, 05 Apr 2009) $
27   */
28  
29  public class ChiSquareTestTest extends TestCase {
30  
31      protected UnknownDistributionChiSquareTest testStatistic = new ChiSquareTestImpl();
32  
33      public ChiSquareTestTest(String name) {
34          super(name);
35      }
36  
37      public static Test suite() {
38          TestSuite suite = new TestSuite(ChiSquareTestTest.class);
39          suite.setName("TestStatistic Tests");
40          return suite;
41      }
42  
43      public void testChiSquare() throws Exception {
44   
45          // Target values computed using R version 1.8.1 
46          // Some assembly required ;-)  
47          //      Use sum((obs - exp)^2/exp) for the chi-square statistic and
48          //      1 - pchisq(sum((obs - exp)^2/exp), length(obs) - 1) for the p-value
49          
50          long[] observed = {10, 9, 11};
51          double[] expected = {10, 10, 10};
52          assertEquals("chi-square statistic", 0.2,  testStatistic.chiSquare(expected, observed), 10E-12);
53          assertEquals("chi-square p-value", 0.904837418036, testStatistic.chiSquareTest(expected, observed), 1E-10);
54          
55          long[] observed1 = { 500, 623, 72, 70, 31 };
56          double[] expected1 = { 485, 541, 82, 61, 37 };
57          assertEquals( "chi-square test statistic", 9.023307936427388, testStatistic.chiSquare(expected1, observed1), 1E-10);
58          assertEquals("chi-square p-value", 0.06051952647453607, testStatistic.chiSquareTest(expected1, observed1), 1E-9);
59          assertTrue("chi-square test reject", testStatistic.chiSquareTest(expected1, observed1, 0.08));
60          assertTrue("chi-square test accept", !testStatistic.chiSquareTest(expected1, observed1, 0.05));
61  
62          try {
63              testStatistic.chiSquareTest(expected1, observed1, 95);
64              fail("alpha out of range, IllegalArgumentException expected");
65          } catch (IllegalArgumentException ex) {
66              // expected
67          }  
68          
69          long[] tooShortObs = { 0 };
70          double[] tooShortEx = { 1 };
71          try {
72              testStatistic.chiSquare(tooShortEx, tooShortObs);
73              fail("arguments too short, IllegalArgumentException expected");
74          } catch (IllegalArgumentException ex) {
75              // expected
76          }
77  
78          // unmatched arrays
79          long[] unMatchedObs = { 0, 1, 2, 3 };
80          double[] unMatchedEx = { 1, 1, 2 };
81          try {
82              testStatistic.chiSquare(unMatchedEx, unMatchedObs);
83              fail("arrays have different lengths, IllegalArgumentException expected");
84          } catch (IllegalArgumentException ex) {
85              // expected
86          }
87          
88          // 0 expected count
89          expected[0] = 0;
90          try {
91              testStatistic.chiSquareTest(expected, observed, .01);
92              fail("bad expected count, IllegalArgumentException expected");
93          } catch (IllegalArgumentException ex) {
94              // expected
95          } 
96          
97          // negative observed count
98          expected[0] = 1;
99          observed[0] = -1;
100         try {
101             testStatistic.chiSquareTest(expected, observed, .01);
102             fail("bad expected count, IllegalArgumentException expected");
103         } catch (IllegalArgumentException ex) {
104             // expected
105         } 
106         
107     }
108 
109     public void testChiSquareIndependence() throws Exception {
110         
111         // Target values computed using R version 1.8.1 
112         
113         long[][] counts = { {40, 22, 43}, {91, 21, 28}, {60, 10, 22}};
114         assertEquals( "chi-square test statistic", 22.709027688, testStatistic.chiSquare(counts), 1E-9);
115         assertEquals("chi-square p-value", 0.000144751460134, testStatistic.chiSquareTest(counts), 1E-9);
116         assertTrue("chi-square test reject", testStatistic.chiSquareTest(counts, 0.0002));
117         assertTrue("chi-square test accept", !testStatistic.chiSquareTest(counts, 0.0001));    
118         
119         long[][] counts2 = {{10, 15}, {30, 40}, {60, 90} };
120         assertEquals( "chi-square test statistic", 0.168965517241, testStatistic.chiSquare(counts2), 1E-9);
121         assertEquals("chi-square p-value",0.918987499852, testStatistic.chiSquareTest(counts2), 1E-9);
122         assertTrue("chi-square test accept", !testStatistic.chiSquareTest(counts2, 0.1)); 
123         
124         // ragged input array
125         long[][] counts3 = { {40, 22, 43}, {91, 21, 28}, {60, 10}};
126         try {
127             testStatistic.chiSquare(counts3);
128             fail("Expecting IllegalArgumentException");
129         } catch (IllegalArgumentException ex) {
130             // expected
131         }
132         
133         // insufficient data
134         long[][] counts4 = {{40, 22, 43}};
135         try {
136             testStatistic.chiSquare(counts4);
137             fail("Expecting IllegalArgumentException");
138         } catch (IllegalArgumentException ex) {
139             // expected
140         } 
141         long[][] counts5 = {{40}, {40}, {30}, {10}};
142         try {
143             testStatistic.chiSquare(counts5);
144             fail("Expecting IllegalArgumentException");
145         } catch (IllegalArgumentException ex) {
146             // expected
147         } 
148         
149         // negative counts
150         long[][] counts6 = {{10, -2}, {30, 40}, {60, 90} };
151         try {
152             testStatistic.chiSquare(counts6);
153             fail("Expecting IllegalArgumentException");
154         } catch (IllegalArgumentException ex) {
155             // expected
156         } 
157         
158         // bad alpha
159         try {
160             testStatistic.chiSquareTest(counts, 0);
161             fail("Expecting IllegalArgumentException");
162         } catch (IllegalArgumentException ex) {
163             // expected
164         } 
165     }
166     
167     public void testChiSquareLargeTestStatistic() throws Exception {
168         double[] exp = new double[] {
169             3389119.5, 649136.6, 285745.4, 25357364.76, 11291189.78, 543628.0, 
170             232921.0, 437665.75
171         };
172 
173         long[] obs = new long[] {
174             2372383, 584222, 257170, 17750155, 7903832, 489265, 209628, 393899
175         };
176         org.apache.commons.math.stat.inference.ChiSquareTestImpl csti =
177             new org.apache.commons.math.stat.inference.ChiSquareTestImpl(); 
178         double cst = csti.chiSquareTest(exp, obs); 
179         assertEquals("chi-square p-value", 0.0, cst, 1E-3);
180         assertEquals( "chi-square test statistic", 
181                 114875.90421929007, testStatistic.chiSquare(exp, obs), 1E-9);
182     }
183     
184     /** Contingency table containing zeros - PR # 32531 */
185     public void testChiSquareZeroCount() throws Exception {
186         // Target values computed using R version 1.8.1 
187         long[][] counts = { {40, 0, 4}, {91, 1, 2}, {60, 2, 0}};
188         assertEquals( "chi-square test statistic", 9.67444662263,
189                 testStatistic.chiSquare(counts), 1E-9);
190         assertEquals("chi-square p-value", 0.0462835770603,
191                 testStatistic.chiSquareTest(counts), 1E-9);       
192     }
193     
194     /** Target values verified using DATAPLOT version 2006.3 */
195     public void testChiSquareDataSetsComparisonEqualCounts()
196     throws Exception {
197         long[] observed1 = {10, 12, 12, 10};
198         long[] observed2 = {5, 15, 14, 10};    
199         assertEquals("chi-square p value", 0.541096, 
200                 testStatistic.chiSquareTestDataSetsComparison(
201                 observed1, observed2), 1E-6);
202         assertEquals("chi-square test statistic", 2.153846,
203                 testStatistic.chiSquareDataSetsComparison(
204                 observed1, observed2), 1E-6);
205         assertFalse("chi-square test result", 
206                 testStatistic.chiSquareTestDataSetsComparison(
207                 observed1, observed2, 0.4));
208     }
209     
210     /** Target values verified using DATAPLOT version 2006.3 */
211     public void testChiSquareDataSetsComparisonUnEqualCounts()
212     throws Exception {
213         long[] observed1 = {10, 12, 12, 10, 15};
214         long[] observed2 = {15, 10, 10, 15, 5};    
215         assertEquals("chi-square p value", 0.124115, 
216                 testStatistic.chiSquareTestDataSetsComparison(
217                 observed1, observed2), 1E-6);
218         assertEquals("chi-square test statistic", 7.232189,
219                 testStatistic.chiSquareDataSetsComparison(
220                 observed1, observed2), 1E-6);
221         assertTrue("chi-square test result", 
222                 testStatistic.chiSquareTestDataSetsComparison(
223                 observed1, observed2, 0.13));
224         assertFalse("chi-square test result", 
225                 testStatistic.chiSquareTestDataSetsComparison(
226                 observed1, observed2, 0.12));
227     }
228     
229     public void testChiSquareDataSetsComparisonBadCounts()
230     throws Exception {
231         long[] observed1 = {10, -1, 12, 10, 15};
232         long[] observed2 = {15, 10, 10, 15, 5};
233         try {
234             testStatistic.chiSquareTestDataSetsComparison(
235                     observed1, observed2);
236             fail("Expecting IllegalArgumentException - negative count");
237         } catch (IllegalArgumentException ex) {
238             // expected
239         }
240         long[] observed3 = {10, 0, 12, 10, 15};
241         long[] observed4 = {15, 0, 10, 15, 5};
242         try {
243             testStatistic.chiSquareTestDataSetsComparison(
244                     observed3, observed4);
245             fail("Expecting IllegalArgumentException - double 0's");
246         } catch (IllegalArgumentException ex) {
247             // expected
248         }
249         long[] observed5 = {10, 10, 12, 10, 15};
250         long[] observed6 = {0, 0, 0, 0, 0};
251         try {
252             testStatistic.chiSquareTestDataSetsComparison(
253                     observed5, observed6);
254             fail("Expecting IllegalArgumentException - vanishing counts");
255         } catch (IllegalArgumentException ex) {
256             // expected
257         }
258     }
259 }