/Users/lyon/j4p/src/math/linearAlgebra/test/TestMatrix.java
|
1 package math.linearAlgebra.test;
2 import math.linearAlgebra.*;
3
4 import java.io.*;
5 import java.text.DecimalFormat;
6 import java.text.DecimalFormatSymbols;
7 import java.util.Locale;
8
9 /** TestMatrix tests the functionality of the linearAlgebra Matrix class and associated decompositions.
10 <P>
11 Run the test from the command line using
12 <BLOCKQUOTE><PRE><CODE>
13 java linearAlgebra.test.TestMatrix
14 </CODE></PRE></BLOCKQUOTE>
15 Detailed output is provided indicating the functionality being tested
16 and whether the functionality is correctly implemented. Exception handling
17 is also tested.
18 <P>
19 The test is designed to run to completion and give a summary of any implementation errors
20 encountered. The final output should be:
21 <BLOCKQUOTE><PRE><CODE>
22 TestMatrix completed.
23 Total errors reported: n1
24 Total warning reported: n2
25 </CODE></PRE></BLOCKQUOTE>
26 If the test does not run to completion, this indicates that there is a
27 substantial problem within the implementation that was not anticipated in the test design.
28 The stopping point should give an indication of where the problem exists.
29 **/
30 public class TestMatrix {
31 public static void main (String argv[]) {
32 Matrix A,B,C,Z,O,I,R,S,X,SUB,M,T,SQ,DEF,SOL;
33 // Uncomment this to test IO in a different locale.
34 // Locale.setDefault(Locale.GERMAN);
35 int errorCount=0;
36 int warningCount=0;
37 double tmp, s;
38 double[] columnwise = {1.,2.,3.,4.,5.,6.,7.,8.,9.,10.,11.,12.};
39 double[] rowwise = {1.,4.,7.,10.,2.,5.,8.,11.,3.,6.,9.,12.};
40 double[][] avals = {{1.,4.,7.,10.},{2.,5.,8.,11.},{3.,6.,9.,12.}};
41 double[][] rankdef = avals;
42 double[][] tvals = {{1.,2.,3.},{4.,5.,6.},{7.,8.,9.},{10.,11.,12.}};
43 double[][] subavals = {{5.,8.,11.},{6.,9.,12.}};
44 double[][] rvals = {{1.,4.,7.},{2.,5.,8.,11.},{3.,6.,9.,12.}};
45 double[][] pvals = {{1.,1.,1.},{1.,2.,3.},{1.,3.,6.}};
46 double[][] ivals = {{1.,0.,0.,0.},{0.,1.,0.,0.},{0.,0.,1.,0.}};
47 double[][] evals =
48 {{0.,1.,0.,0.},{1.,0.,2.e-7,0.},{0.,-2.e-7,0.,1.},{0.,0.,1.,0.}};
49 double[][] square = {{166.,188.,210.},{188.,214.,240.},{210.,240.,270.}};
50 double[][] sqSolution = {{13.},{15.}};
51 double[][] condmat = {{1.,3.},{7.,9.}};
52 int rows=3,cols=4;
53 int invalidld=5;/* should trigger bad shape for construction with val */
54 int raggedr=0; /* (raggedr,raggedc) should be out of bounds in ragged array */
55 int raggedc=4;
56 int validld=3; /* leading dimension of intended test Matrices */
57 int nonconformld=4; /* leading dimension which is valid, but nonconforming */
58 int ib=1,ie=2,jb=1,je=3; /* index ranges for sub Matrix */
59 int[] rowindexset = {1,2};
60 int[] badrowindexset = {1,3};
61 int[] columnindexset = {1,2,3};
62 int[] badcolumnindexset = {1,2,4};
63 double columnsummax = 33.;
64 double rowsummax = 30.;
65 double sumofdiagonals = 15;
66 double sumofsquares = 650;
67
68 /**
69 Constructors and constructor-like methods:
70 double[], int
71 double[][]
72 int, int
73 int, int, double
74 int, int, double[][]
75 constructWithCopy(double[][])
76 random(int,int)
77 identity(int)
78 **/
79
80 print("\nTesting constructors and constructor-like methods...\n");
81 try{
82 /** check that exception is thrown in packed constructor with invalid length **/
83 A = new Matrix(columnwise,invalidld);
84 errorCount = try_failure(errorCount,"Catch invalid length in packed constructor... ",
85 "exception not thrown for invalid input");
86 } catch ( IllegalArgumentException e ) {
87 try_success("Catch invalid length in packed constructor... ",
88 e.getMessage());
89 }
90 try{
91 /** check that exception is thrown in default constructor
92 if input array is 'ragged' **/
93 A = new Matrix(rvals);
94 tmp = A.get(raggedr,raggedc);
95 } catch ( IllegalArgumentException e ) {
96 try_success("Catch ragged input to default constructor... ",
97 e.getMessage());
98 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
99 errorCount = try_failure(errorCount,"Catch ragged input to constructor... ",
100 "exception not thrown in construction...ArrayIndexOutOfBoundsException thrown later");
101 }
102 try{
103 /** check that exception is thrown in constructWithCopy
104 if input array is 'ragged' **/
105 A = Matrix.constructWithCopy(rvals);
106 tmp = A.get(raggedr,raggedc);
107 } catch ( IllegalArgumentException e ) {
108 try_success("Catch ragged input to constructWithCopy... ",e.getMessage());
109 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
110 errorCount = try_failure(errorCount,"Catch ragged input to constructWithCopy... ","exception not thrown in construction...ArrayIndexOutOfBoundsException thrown later");
111 }
112
113 A = new Matrix(columnwise,validld);
114 B = new Matrix(avals);
115 tmp = B.get(0,0);
116 avals[0][0] = 0.0;
117 C = B.minus(A);
118 avals[0][0] = tmp;
119 B = Matrix.constructWithCopy(avals);
120 tmp = B.get(0,0);
121 avals[0][0] = 0.0;
122 if ( ( tmp - B.get(0,0) ) != 0.0 ) {
123 /** check that constructWithCopy behaves properly **/
124 errorCount = try_failure(errorCount,"constructWithCopy... ","copy not effected... data visible outside");
125 } else {
126 try_success("constructWithCopy... ","");
127 }
128 avals[0][0] = columnwise[0];
129 I = new Matrix(ivals);
130 try {
131 check(I,Matrix.identity(3,4));
132 try_success("identity... ","");
133 } catch ( java.lang.RuntimeException e ) {
134 errorCount = try_failure(errorCount,"identity... ","identity Matrix not successfully created");
135 }
136
137 /**
138 Access Methods:
139 getColumnDimension()
140 getRowDimension()
141 getArray()
142 getArrayCopy()
143 getColumnPackedCopy()
144 getRowPackedCopy()
145 get(int,int)
146 getMatrix(int,int,int,int)
147 getMatrix(int,int,int[])
148 getMatrix(int[],int,int)
149 getMatrix(int[],int[])
150 set(int,int,double)
151 setMatrix(int,int,int,int,Matrix)
152 setMatrix(int,int,int[],Matrix)
153 setMatrix(int[],int,int,Matrix)
154 setMatrix(int[],int[],Matrix)
155 **/
156
157 print("\nTesting access methods...\n");
158
159 /**
160 Various get methods:
161 **/
162
163 B = new Matrix(avals);
164 if (B.getRowDimension() != rows) {
165 errorCount = try_failure(errorCount,"getRowDimension... ","");
166 } else {
167 try_success("getRowDimension... ","");
168 }
169 if (B.getColumnDimension() != cols) {
170 errorCount = try_failure(errorCount,"getColumnDimension... ","");
171 } else {
172 try_success("getColumnDimension... ","");
173 }
174 B = new Matrix(avals);
175 double[][] barray = B.getArray();
176 if ( barray != avals ) {
177 errorCount = try_failure(errorCount,"getArray... ","");
178 } else {
179 try_success("getArray... ","");
180 }
181 barray = B.getArrayCopy();
182 if ( barray == avals ) {
183 errorCount = try_failure(errorCount,"getArrayCopy... ","data not (deep) copied");
184 }
185 try {
186 check(barray,avals);
187 try_success("getArrayCopy... ","");
188 } catch ( java.lang.RuntimeException e ) {
189 errorCount = try_failure(errorCount,"getArrayCopy... ","data not successfully (deep) copied");
190 }
191 double[] bpacked = B.getColumnPackedCopy();
192 try {
193 check(bpacked,columnwise);
194 try_success("getColumnPackedCopy... ","");
195 } catch ( java.lang.RuntimeException e ) {
196 errorCount = try_failure(errorCount,"getColumnPackedCopy... ","data not successfully (deep) copied by columns");
197 }
198 bpacked = B.getRowPackedCopy();
199 try {
200 check(bpacked,rowwise);
201 try_success("getRowPackedCopy... ","");
202 } catch ( java.lang.RuntimeException e ) {
203 errorCount = try_failure(errorCount,"getRowPackedCopy... ","data not successfully (deep) copied by rows");
204 }
205 try {
206 tmp = B.get(B.getRowDimension(),B.getColumnDimension()-1);
207 errorCount = try_failure(errorCount,"get(int,int)... ","OutOfBoundsException expected but not thrown");
208 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
209 try {
210 tmp = B.get(B.getRowDimension()-1,B.getColumnDimension());
211 errorCount = try_failure(errorCount,"get(int,int)... ","OutOfBoundsException expected but not thrown");
212 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
213 try_success("get(int,int)... OutofBoundsException... ","");
214 }
215 } catch ( java.lang.IllegalArgumentException e1 ) {
216 errorCount = try_failure(errorCount,"get(int,int)... ","OutOfBoundsException expected but not thrown");
217 }
218 try {
219 if (B.get(B.getRowDimension()-1,B.getColumnDimension()-1) !=
220 avals[B.getRowDimension()-1][B.getColumnDimension()-1] ) {
221 errorCount = try_failure(errorCount,"get(int,int)... ","Matrix entry (i,j) not successfully retreived");
222 } else {
223 try_success("get(int,int)... ","");
224 }
225 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
226 errorCount = try_failure(errorCount,"get(int,int)... ","Unexpected ArrayIndexOutOfBoundsException");
227 }
228 SUB = new Matrix(subavals);
229 try {
230 M = B.getMatrix(ib,ie+B.getRowDimension()+1,jb,je);
231 errorCount = try_failure(errorCount,"getMatrix(int,int,int,int)... ","ArrayIndexOutOfBoundsException expected but not thrown");
232 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
233 try {
234 M = B.getMatrix(ib,ie,jb,je+B.getColumnDimension()+1);
235 errorCount = try_failure(errorCount,"getMatrix(int,int,int,int)... ","ArrayIndexOutOfBoundsException expected but not thrown");
236 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
237 try_success("getMatrix(int,int,int,int)... ArrayIndexOutOfBoundsException... ","");
238 }
239 } catch ( java.lang.IllegalArgumentException e1 ) {
240 errorCount = try_failure(errorCount,"getMatrix(int,int,int,int)... ","ArrayIndexOutOfBoundsException expected but not thrown");
241 }
242 try {
243 M = B.getMatrix(ib,ie,jb,je);
244 try {
245 check(SUB,M);
246 try_success("getMatrix(int,int,int,int)... ","");
247 } catch ( java.lang.RuntimeException e ) {
248 errorCount = try_failure(errorCount,"getMatrix(int,int,int,int)... ","submatrix not successfully retreived");
249 }
250 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
251 errorCount = try_failure(errorCount,"getMatrix(int,int,int,int)... ","Unexpected ArrayIndexOutOfBoundsException");
252 }
253
254 try {
255 M = B.getMatrix(ib,ie,badcolumnindexset);
256 errorCount = try_failure(errorCount,"getMatrix(int,int,int[])... ","ArrayIndexOutOfBoundsException expected but not thrown");
257 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
258 try {
259 M = B.getMatrix(ib,ie+B.getRowDimension()+1,columnindexset);
260 errorCount = try_failure(errorCount,"getMatrix(int,int,int[])... ","ArrayIndexOutOfBoundsException expected but not thrown");
261 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
262 try_success("getMatrix(int,int,int[])... ArrayIndexOutOfBoundsException... ","");
263 }
264 } catch ( java.lang.IllegalArgumentException e1 ) {
265 errorCount = try_failure(errorCount,"getMatrix(int,int,int[])... ","ArrayIndexOutOfBoundsException expected but not thrown");
266 }
267 try {
268 M = B.getMatrix(ib,ie,columnindexset);
269 try {
270 check(SUB,M);
271 try_success("getMatrix(int,int,int[])... ","");
272 } catch ( java.lang.RuntimeException e ) {
273 errorCount = try_failure(errorCount,"getMatrix(int,int,int[])... ","submatrix not successfully retreived");
274 }
275 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
276 errorCount = try_failure(errorCount,"getMatrix(int,int,int[])... ","Unexpected ArrayIndexOutOfBoundsException");
277 }
278 try {
279 M = B.getMatrix(badrowindexset,jb,je);
280 errorCount = try_failure(errorCount,"getMatrix(int[],int,int)... ","ArrayIndexOutOfBoundsException expected but not thrown");
281 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
282 try {
283 M = B.getMatrix(rowindexset,jb,je+B.getColumnDimension()+1);
284 errorCount = try_failure(errorCount,"getMatrix(int[],int,int)... ","ArrayIndexOutOfBoundsException expected but not thrown");
285 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
286 try_success("getMatrix(int[],int,int)... ArrayIndexOutOfBoundsException... ","");
287 }
288 } catch ( java.lang.IllegalArgumentException e1 ) {
289 errorCount = try_failure(errorCount,"getMatrix(int[],int,int)... ","ArrayIndexOutOfBoundsException expected but not thrown");
290 }
291 try {
292 M = B.getMatrix(rowindexset,jb,je);
293 try {
294 check(SUB,M);
295 try_success("getMatrix(int[],int,int)... ","");
296 } catch ( java.lang.RuntimeException e ) {
297 errorCount = try_failure(errorCount,"getMatrix(int[],int,int)... ","submatrix not successfully retreived");
298 }
299 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
300 errorCount = try_failure(errorCount,"getMatrix(int[],int,int)... ","Unexpected ArrayIndexOutOfBoundsException");
301 }
302 try {
303 M = B.getMatrix(badrowindexset,columnindexset);
304 errorCount = try_failure(errorCount,"getMatrix(int[],int[])... ","ArrayIndexOutOfBoundsException expected but not thrown");
305 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
306 try {
307 M = B.getMatrix(rowindexset,badcolumnindexset);
308 errorCount = try_failure(errorCount,"getMatrix(int[],int[])... ","ArrayIndexOutOfBoundsException expected but not thrown");
309 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
310 try_success("getMatrix(int[],int[])... ArrayIndexOutOfBoundsException... ","");
311 }
312 } catch ( java.lang.IllegalArgumentException e1 ) {
313 errorCount = try_failure(errorCount,"getMatrix(int[],int[])... ","ArrayIndexOutOfBoundsException expected but not thrown");
314 }
315 try {
316 M = B.getMatrix(rowindexset,columnindexset);
317 try {
318 check(SUB,M);
319 try_success("getMatrix(int[],int[])... ","");
320 } catch ( java.lang.RuntimeException e ) {
321 errorCount = try_failure(errorCount,"getMatrix(int[],int[])... ","submatrix not successfully retreived");
322 }
323 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
324 errorCount = try_failure(errorCount,"getMatrix(int[],int[])... ","Unexpected ArrayIndexOutOfBoundsException");
325 }
326
327 /**
328 Various set methods:
329 **/
330
331 try {
332 B.set(B.getRowDimension(),B.getColumnDimension()-1,0.);
333 errorCount = try_failure(errorCount,"set(int,int,double)... ","OutOfBoundsException expected but not thrown");
334 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
335 try {
336 B.set(B.getRowDimension()-1,B.getColumnDimension(),0.);
337 errorCount = try_failure(errorCount,"set(int,int,double)... ","OutOfBoundsException expected but not thrown");
338 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
339 try_success("set(int,int,double)... OutofBoundsException... ","");
340 }
341 } catch ( java.lang.IllegalArgumentException e1 ) {
342 errorCount = try_failure(errorCount,"set(int,int,double)... ","OutOfBoundsException expected but not thrown");
343 }
344 try {
345 B.set(ib,jb,0.);
346 tmp = B.get(ib,jb);
347 try {
348 check(tmp,0.);
349 try_success("set(int,int,double)... ","");
350 } catch ( java.lang.RuntimeException e ) {
351 errorCount = try_failure(errorCount,"set(int,int,double)... ","Matrix element not successfully set");
352 }
353 } catch ( java.lang.ArrayIndexOutOfBoundsException e1) {
354 errorCount = try_failure(errorCount,"set(int,int,double)... ","Unexpected ArrayIndexOutOfBoundsException");
355 }
356 M = new Matrix(2,3,0.);
357 try {
358 B.setMatrix(ib,ie+B.getRowDimension()+1,jb,je,M);
359 errorCount = try_failure(errorCount,"setMatrix(int,int,int,int,Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
360 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
361 try {
362 B.setMatrix(ib,ie,jb,je+B.getColumnDimension()+1,M);
363 errorCount = try_failure(errorCount,"setMatrix(int,int,int,int,Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
364 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
365 try_success("setMatrix(int,int,int,int,Matrix)... ArrayIndexOutOfBoundsException... ","");
366 }
367 } catch ( java.lang.IllegalArgumentException e1 ) {
368 errorCount = try_failure(errorCount,"setMatrix(int,int,int,int,Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
369 }
370 try {
371 B.setMatrix(ib,ie,jb,je,M);
372 try {
373 check(M.minus(B.getMatrix(ib,ie,jb,je)),M);
374 try_success("setMatrix(int,int,int,int,Matrix)... ","");
375 } catch ( java.lang.RuntimeException e ) {
376 errorCount = try_failure(errorCount,"setMatrix(int,int,int,int,Matrix)... ","submatrix not successfully set");
377 }
378 B.setMatrix(ib,ie,jb,je,SUB);
379 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
380 errorCount = try_failure(errorCount,"setMatrix(int,int,int,int,Matrix)... ","Unexpected ArrayIndexOutOfBoundsException");
381 }
382 try {
383 B.setMatrix(ib,ie+B.getRowDimension()+1,columnindexset,M);
384 errorCount = try_failure(errorCount,"setMatrix(int,int,int[],Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
385 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
386 try {
387 B.setMatrix(ib,ie,badcolumnindexset,M);
388 errorCount = try_failure(errorCount,"setMatrix(int,int,int[],Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
389 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
390 try_success("setMatrix(int,int,int[],Matrix)... ArrayIndexOutOfBoundsException... ","");
391 }
392 } catch ( java.lang.IllegalArgumentException e1 ) {
393 errorCount = try_failure(errorCount,"setMatrix(int,int,int[],Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
394 }
395 try {
396 B.setMatrix(ib,ie,columnindexset,M);
397 try {
398 check(M.minus(B.getMatrix(ib,ie,columnindexset)),M);
399 try_success("setMatrix(int,int,int[],Matrix)... ","");
400 } catch ( java.lang.RuntimeException e ) {
401 errorCount = try_failure(errorCount,"setMatrix(int,int,int[],Matrix)... ","submatrix not successfully set");
402 }
403 B.setMatrix(ib,ie,jb,je,SUB);
404 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
405 errorCount = try_failure(errorCount,"setMatrix(int,int,int[],Matrix)... ","Unexpected ArrayIndexOutOfBoundsException");
406 }
407 try {
408 B.setMatrix(rowindexset,jb,je+B.getColumnDimension()+1,M);
409 errorCount = try_failure(errorCount,"setMatrix(int[],int,int,Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
410 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
411 try {
412 B.setMatrix(badrowindexset,jb,je,M);
413 errorCount = try_failure(errorCount,"setMatrix(int[],int,int,Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
414 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
415 try_success("setMatrix(int[],int,int,Matrix)... ArrayIndexOutOfBoundsException... ","");
416 }
417 } catch ( java.lang.IllegalArgumentException e1 ) {
418 errorCount = try_failure(errorCount,"setMatrix(int[],int,int,Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
419 }
420 try {
421 B.setMatrix(rowindexset,jb,je,M);
422 try {
423 check(M.minus(B.getMatrix(rowindexset,jb,je)),M);
424 try_success("setMatrix(int[],int,int,Matrix)... ","");
425 } catch ( java.lang.RuntimeException e ) {
426 errorCount = try_failure(errorCount,"setMatrix(int[],int,int,Matrix)... ","submatrix not successfully set");
427 }
428 B.setMatrix(ib,ie,jb,je,SUB);
429 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
430 errorCount = try_failure(errorCount,"setMatrix(int[],int,int,Matrix)... ","Unexpected ArrayIndexOutOfBoundsException");
431 }
432 try {
433 B.setMatrix(rowindexset,badcolumnindexset,M);
434 errorCount = try_failure(errorCount,"setMatrix(int[],int[],Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
435 } catch ( java.lang.ArrayIndexOutOfBoundsException e ) {
436 try {
437 B.setMatrix(badrowindexset,columnindexset,M);
438 errorCount = try_failure(errorCount,"setMatrix(int[],int[],Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
439 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
440 try_success("setMatrix(int[],int[],Matrix)... ArrayIndexOutOfBoundsException... ","");
441 }
442 } catch ( java.lang.IllegalArgumentException e1 ) {
443 errorCount = try_failure(errorCount,"setMatrix(int[],int[],Matrix)... ","ArrayIndexOutOfBoundsException expected but not thrown");
444 }
445 try {
446 B.setMatrix(rowindexset,columnindexset,M);
447 try {
448 check(M.minus(B.getMatrix(rowindexset,columnindexset)),M);
449 try_success("setMatrix(int[],int[],Matrix)... ","");
450 } catch ( java.lang.RuntimeException e ) {
451 errorCount = try_failure(errorCount,"setMatrix(int[],int[],Matrix)... ","submatrix not successfully set");
452 }
453 } catch ( java.lang.ArrayIndexOutOfBoundsException e1 ) {
454 errorCount = try_failure(errorCount,"setMatrix(int[],int[],Matrix)... ","Unexpected ArrayIndexOutOfBoundsException");
455 }
456
457 /**
458 Array-like methods:
459 minus
460 minusEquals
461 plus
462 plusEquals
463 arrayLeftDivide
464 arrayLeftDivideEquals
465 arrayRightDivide
466 arrayRightDivideEquals
467 arrayTimes
468 arrayTimesEquals
469 uminus
470 **/
471
472 print("\nTesting array-like methods...\n");
473 S = new Matrix(columnwise,nonconformld);
474 R = Matrix.random(A.getRowDimension(),A.getColumnDimension());
475 A = R;
476 try {
477 S = A.minus(S);
478 errorCount = try_failure(errorCount,"minus conformance check... ","nonconformance not raised");
479 } catch ( IllegalArgumentException e ) {
480 try_success("minus conformance check... ","");
481 }
482 if (A.minus(R).norm1() != 0.) {
483 errorCount = try_failure(errorCount,"minus... ","(difference of identical Matrices is nonzero,\nSubsequent use of minus should be suspect)");
484 } else {
485 try_success("minus... ","");
486 }
487 A = R.copy();
488 A.minusEquals(R);
489 Z = new Matrix(A.getRowDimension(),A.getColumnDimension());
490 try {
491 A.minusEquals(S);
492 errorCount = try_failure(errorCount,"minusEquals conformance check... ","nonconformance not raised");
493 } catch ( IllegalArgumentException e ) {
494 try_success("minusEquals conformance check... ","");
495 }
496 if (A.minus(Z).norm1() != 0.) {
497 errorCount = try_failure(errorCount,"minusEquals... ","(difference of identical Matrices is nonzero,\nSubsequent use of minus should be suspect)");
498 } else {
499 try_success("minusEquals... ","");
500 }
501
502 A = R.copy();
503 B = Matrix.random(A.getRowDimension(),A.getColumnDimension());
504 C = A.minus(B);
505 try {
506 S = A.plus(S);
507 errorCount = try_failure(errorCount,"plus conformance check... ","nonconformance not raised");
508 } catch ( IllegalArgumentException e ) {
509 try_success("plus conformance check... ","");
510 }
511 try {
512 check(C.plus(B),A);
513 try_success("plus... ","");
514 } catch ( java.lang.RuntimeException e ) {
515 errorCount = try_failure(errorCount,"plus... ","(C = A - B, but C + B != A)");
516 }
517 C = A.minus(B);
518 C.plusEquals(B);
519 try {
520 A.plusEquals(S);
521 errorCount = try_failure(errorCount,"plusEquals conformance check... ","nonconformance not raised");
522 } catch ( IllegalArgumentException e ) {
523 try_success("plusEquals conformance check... ","");
524 }
525 try {
526 check(C,A);
527 try_success("plusEquals... ","");
528 } catch ( java.lang.RuntimeException e ) {
529 errorCount = try_failure(errorCount,"plusEquals... ","(C = A - B, but C = C + B != A)");
530 }
531 A = R.uminus();
532 try {
533 check(A.plus(R),Z);
534 try_success("uminus... ","");
535 } catch ( java.lang.RuntimeException e ) {
536 errorCount = try_failure(errorCount,"uminus... ","(-A + A != zeros)");
537 }
538 A = R.copy();
539 O = new Matrix(A.getRowDimension(),A.getColumnDimension(),1.0);
540 C = A.arrayLeftDivide(R);
541 try {
542 S = A.arrayLeftDivide(S);
543 errorCount = try_failure(errorCount,"arrayLeftDivide conformance check... ","nonconformance not raised");
544 } catch ( IllegalArgumentException e ) {
545 try_success("arrayLeftDivide conformance check... ","");
546 }
547 try {
548 check(C,O);
549 try_success("arrayLeftDivide... ","");
550 } catch ( java.lang.RuntimeException e ) {
551 errorCount = try_failure(errorCount,"arrayLeftDivide... ","(M.\\M != ones)");
552 }
553 try {
554 A.arrayLeftDivideEquals(S);
555 errorCount = try_failure(errorCount,"arrayLeftDivideEquals conformance check... ","nonconformance not raised");
556 } catch ( IllegalArgumentException e ) {
557 try_success("arrayLeftDivideEquals conformance check... ","");
558 }
559 A.arrayLeftDivideEquals(R);
560 try {
561 check(A,O);
562 try_success("arrayLeftDivideEquals... ","");
563 } catch ( java.lang.RuntimeException e ) {
564 errorCount = try_failure(errorCount,"arrayLeftDivideEquals... ","(M.\\M != ones)");
565 }
566 A = R.copy();
567 try {
568 A.arrayRightDivide(S);
569 errorCount = try_failure(errorCount,"arrayRightDivide conformance check... ","nonconformance not raised");
570 } catch ( IllegalArgumentException e ) {
571 try_success("arrayRightDivide conformance check... ","");
572 }
573 C = A.arrayRightDivide(R);
574 try {
575 check(C,O);
576 try_success("arrayRightDivide... ","");
577 } catch ( java.lang.RuntimeException e ) {
578 errorCount = try_failure(errorCount,"arrayRightDivide... ","(M./M != ones)");
579 }
580 try {
581 A.arrayRightDivideEquals(S);
582 errorCount = try_failure(errorCount,"arrayRightDivideEquals conformance check... ","nonconformance not raised");
583 } catch ( IllegalArgumentException e ) {
584 try_success("arrayRightDivideEquals conformance check... ","");
585 }
586 A.arrayRightDivideEquals(R);
587 try {
588 check(A,O);
589 try_success("arrayRightDivideEquals... ","");
590 } catch ( java.lang.RuntimeException e ) {
591 errorCount = try_failure(errorCount,"arrayRightDivideEquals... ","(M./M != ones)");
592 }
593 A = R.copy();
594 B = Matrix.random(A.getRowDimension(),A.getColumnDimension());
595 try {
596 S = A.arrayTimes(S);
597 errorCount = try_failure(errorCount,"arrayTimes conformance check... ","nonconformance not raised");
598 } catch ( IllegalArgumentException e ) {
599 try_success("arrayTimes conformance check... ","");
600 }
601 C = A.arrayTimes(B);
602 try {
603 check(C.arrayRightDivideEquals(B),A);
604 try_success("arrayTimes... ","");
605 } catch ( java.lang.RuntimeException e ) {
606 errorCount = try_failure(errorCount,"arrayTimes... ","(A = R, C = A.*B, but C./B != A)");
607 }
608 try {
609 A.arrayTimesEquals(S);
610 errorCount = try_failure(errorCount,"arrayTimesEquals conformance check... ","nonconformance not raised");
611 } catch ( IllegalArgumentException e ) {
612 try_success("arrayTimesEquals conformance check... ","");
613 }
614 A.arrayTimesEquals(B);
615 try {
616 check(A.arrayRightDivideEquals(B),R);
617 try_success("arrayTimesEquals... ","");
618 } catch ( java.lang.RuntimeException e ) {
619 errorCount = try_failure(errorCount,"arrayTimesEquals... ","(A = R, A = A.*B, but A./B != R)");
620 }
621
622 /**
623 I/O methods:
624 read
625 print
626 serializable:
627 writeObject
628 readObject
629 **/
630 print("\nTesting I/O methods...\n");
631 try {
632 DecimalFormat fmt = new DecimalFormat("0.0000E00");
633 fmt.setDecimalFormatSymbols(new DecimalFormatSymbols(Locale.US));
634
635 PrintWriter FILE = new PrintWriter(new FileOutputStream("JamaTestMatrix.out"));
636 A.print(FILE,fmt,10);
637 FILE.close();
638 R = Matrix.read(new BufferedReader(new FileReader("JamaTestMatrix.out")));
639 if (A.minus(R).norm1() < .001 ) {
640 try_success("print()/read()...","");
641 } else {
642 errorCount = try_failure(errorCount,"print()/read()...","Matrix read from file does not match Matrix printed to file");
643 }
644 } catch ( java.io.IOException ioe ) {
645 warningCount = try_warning(warningCount,"print()/read()...","unexpected I/O error, unable to run print/read test; check write permission in current directory and retry");
646 } catch(Exception e) {
647 try {
648 e.printStackTrace(System.out);
649 warningCount = try_warning(warningCount,"print()/read()...","Formatting error... will try JDK1.1 reformulation...");
650 DecimalFormat fmt = new DecimalFormat("0.0000");
651 PrintWriter FILE = new PrintWriter(new FileOutputStream("JamaTestMatrix.out"));
652 A.print(FILE,fmt,10);
653 FILE.close();
654 R = Matrix.read(new BufferedReader(new FileReader("JamaTestMatrix.out")));
655 if (A.minus(R).norm1() < .001 ) {
656 try_success("print()/read()...","");
657 } else {
658 errorCount = try_failure(errorCount,"print()/read() (2nd attempt) ...","Matrix read from file does not match Matrix printed to file");
659 }
660 } catch ( java.io.IOException ioe ) {
661 warningCount = try_warning(warningCount,"print()/read()...","unexpected I/O error, unable to run print/read test; check write permission in current directory and retry");
662 }
663 }
664
665 R = Matrix.random(A.getRowDimension(),A.getColumnDimension());
666 String tmpname = "TMPMATRIX.serial";
667 try {
668 ObjectOutputStream out = new ObjectOutputStream(new FileOutputStream(tmpname));
669 out.writeObject(R);
670 ObjectInputStream sin = new ObjectInputStream(new FileInputStream(tmpname));
671 A = (Matrix) sin.readObject();
672
673 try {
674 check(A,R);
675 try_success("writeObject(Matrix)/readObject(Matrix)...","");
676 } catch ( java.lang.RuntimeException e ) {
677 errorCount = try_failure(errorCount,"writeObject(Matrix)/readObject(Matrix)...","Matrix not serialized correctly");
678 }
679 } catch ( java.io.IOException ioe ) {
680 warningCount = try_warning(warningCount,"writeObject()/readObject()...","unexpected I/O error, unable to run serialization test; check write permission in current directory and retry");
681 } catch(Exception e) {
682 errorCount = try_failure(errorCount,"writeObject(Matrix)/readObject(Matrix)...","unexpected error in serialization test");
683 }
684
685 /**
686 LA methods:
687 transpose
688 times
689 cond
690 rank
691 det
692 trace
693 norm1
694 norm2
695 normF
696 normInf
697 solve
698 solveTranspose
699 inverse
700 chol
701 eig
702 lu
703 qr
704 svd
705 **/
706
707 print("\nTesting linear algebra methods...\n");
708 A = new Matrix(columnwise,3);
709 T = new Matrix(tvals);
710 T = A.transpose();
711 try {
712 check(A.transpose(),T);
713 try_success("transpose...","");
714 } catch ( java.lang.RuntimeException e ) {
715 errorCount = try_failure(errorCount,"transpose()...","transpose unsuccessful");
716 }
717 A.transpose();
718 try {
719 check(A.norm1(),columnsummax);
720 try_success("norm1...","");
721 } catch ( java.lang.RuntimeException e ) {
722 errorCount = try_failure(errorCount,"norm1()...","incorrect norm calculation");
723 }
724 try {
725 check(A.normInf(),rowsummax);
726 try_success("normInf()...","");
727 } catch ( java.lang.RuntimeException e ) {
728 errorCount = try_failure(errorCount,"normInf()...","incorrect norm calculation");
729 }
730 try {
731 check(A.normF(),Math.sqrt(sumofsquares));
732 try_success("normF...","");
733 } catch ( java.lang.RuntimeException e ) {
734 errorCount = try_failure(errorCount,"normF()...","incorrect norm calculation");
735 }
736 try {
737 check(A.trace(),sumofdiagonals);
738 try_success("trace()...","");
739 } catch ( java.lang.RuntimeException e ) {
740 errorCount = try_failure(errorCount,"trace()...","incorrect trace calculation");
741 }
742 try {
743 check(A.getMatrix(0,A.getRowDimension()-1,0,A.getRowDimension()-1).det(),0.);
744 try_success("det()...","");
745 } catch ( java.lang.RuntimeException e ) {
746 errorCount = try_failure(errorCount,"det()...","incorrect determinant calculation");
747 }
748 SQ = new Matrix(square);
749 try {
750 check(A.times(A.transpose()),SQ);
751 try_success("times(Matrix)...","");
752 } catch ( java.lang.RuntimeException e ) {
753 errorCount = try_failure(errorCount,"times(Matrix)...","incorrect Matrix-Matrix product calculation");
754 }
755 try {
756 check(A.times(0.),Z);
757 try_success("times(double)...","");
758 } catch ( java.lang.RuntimeException e ) {
759 errorCount = try_failure(errorCount,"times(double)...","incorrect Matrix-scalar product calculation");
760 }
761
762 A = new Matrix(columnwise,4);
763 QRDecomposition QR = A.qr();
764 R = QR.getR();
765 try {
766 check(A,QR.getQ().times(R));
767 try_success("QRDecomposition...","");
768 } catch ( java.lang.RuntimeException e ) {
769 errorCount = try_failure(errorCount,"QRDecomposition...","incorrect QR decomposition calculation");
770 }
771 SingularValueDecomposition SVD = A.svd();
772 try {
773 check(A,SVD.getU().times(SVD.getS().times(SVD.getV().transpose())));
774 try_success("SingularValueDecomposition...","");
775 } catch ( java.lang.RuntimeException e ) {
776 errorCount = try_failure(errorCount,"SingularValueDecomposition...","incorrect singular value decomposition calculation");
777 }
778 DEF = new Matrix(rankdef);
779 try {
780 check(DEF.rank(),Math.min(DEF.getRowDimension(),DEF.getColumnDimension())-1);
781 try_success("rank()...","");
782 } catch ( java.lang.RuntimeException e ) {
783 errorCount = try_failure(errorCount,"rank()...","incorrect rank calculation");
784 }
785 B = new Matrix(condmat);
786 SVD = B.svd();
787 double [] singularvalues = SVD.getSingularValues();
788 try {
789 check(B.cond(),singularvalues[0]/singularvalues[Math.min(B.getRowDimension(),B.getColumnDimension())-1]);
790 try_success("cond()...","");
791 } catch ( java.lang.RuntimeException e ) {
792 errorCount = try_failure(errorCount,"cond()...","incorrect condition number calculation");
793 }
794 int n = A.getColumnDimension();
795 A = A.getMatrix(0,n-1,0,n-1);
796 A.set(0,0,0.);
797 LUDecomposition LU = A.lu();
798 try {
799 check(A.getMatrix(LU.getPivot(),0,n-1),LU.getL().times(LU.getU()));
800 try_success("LUDecomposition...","");
801 } catch ( java.lang.RuntimeException e ) {
802 errorCount = try_failure(errorCount,"LUDecomposition...","incorrect LU decomposition calculation");
803 }
804 X = A.inverse();
805 try {
806 check(A.times(X),Matrix.identity(3,3));
807 try_success("inverse()...","");
808 } catch ( java.lang.RuntimeException e ) {
809 errorCount = try_failure(errorCount,"inverse()...","incorrect inverse calculation");
810 }
811 O = new Matrix(SUB.getRowDimension(),1,1.0);
812 SOL = new Matrix(sqSolution);
813 SQ = SUB.getMatrix(0,SUB.getRowDimension()-1,0,SUB.getRowDimension()-1);
814 try {
815 check(SQ.solve(SOL),O);
816 try_success("solve()...","");
817 } catch ( java.lang.IllegalArgumentException e1 ) {
818 errorCount = try_failure(errorCount,"solve()...",e1.getMessage());
819 } catch ( java.lang.RuntimeException e ) {
820 errorCount = try_failure(errorCount,"solve()...",e.getMessage());
821 }
822 A = new Matrix(pvals);
823 CholeskyDecomposition Chol = A.chol();
824 Matrix L = Chol.getL();
825 try {
826 check(A,L.times(L.transpose()));
827 try_success("CholeskyDecomposition...","");
828 } catch ( java.lang.RuntimeException e ) {
829 errorCount = try_failure(errorCount,"CholeskyDecomposition...","incorrect Cholesky decomposition calculation");
830 }
831 X = Chol.solve(Matrix.identity(3,3));
832 try {
833 check(A.times(X),Matrix.identity(3,3));
834 try_success("CholeskyDecomposition solve()...","");
835 } catch ( java.lang.RuntimeException e ) {
836 errorCount = try_failure(errorCount,"CholeskyDecomposition solve()...","incorrect Choleskydecomposition solve calculation");
837 }
838 EigenvalueDecomposition Eig = A.eig();
839 Matrix D = Eig.getD();
840 Matrix V = Eig.getV();
841 try {
842 check(A.times(V),V.times(D));
843 try_success("EigenvalueDecomposition (symmetric)...","");
844 } catch ( java.lang.RuntimeException e ) {
845 errorCount = try_failure(errorCount,"EigenvalueDecomposition (symmetric)...","incorrect symmetric Eigenvalue decomposition calculation");
846 }
847 A = new Matrix(evals);
848 Eig = A.eig();
849 D = Eig.getD();
850 V = Eig.getV();
851 try {
852 check(A.times(V),V.times(D));
853 try_success("EigenvalueDecomposition (nonsymmetric)...","");
854 } catch ( java.lang.RuntimeException e ) {
855 errorCount = try_failure(errorCount,"EigenvalueDecomposition (nonsymmetric)...","incorrect nonsymmetric Eigenvalue decomposition calculation");
856 }
857
858 print("\nTestMatrix completed.\n");
859 print("Total errors reported: " + Integer.toString(errorCount) + "\n");
860 print("Total warnings reported: " + Integer.toString(warningCount) + "\n");
861 }
862
863 /** private utility routines **/
864
865 /** Check magnitude of difference of scalars. **/
866
867 private static void check(double x, double y) {
868 double eps = Math.pow(2.0,-52.0);
869 if (x == 0 & Math.abs(y) < 10*eps) return;
870 if (y == 0 & Math.abs(x) < 10*eps) return;
871 if (Math.abs(x-y) > 10*eps*Math.max(Math.abs(x),Math.abs(y))) {
872 throw new RuntimeException("The difference x-y is too large: x = " + Double.toString(x) + " y = " + Double.toString(y));
873 }
874 }
875
876 /** Check norm of difference of "vectors". **/
877
878 private static void check(double[] x, double[] y) {
879 if (x.length == y.length ) {
880 for (int i=0;i<x.length;i++) {
881 check(x[i],y[i]);
882 }
883 } else {
884 throw new RuntimeException("Attempt to compare vectors of different lengths");
885 }
886 }
887
888 /** Check norm of difference of arrays. **/
889
890 private static void check(double[][] x, double[][] y) {
891 Matrix A = new Matrix(x);
892 Matrix B = new Matrix(y);
893 check(A,B);
894 }
895
896 /** Check norm of difference of Matrices. **/
897
898 private static void check(Matrix X, Matrix Y) {
899 double eps = Math.pow(2.0,-52.0);
900 if (X.norm1() == 0. & Y.norm1() < 10*eps) return;
901 if (Y.norm1() == 0. & X.norm1() < 10*eps) return;
902 if (X.minus(Y).norm1() > 1000*eps*Math.max(X.norm1(),Y.norm1())) {
903 throw new RuntimeException("The norm of (X-Y) is too large: " + Double.toString(X.minus(Y).norm1()));
904 }
905 }
906
907 /** Shorten spelling of print. **/
908
909 private static void print (String s) {
910 System.out.print(s);
911 }
912
913 /** Print appropriate messages for successful outcome try **/
914
915 private static void try_success (String s,String e) {
916 print("> " + s + "success\n");
917 if ( e != "" ) {
918 print("> Message: " + e + "\n");
919 }
920 }
921 /** Print appropriate messages for unsuccessful outcome try **/
922
923 private static int try_failure (int count, String s,String e) {
924 print("> " + s + "*** failure ***\n> Message: " + e + "\n");
925 return ++count;
926 }
927
928 /** Print appropriate messages for unsuccessful outcome try **/
929
930 private static int try_warning (int count, String s,String e) {
931 print("> " + s + "*** warning ***\n> Message: " + e + "\n");
932 return ++count;
933 }
934
935 /** Print a row vector. **/
936
937 private static void print(double[] x, int w, int d) {
938 // Use format Fw.d for all elements.
939 System.out.print("\n");
940 new Matrix(x,1).print(w,d);
941 print("\n");
942 }
943
944 }
945