001 /* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017 package org.apache.commons.math.linear; 018 019 import junit.framework.Test; 020 import junit.framework.TestCase; 021 import junit.framework.TestSuite; 022 023 import org.apache.commons.math.TestUtils; 024 025 /** 026 * Test cases for the {@link RealMatrixImpl} class. 027 * 028 * @version $Revision: 783702 $ $Date: 2009-06-11 04:54:02 -0400 (Thu, 11 Jun 2009) $ 029 */ 030 @Deprecated 031 public final class RealMatrixImplTest extends TestCase { 032 033 // 3 x 3 identity matrix 034 protected double[][] id = { {1d,0d,0d}, {0d,1d,0d}, {0d,0d,1d} }; 035 036 // Test data for group operations 037 protected double[][] testData = { {1d,2d,3d}, {2d,5d,3d}, {1d,0d,8d} }; 038 protected double[][] testDataLU = {{2d, 5d, 3d}, {.5d, -2.5d, 6.5d}, {0.5d, 0.2d, .2d}}; 039 protected double[][] testDataPlus2 = { {3d,4d,5d}, {4d,7d,5d}, {3d,2d,10d} }; 040 protected double[][] testDataMinus = { {-1d,-2d,-3d}, {-2d,-5d,-3d}, 041 {-1d,0d,-8d} }; 042 protected double[] testDataRow1 = {1d,2d,3d}; 043 protected double[] testDataCol3 = {3d,3d,8d}; 044 protected double[][] testDataInv = 045 { {-40d,16d,9d}, {13d,-5d,-3d}, {5d,-2d,-1d} }; 046 protected double[] preMultTest = {8,12,33}; 047 protected double[][] testData2 ={ {1d,2d,3d}, {2d,5d,3d}}; 048 protected double[][] testData2T = { {1d,2d}, {2d,5d}, {3d,3d}}; 049 protected double[][] testDataPlusInv = 050 { {-39d,18d,12d}, {15d,0d,0d}, {6d,-2d,7d} }; 051 052 // lu decomposition tests 053 protected double[][] luData = { {2d,3d,3d}, {0d,5d,7d}, {6d,9d,8d} }; 054 protected double[][] luDataLUDecomposition = { {6d,9d,8d}, {0d,5d,7d}, 055 {0.33333333333333,0d,0.33333333333333} }; 056 057 // singular matrices 058 protected double[][] singular = { {2d,3d}, {2d,3d} }; 059 protected double[][] bigSingular = {{1d,2d,3d,4d}, {2d,5d,3d,4d}, 060 {7d,3d,256d,1930d}, {3d,7d,6d,8d}}; // 4th row = 1st + 2nd 061 protected double[][] detData = { {1d,2d,3d}, {4d,5d,6d}, {7d,8d,10d} }; 062 protected double[][] detData2 = { {1d, 3d}, {2d, 4d}}; 063 064 // vectors 065 protected double[] testVector = {1,2,3}; 066 protected double[] testVector2 = {1,2,3,4}; 067 068 // submatrix accessor tests 069 protected double[][] subTestData = {{1, 2, 3, 4}, {1.5, 2.5, 3.5, 4.5}, 070 {2, 4, 6, 8}, {4, 5, 6, 7}}; 071 // array selections 072 protected double[][] subRows02Cols13 = { {2, 4}, {4, 8}}; 073 protected double[][] subRows03Cols12 = { {2, 3}, {5, 6}}; 074 protected double[][] subRows03Cols123 = { {2, 3, 4} , {5, 6, 7}}; 075 // effective permutations 076 protected double[][] subRows20Cols123 = { {4, 6, 8} , {2, 3, 4}}; 077 protected double[][] subRows31Cols31 = {{7, 5}, {4.5, 2.5}}; 078 // contiguous ranges 079 protected double[][] subRows01Cols23 = {{3,4} , {3.5, 4.5}}; 080 protected double[][] subRows23Cols00 = {{2} , {4}}; 081 protected double[][] subRows00Cols33 = {{4}}; 082 // row matrices 083 protected double[][] subRow0 = {{1,2,3,4}}; 084 protected double[][] subRow3 = {{4,5,6,7}}; 085 // column matrices 086 protected double[][] subColumn1 = {{2}, {2.5}, {4}, {5}}; 087 protected double[][] subColumn3 = {{4}, {4.5}, {8}, {7}}; 088 089 // tolerances 090 protected double entryTolerance = 10E-16; 091 protected double normTolerance = 10E-14; 092 093 public RealMatrixImplTest(String name) { 094 super(name); 095 } 096 097 public static Test suite() { 098 TestSuite suite = new TestSuite(RealMatrixImplTest.class); 099 suite.setName("RealMatrixImpl Tests"); 100 return suite; 101 } 102 103 /** test dimensions */ 104 public void testDimensions() { 105 RealMatrixImpl m = new RealMatrixImpl(testData); 106 RealMatrixImpl m2 = new RealMatrixImpl(testData2); 107 assertEquals("testData row dimension",3,m.getRowDimension()); 108 assertEquals("testData column dimension",3,m.getColumnDimension()); 109 assertTrue("testData is square",m.isSquare()); 110 assertEquals("testData2 row dimension",m2.getRowDimension(),2); 111 assertEquals("testData2 column dimension",m2.getColumnDimension(),3); 112 assertTrue("testData2 is not square",!m2.isSquare()); 113 } 114 115 /** test copy functions */ 116 public void testCopyFunctions() { 117 RealMatrixImpl m1 = new RealMatrixImpl(testData); 118 RealMatrixImpl m2 = new RealMatrixImpl(m1.getData()); 119 assertEquals(m2,m1); 120 RealMatrixImpl m3 = new RealMatrixImpl(testData); 121 RealMatrixImpl m4 = new RealMatrixImpl(m3.getData(), false); 122 assertEquals(m4,m3); 123 } 124 125 /** test add */ 126 public void testAdd() { 127 RealMatrixImpl m = new RealMatrixImpl(testData); 128 RealMatrixImpl mInv = new RealMatrixImpl(testDataInv); 129 RealMatrix mPlusMInv = m.add(mInv); 130 double[][] sumEntries = mPlusMInv.getData(); 131 for (int row = 0; row < m.getRowDimension(); row++) { 132 for (int col = 0; col < m.getColumnDimension(); col++) { 133 assertEquals("sum entry entry", 134 testDataPlusInv[row][col],sumEntries[row][col], 135 entryTolerance); 136 } 137 } 138 } 139 140 /** test add failure */ 141 public void testAddFail() { 142 RealMatrixImpl m = new RealMatrixImpl(testData); 143 RealMatrixImpl m2 = new RealMatrixImpl(testData2); 144 try { 145 m.add(m2); 146 fail("IllegalArgumentException expected"); 147 } catch (IllegalArgumentException ex) { 148 // ignored 149 } 150 } 151 152 /** test norm */ 153 public void testNorm() { 154 RealMatrixImpl m = new RealMatrixImpl(testData); 155 RealMatrixImpl m2 = new RealMatrixImpl(testData2); 156 assertEquals("testData norm",14d,m.getNorm(),entryTolerance); 157 assertEquals("testData2 norm",7d,m2.getNorm(),entryTolerance); 158 } 159 160 /** test Frobenius norm */ 161 public void testFrobeniusNorm() { 162 RealMatrixImpl m = new RealMatrixImpl(testData); 163 RealMatrixImpl m2 = new RealMatrixImpl(testData2); 164 assertEquals("testData Frobenius norm", Math.sqrt(117.0), m.getFrobeniusNorm(), entryTolerance); 165 assertEquals("testData2 Frobenius norm", Math.sqrt(52.0), m2.getFrobeniusNorm(), entryTolerance); 166 } 167 168 /** test m-n = m + -n */ 169 public void testPlusMinus() { 170 RealMatrixImpl m = new RealMatrixImpl(testData); 171 RealMatrixImpl m2 = new RealMatrixImpl(testDataInv); 172 TestUtils.assertEquals("m-n = m + -n",m.subtract(m2), 173 m2.scalarMultiply(-1d).add(m),entryTolerance); 174 try { 175 m.subtract(new RealMatrixImpl(testData2)); 176 fail("Expecting illegalArgumentException"); 177 } catch (IllegalArgumentException ex) { 178 // ignored 179 } 180 } 181 182 /** test multiply */ 183 public void testMultiply() { 184 RealMatrixImpl m = new RealMatrixImpl(testData); 185 RealMatrixImpl mInv = new RealMatrixImpl(testDataInv); 186 RealMatrixImpl identity = new RealMatrixImpl(id); 187 RealMatrixImpl m2 = new RealMatrixImpl(testData2); 188 TestUtils.assertEquals("inverse multiply",m.multiply(mInv), 189 identity,entryTolerance); 190 TestUtils.assertEquals("inverse multiply",mInv.multiply(m), 191 identity,entryTolerance); 192 TestUtils.assertEquals("identity multiply",m.multiply(identity), 193 m,entryTolerance); 194 TestUtils.assertEquals("identity multiply",identity.multiply(mInv), 195 mInv,entryTolerance); 196 TestUtils.assertEquals("identity multiply",m2.multiply(identity), 197 m2,entryTolerance); 198 try { 199 m.multiply(new RealMatrixImpl(bigSingular)); 200 fail("Expecting illegalArgumentException"); 201 } catch (IllegalArgumentException ex) { 202 // ignored 203 } 204 } 205 206 //Additional Test for RealMatrixImplTest.testMultiply 207 208 private double[][] d3 = new double[][] {{1,2,3,4},{5,6,7,8}}; 209 private double[][] d4 = new double[][] {{1},{2},{3},{4}}; 210 private double[][] d5 = new double[][] {{30},{70}}; 211 212 public void testMultiply2() { 213 RealMatrix m3 = new RealMatrixImpl(d3); 214 RealMatrix m4 = new RealMatrixImpl(d4); 215 RealMatrix m5 = new RealMatrixImpl(d5); 216 TestUtils.assertEquals("m3*m4=m5", m3.multiply(m4), m5, entryTolerance); 217 } 218 219 /** test trace */ 220 public void testTrace() { 221 RealMatrix m = new RealMatrixImpl(id); 222 assertEquals("identity trace",3d,m.getTrace(),entryTolerance); 223 m = new RealMatrixImpl(testData2); 224 try { 225 m.getTrace(); 226 fail("Expecting NonSquareMatrixException"); 227 } catch (NonSquareMatrixException ex) { 228 // ignored 229 } 230 } 231 232 /** test sclarAdd */ 233 public void testScalarAdd() { 234 RealMatrix m = new RealMatrixImpl(testData); 235 TestUtils.assertEquals("scalar add",new RealMatrixImpl(testDataPlus2), 236 m.scalarAdd(2d),entryTolerance); 237 } 238 239 /** test operate */ 240 public void testOperate() { 241 RealMatrix m = new RealMatrixImpl(id); 242 TestUtils.assertEquals("identity operate", testVector, 243 m.operate(testVector), entryTolerance); 244 TestUtils.assertEquals("identity operate", testVector, 245 m.operate(new ArrayRealVector(testVector)).getData(), entryTolerance); 246 m = new RealMatrixImpl(bigSingular); 247 try { 248 m.operate(testVector); 249 fail("Expecting illegalArgumentException"); 250 } catch (IllegalArgumentException ex) { 251 // ignored 252 } 253 } 254 255 /** test issue MATH-209 */ 256 public void testMath209() { 257 RealMatrix a = new RealMatrixImpl(new double[][] { 258 { 1, 2 }, { 3, 4 }, { 5, 6 } 259 }, false); 260 double[] b = a.operate(new double[] { 1, 1 }); 261 assertEquals(a.getRowDimension(), b.length); 262 assertEquals( 3.0, b[0], 1.0e-12); 263 assertEquals( 7.0, b[1], 1.0e-12); 264 assertEquals(11.0, b[2], 1.0e-12); 265 } 266 267 /** test transpose */ 268 public void testTranspose() { 269 RealMatrix m = new RealMatrixImpl(testData); 270 RealMatrix mIT = new LUDecompositionImpl(m).getSolver().getInverse().transpose(); 271 RealMatrix mTI = new LUDecompositionImpl(m.transpose()).getSolver().getInverse(); 272 TestUtils.assertEquals("inverse-transpose", mIT, mTI, normTolerance); 273 m = new RealMatrixImpl(testData2); 274 RealMatrix mt = new RealMatrixImpl(testData2T); 275 TestUtils.assertEquals("transpose",mt,m.transpose(),normTolerance); 276 } 277 278 /** test preMultiply by vector */ 279 public void testPremultiplyVector() { 280 RealMatrix m = new RealMatrixImpl(testData); 281 TestUtils.assertEquals("premultiply", m.preMultiply(testVector), 282 preMultTest, normTolerance); 283 TestUtils.assertEquals("premultiply", m.preMultiply(new ArrayRealVector(testVector).getData()), 284 preMultTest, normTolerance); 285 m = new RealMatrixImpl(bigSingular); 286 try { 287 m.preMultiply(testVector); 288 fail("expecting IllegalArgumentException"); 289 } catch (IllegalArgumentException ex) { 290 // ignored 291 } 292 } 293 294 public void testPremultiply() { 295 RealMatrix m3 = new RealMatrixImpl(d3); 296 RealMatrix m4 = new RealMatrixImpl(d4); 297 RealMatrix m5 = new RealMatrixImpl(d5); 298 TestUtils.assertEquals("m3*m4=m5", m4.preMultiply(m3), m5, entryTolerance); 299 300 RealMatrixImpl m = new RealMatrixImpl(testData); 301 RealMatrixImpl mInv = new RealMatrixImpl(testDataInv); 302 RealMatrixImpl identity = new RealMatrixImpl(id); 303 TestUtils.assertEquals("inverse multiply",m.preMultiply(mInv), 304 identity,entryTolerance); 305 TestUtils.assertEquals("inverse multiply",mInv.preMultiply(m), 306 identity,entryTolerance); 307 TestUtils.assertEquals("identity multiply",m.preMultiply(identity), 308 m,entryTolerance); 309 TestUtils.assertEquals("identity multiply",identity.preMultiply(mInv), 310 mInv,entryTolerance); 311 try { 312 m.preMultiply(new RealMatrixImpl(bigSingular)); 313 fail("Expecting illegalArgumentException"); 314 } catch (IllegalArgumentException ex) { 315 // ignored 316 } 317 } 318 319 public void testGetVectors() { 320 RealMatrix m = new RealMatrixImpl(testData); 321 TestUtils.assertEquals("get row",m.getRow(0),testDataRow1,entryTolerance); 322 TestUtils.assertEquals("get col",m.getColumn(2),testDataCol3,entryTolerance); 323 try { 324 m.getRow(10); 325 fail("expecting MatrixIndexException"); 326 } catch (MatrixIndexException ex) { 327 // ignored 328 } 329 try { 330 m.getColumn(-1); 331 fail("expecting MatrixIndexException"); 332 } catch (MatrixIndexException ex) { 333 // ignored 334 } 335 } 336 337 public void testGetEntry() { 338 RealMatrix m = new RealMatrixImpl(testData); 339 assertEquals("get entry",m.getEntry(0,1),2d,entryTolerance); 340 try { 341 m.getEntry(10, 4); 342 fail ("Expecting MatrixIndexException"); 343 } catch (MatrixIndexException ex) { 344 // expected 345 } 346 } 347 348 /** test examples in user guide */ 349 public void testExamples() { 350 // Create a real matrix with two rows and three columns 351 double[][] matrixData = { {1d,2d,3d}, {2d,5d,3d}}; 352 RealMatrix m = new RealMatrixImpl(matrixData); 353 // One more with three rows, two columns 354 double[][] matrixData2 = { {1d,2d}, {2d,5d}, {1d, 7d}}; 355 RealMatrix n = new RealMatrixImpl(matrixData2); 356 // Now multiply m by n 357 RealMatrix p = m.multiply(n); 358 assertEquals(2, p.getRowDimension()); 359 assertEquals(2, p.getColumnDimension()); 360 // Invert p 361 RealMatrix pInverse = new LUDecompositionImpl(p).getSolver().getInverse(); 362 assertEquals(2, pInverse.getRowDimension()); 363 assertEquals(2, pInverse.getColumnDimension()); 364 365 // Solve example 366 double[][] coefficientsData = {{2, 3, -2}, {-1, 7, 6}, {4, -3, -5}}; 367 RealMatrix coefficients = new RealMatrixImpl(coefficientsData); 368 double[] constants = {1, -2, 1}; 369 double[] solution = new LUDecompositionImpl(coefficients).getSolver().solve(constants); 370 assertEquals(2 * solution[0] + 3 * solution[1] -2 * solution[2], constants[0], 1E-12); 371 assertEquals(-1 * solution[0] + 7 * solution[1] + 6 * solution[2], constants[1], 1E-12); 372 assertEquals(4 * solution[0] - 3 * solution[1] -5 * solution[2], constants[2], 1E-12); 373 374 } 375 376 // test submatrix accessors 377 public void testGetSubMatrix() { 378 RealMatrix m = new RealMatrixImpl(subTestData); 379 checkGetSubMatrix(m, subRows23Cols00, 2 , 3 , 0, 0, false); 380 checkGetSubMatrix(m, subRows00Cols33, 0 , 0 , 3, 3, false); 381 checkGetSubMatrix(m, subRows01Cols23, 0 , 1 , 2, 3, false); 382 checkGetSubMatrix(m, subRows02Cols13, new int[] { 0, 2 }, new int[] { 1, 3 }, false); 383 checkGetSubMatrix(m, subRows03Cols12, new int[] { 0, 3 }, new int[] { 1, 2 }, false); 384 checkGetSubMatrix(m, subRows03Cols123, new int[] { 0, 3 }, new int[] { 1, 2, 3 }, false); 385 checkGetSubMatrix(m, subRows20Cols123, new int[] { 2, 0 }, new int[] { 1, 2, 3 }, false); 386 checkGetSubMatrix(m, subRows31Cols31, new int[] { 3, 1 }, new int[] { 3, 1 }, false); 387 checkGetSubMatrix(m, subRows31Cols31, new int[] { 3, 1 }, new int[] { 3, 1 }, false); 388 checkGetSubMatrix(m, null, 1, 0, 2, 4, true); 389 checkGetSubMatrix(m, null, -1, 1, 2, 2, true); 390 checkGetSubMatrix(m, null, 1, 0, 2, 2, true); 391 checkGetSubMatrix(m, null, 1, 0, 2, 4, true); 392 checkGetSubMatrix(m, null, new int[] {}, new int[] { 0 }, true); 393 checkGetSubMatrix(m, null, new int[] { 0 }, new int[] { 4 }, true); 394 } 395 396 private void checkGetSubMatrix(RealMatrix m, double[][] reference, 397 int startRow, int endRow, int startColumn, int endColumn, 398 boolean mustFail) { 399 try { 400 RealMatrix sub = m.getSubMatrix(startRow, endRow, startColumn, endColumn); 401 assertEquals(new RealMatrixImpl(reference), sub); 402 if (mustFail) { 403 fail("Expecting MatrixIndexException"); 404 } 405 } catch (MatrixIndexException e) { 406 if (!mustFail) { 407 throw e; 408 } 409 } 410 } 411 412 private void checkGetSubMatrix(RealMatrix m, double[][] reference, 413 int[] selectedRows, int[] selectedColumns, 414 boolean mustFail) { 415 try { 416 RealMatrix sub = m.getSubMatrix(selectedRows, selectedColumns); 417 assertEquals(new RealMatrixImpl(reference), sub); 418 if (mustFail) { 419 fail("Expecting MatrixIndexException"); 420 } 421 } catch (MatrixIndexException e) { 422 if (!mustFail) { 423 throw e; 424 } 425 } 426 } 427 428 public void testCopySubMatrix() { 429 RealMatrix m = new RealMatrixImpl(subTestData); 430 checkCopy(m, subRows23Cols00, 2 , 3 , 0, 0, false); 431 checkCopy(m, subRows00Cols33, 0 , 0 , 3, 3, false); 432 checkCopy(m, subRows01Cols23, 0 , 1 , 2, 3, false); 433 checkCopy(m, subRows02Cols13, new int[] { 0, 2 }, new int[] { 1, 3 }, false); 434 checkCopy(m, subRows03Cols12, new int[] { 0, 3 }, new int[] { 1, 2 }, false); 435 checkCopy(m, subRows03Cols123, new int[] { 0, 3 }, new int[] { 1, 2, 3 }, false); 436 checkCopy(m, subRows20Cols123, new int[] { 2, 0 }, new int[] { 1, 2, 3 }, false); 437 checkCopy(m, subRows31Cols31, new int[] { 3, 1 }, new int[] { 3, 1 }, false); 438 checkCopy(m, subRows31Cols31, new int[] { 3, 1 }, new int[] { 3, 1 }, false); 439 440 checkCopy(m, null, 1, 0, 2, 4, true); 441 checkCopy(m, null, -1, 1, 2, 2, true); 442 checkCopy(m, null, 1, 0, 2, 2, true); 443 checkCopy(m, null, 1, 0, 2, 4, true); 444 checkCopy(m, null, new int[] {}, new int[] { 0 }, true); 445 checkCopy(m, null, new int[] { 0 }, new int[] { 4 }, true); 446 } 447 448 private void checkCopy(RealMatrix m, double[][] reference, 449 int startRow, int endRow, int startColumn, int endColumn, 450 boolean mustFail) { 451 try { 452 double[][] sub = (reference == null) ? 453 new double[1][1] : 454 new double[reference.length][reference[0].length]; 455 m.copySubMatrix(startRow, endRow, startColumn, endColumn, sub); 456 assertEquals(new RealMatrixImpl(reference), new RealMatrixImpl(sub)); 457 if (mustFail) { 458 fail("Expecting MatrixIndexException"); 459 } 460 } catch (MatrixIndexException e) { 461 if (!mustFail) { 462 throw e; 463 } 464 } 465 } 466 467 private void checkCopy(RealMatrix m, double[][] reference, 468 int[] selectedRows, int[] selectedColumns, 469 boolean mustFail) { 470 try { 471 double[][] sub = (reference == null) ? 472 new double[1][1] : 473 new double[reference.length][reference[0].length]; 474 m.copySubMatrix(selectedRows, selectedColumns, sub); 475 assertEquals(new RealMatrixImpl(reference), new RealMatrixImpl(sub)); 476 if (mustFail) { 477 fail("Expecting MatrixIndexException"); 478 } 479 } catch (MatrixIndexException e) { 480 if (!mustFail) { 481 throw e; 482 } 483 } 484 } 485 486 public void testGetRowMatrix() { 487 RealMatrix m = new RealMatrixImpl(subTestData); 488 RealMatrix mRow0 = new RealMatrixImpl(subRow0); 489 RealMatrix mRow3 = new RealMatrixImpl(subRow3); 490 assertEquals("Row0", mRow0, 491 m.getRowMatrix(0)); 492 assertEquals("Row3", mRow3, 493 m.getRowMatrix(3)); 494 try { 495 m.getRowMatrix(-1); 496 fail("Expecting MatrixIndexException"); 497 } catch (MatrixIndexException ex) { 498 // expected 499 } 500 try { 501 m.getRowMatrix(4); 502 fail("Expecting MatrixIndexException"); 503 } catch (MatrixIndexException ex) { 504 // expected 505 } 506 } 507 508 public void testSetRowMatrix() { 509 RealMatrix m = new RealMatrixImpl(subTestData); 510 RealMatrix mRow3 = new RealMatrixImpl(subRow3); 511 assertNotSame(mRow3, m.getRowMatrix(0)); 512 m.setRowMatrix(0, mRow3); 513 assertEquals(mRow3, m.getRowMatrix(0)); 514 try { 515 m.setRowMatrix(-1, mRow3); 516 fail("Expecting MatrixIndexException"); 517 } catch (MatrixIndexException ex) { 518 // expected 519 } 520 try { 521 m.setRowMatrix(0, m); 522 fail("Expecting InvalidMatrixException"); 523 } catch (InvalidMatrixException ex) { 524 // expected 525 } 526 } 527 528 public void testGetColumnMatrix() { 529 RealMatrix m = new RealMatrixImpl(subTestData); 530 RealMatrix mColumn1 = new RealMatrixImpl(subColumn1); 531 RealMatrix mColumn3 = new RealMatrixImpl(subColumn3); 532 assertEquals("Column1", mColumn1, 533 m.getColumnMatrix(1)); 534 assertEquals("Column3", mColumn3, 535 m.getColumnMatrix(3)); 536 try { 537 m.getColumnMatrix(-1); 538 fail("Expecting MatrixIndexException"); 539 } catch (MatrixIndexException ex) { 540 // expected 541 } 542 try { 543 m.getColumnMatrix(4); 544 fail("Expecting MatrixIndexException"); 545 } catch (MatrixIndexException ex) { 546 // expected 547 } 548 } 549 550 public void testSetColumnMatrix() { 551 RealMatrix m = new RealMatrixImpl(subTestData); 552 RealMatrix mColumn3 = new RealMatrixImpl(subColumn3); 553 assertNotSame(mColumn3, m.getColumnMatrix(1)); 554 m.setColumnMatrix(1, mColumn3); 555 assertEquals(mColumn3, m.getColumnMatrix(1)); 556 try { 557 m.setColumnMatrix(-1, mColumn3); 558 fail("Expecting MatrixIndexException"); 559 } catch (MatrixIndexException ex) { 560 // expected 561 } 562 try { 563 m.setColumnMatrix(0, m); 564 fail("Expecting InvalidMatrixException"); 565 } catch (InvalidMatrixException ex) { 566 // expected 567 } 568 } 569 570 public void testGetRowVector() { 571 RealMatrix m = new RealMatrixImpl(subTestData); 572 RealVector mRow0 = new ArrayRealVector(subRow0[0]); 573 RealVector mRow3 = new ArrayRealVector(subRow3[0]); 574 assertEquals("Row0", mRow0, m.getRowVector(0)); 575 assertEquals("Row3", mRow3, m.getRowVector(3)); 576 try { 577 m.getRowVector(-1); 578 fail("Expecting MatrixIndexException"); 579 } catch (MatrixIndexException ex) { 580 // expected 581 } 582 try { 583 m.getRowVector(4); 584 fail("Expecting MatrixIndexException"); 585 } catch (MatrixIndexException ex) { 586 // expected 587 } 588 } 589 590 public void testSetRowVector() { 591 RealMatrix m = new RealMatrixImpl(subTestData); 592 RealVector mRow3 = new ArrayRealVector(subRow3[0]); 593 assertNotSame(mRow3, m.getRowMatrix(0)); 594 m.setRowVector(0, mRow3); 595 assertEquals(mRow3, m.getRowVector(0)); 596 try { 597 m.setRowVector(-1, mRow3); 598 fail("Expecting MatrixIndexException"); 599 } catch (MatrixIndexException ex) { 600 // expected 601 } 602 try { 603 m.setRowVector(0, new ArrayRealVector(5)); 604 fail("Expecting InvalidMatrixException"); 605 } catch (InvalidMatrixException ex) { 606 // expected 607 } 608 } 609 610 public void testGetColumnVector() { 611 RealMatrix m = new RealMatrixImpl(subTestData); 612 RealVector mColumn1 = columnToVector(subColumn1); 613 RealVector mColumn3 = columnToVector(subColumn3); 614 assertEquals("Column1", mColumn1, m.getColumnVector(1)); 615 assertEquals("Column3", mColumn3, m.getColumnVector(3)); 616 try { 617 m.getColumnVector(-1); 618 fail("Expecting MatrixIndexException"); 619 } catch (MatrixIndexException ex) { 620 // expected 621 } 622 try { 623 m.getColumnVector(4); 624 fail("Expecting MatrixIndexException"); 625 } catch (MatrixIndexException ex) { 626 // expected 627 } 628 } 629 630 public void testSetColumnVector() { 631 RealMatrix m = new RealMatrixImpl(subTestData); 632 RealVector mColumn3 = columnToVector(subColumn3); 633 assertNotSame(mColumn3, m.getColumnVector(1)); 634 m.setColumnVector(1, mColumn3); 635 assertEquals(mColumn3, m.getColumnVector(1)); 636 try { 637 m.setColumnVector(-1, mColumn3); 638 fail("Expecting MatrixIndexException"); 639 } catch (MatrixIndexException ex) { 640 // expected 641 } 642 try { 643 m.setColumnVector(0, new ArrayRealVector(5)); 644 fail("Expecting InvalidMatrixException"); 645 } catch (InvalidMatrixException ex) { 646 // expected 647 } 648 } 649 650 private RealVector columnToVector(double[][] column) { 651 double[] data = new double[column.length]; 652 for (int i = 0; i < data.length; ++i) { 653 data[i] = column[i][0]; 654 } 655 return new ArrayRealVector(data, false); 656 } 657 658 public void testGetRow() { 659 RealMatrix m = new RealMatrixImpl(subTestData); 660 checkArrays(subRow0[0], m.getRow(0)); 661 checkArrays(subRow3[0], m.getRow(3)); 662 try { 663 m.getRow(-1); 664 fail("Expecting MatrixIndexException"); 665 } catch (MatrixIndexException ex) { 666 // expected 667 } 668 try { 669 m.getRow(4); 670 fail("Expecting MatrixIndexException"); 671 } catch (MatrixIndexException ex) { 672 // expected 673 } 674 } 675 676 public void testSetRow() { 677 RealMatrix m = new RealMatrixImpl(subTestData); 678 assertTrue(subRow3[0][0] != m.getRow(0)[0]); 679 m.setRow(0, subRow3[0]); 680 checkArrays(subRow3[0], m.getRow(0)); 681 try { 682 m.setRow(-1, subRow3[0]); 683 fail("Expecting MatrixIndexException"); 684 } catch (MatrixIndexException ex) { 685 // expected 686 } 687 try { 688 m.setRow(0, new double[5]); 689 fail("Expecting InvalidMatrixException"); 690 } catch (InvalidMatrixException ex) { 691 // expected 692 } 693 } 694 695 public void testGetColumn() { 696 RealMatrix m = new RealMatrixImpl(subTestData); 697 double[] mColumn1 = columnToArray(subColumn1); 698 double[] mColumn3 = columnToArray(subColumn3); 699 checkArrays(mColumn1, m.getColumn(1)); 700 checkArrays(mColumn3, m.getColumn(3)); 701 try { 702 m.getColumn(-1); 703 fail("Expecting MatrixIndexException"); 704 } catch (MatrixIndexException ex) { 705 // expected 706 } 707 try { 708 m.getColumn(4); 709 fail("Expecting MatrixIndexException"); 710 } catch (MatrixIndexException ex) { 711 // expected 712 } 713 } 714 715 public void testSetColumn() { 716 RealMatrix m = new RealMatrixImpl(subTestData); 717 double[] mColumn3 = columnToArray(subColumn3); 718 assertTrue(mColumn3[0] != m.getColumn(1)[0]); 719 m.setColumn(1, mColumn3); 720 checkArrays(mColumn3, m.getColumn(1)); 721 try { 722 m.setColumn(-1, mColumn3); 723 fail("Expecting MatrixIndexException"); 724 } catch (MatrixIndexException ex) { 725 // expected 726 } 727 try { 728 m.setColumn(0, new double[5]); 729 fail("Expecting InvalidMatrixException"); 730 } catch (InvalidMatrixException ex) { 731 // expected 732 } 733 } 734 735 private double[] columnToArray(double[][] column) { 736 double[] data = new double[column.length]; 737 for (int i = 0; i < data.length; ++i) { 738 data[i] = column[i][0]; 739 } 740 return data; 741 } 742 743 private void checkArrays(double[] expected, double[] actual) { 744 assertEquals(expected.length, actual.length); 745 for (int i = 0; i < expected.length; ++i) { 746 assertEquals(expected[i], actual[i]); 747 } 748 } 749 750 public void testEqualsAndHashCode() { 751 RealMatrixImpl m = new RealMatrixImpl(testData); 752 RealMatrixImpl m1 = (RealMatrixImpl) m.copy(); 753 RealMatrixImpl mt = (RealMatrixImpl) m.transpose(); 754 assertTrue(m.hashCode() != mt.hashCode()); 755 assertEquals(m.hashCode(), m1.hashCode()); 756 assertEquals(m, m); 757 assertEquals(m, m1); 758 assertFalse(m.equals(null)); 759 assertFalse(m.equals(mt)); 760 assertFalse(m.equals(new RealMatrixImpl(bigSingular))); 761 } 762 763 public void testToString() { 764 RealMatrixImpl m = new RealMatrixImpl(testData); 765 assertEquals("RealMatrixImpl{{1.0,2.0,3.0},{2.0,5.0,3.0},{1.0,0.0,8.0}}", 766 m.toString()); 767 m = new RealMatrixImpl(); 768 assertEquals("RealMatrixImpl{}", 769 m.toString()); 770 } 771 772 public void testSetSubMatrix() throws Exception { 773 RealMatrixImpl m = new RealMatrixImpl(testData); 774 m.setSubMatrix(detData2,1,1); 775 RealMatrix expected = MatrixUtils.createRealMatrix 776 (new double[][] {{1.0,2.0,3.0},{2.0,1.0,3.0},{1.0,2.0,4.0}}); 777 assertEquals(expected, m); 778 779 m.setSubMatrix(detData2,0,0); 780 expected = MatrixUtils.createRealMatrix 781 (new double[][] {{1.0,3.0,3.0},{2.0,4.0,3.0},{1.0,2.0,4.0}}); 782 assertEquals(expected, m); 783 784 m.setSubMatrix(testDataPlus2,0,0); 785 expected = MatrixUtils.createRealMatrix 786 (new double[][] {{3.0,4.0,5.0},{4.0,7.0,5.0},{3.0,2.0,10.0}}); 787 assertEquals(expected, m); 788 789 // dimension overflow 790 try { 791 m.setSubMatrix(testData,1,1); 792 fail("expecting MatrixIndexException"); 793 } catch (MatrixIndexException e) { 794 // expected 795 } 796 // dimension underflow 797 try { 798 m.setSubMatrix(testData,-1,1); 799 fail("expecting MatrixIndexException"); 800 } catch (MatrixIndexException e) { 801 // expected 802 } 803 try { 804 m.setSubMatrix(testData,1,-1); 805 fail("expecting MatrixIndexException"); 806 } catch (MatrixIndexException e) { 807 // expected 808 } 809 810 // null 811 try { 812 m.setSubMatrix(null,1,1); 813 fail("expecting NullPointerException"); 814 } catch (NullPointerException e) { 815 // expected 816 } 817 RealMatrixImpl m2 = new RealMatrixImpl(); 818 try { 819 m2.setSubMatrix(testData,0,1); 820 fail("expecting IllegalStateException"); 821 } catch (IllegalStateException e) { 822 // expected 823 } 824 try { 825 m2.setSubMatrix(testData,1,0); 826 fail("expecting IllegalStateException"); 827 } catch (IllegalStateException e) { 828 // expected 829 } 830 831 // ragged 832 try { 833 m.setSubMatrix(new double[][] {{1}, {2, 3}}, 0, 0); 834 fail("expecting IllegalArgumentException"); 835 } catch (IllegalArgumentException e) { 836 // expected 837 } 838 839 // empty 840 try { 841 m.setSubMatrix(new double[][] {{}}, 0, 0); 842 fail("expecting IllegalArgumentException"); 843 } catch (IllegalArgumentException e) { 844 // expected 845 } 846 847 } 848 849 public void testWalk() { 850 int rows = 150; 851 int columns = 75; 852 853 RealMatrix m = new RealMatrixImpl(rows, columns); 854 m.walkInRowOrder(new SetVisitor()); 855 GetVisitor getVisitor = new GetVisitor(); 856 m.walkInOptimizedOrder(getVisitor); 857 assertEquals(rows * columns, getVisitor.getCount()); 858 859 m = new RealMatrixImpl(rows, columns); 860 m.walkInRowOrder(new SetVisitor(), 1, rows - 2, 1, columns - 2); 861 getVisitor = new GetVisitor(); 862 m.walkInOptimizedOrder(getVisitor, 1, rows - 2, 1, columns - 2); 863 assertEquals((rows - 2) * (columns - 2), getVisitor.getCount()); 864 for (int i = 0; i < rows; ++i) { 865 assertEquals(0.0, m.getEntry(i, 0), 0); 866 assertEquals(0.0, m.getEntry(i, columns - 1), 0); 867 } 868 for (int j = 0; j < columns; ++j) { 869 assertEquals(0.0, m.getEntry(0, j), 0); 870 assertEquals(0.0, m.getEntry(rows - 1, j), 0); 871 } 872 873 m = new RealMatrixImpl(rows, columns); 874 m.walkInColumnOrder(new SetVisitor()); 875 getVisitor = new GetVisitor(); 876 m.walkInOptimizedOrder(getVisitor); 877 assertEquals(rows * columns, getVisitor.getCount()); 878 879 m = new RealMatrixImpl(rows, columns); 880 m.walkInColumnOrder(new SetVisitor(), 1, rows - 2, 1, columns - 2); 881 getVisitor = new GetVisitor(); 882 m.walkInOptimizedOrder(getVisitor, 1, rows - 2, 1, columns - 2); 883 assertEquals((rows - 2) * (columns - 2), getVisitor.getCount()); 884 for (int i = 0; i < rows; ++i) { 885 assertEquals(0.0, m.getEntry(i, 0), 0); 886 assertEquals(0.0, m.getEntry(i, columns - 1), 0); 887 } 888 for (int j = 0; j < columns; ++j) { 889 assertEquals(0.0, m.getEntry(0, j), 0); 890 assertEquals(0.0, m.getEntry(rows - 1, j), 0); 891 } 892 893 m = new RealMatrixImpl(rows, columns); 894 m.walkInOptimizedOrder(new SetVisitor()); 895 getVisitor = new GetVisitor(); 896 m.walkInRowOrder(getVisitor); 897 assertEquals(rows * columns, getVisitor.getCount()); 898 899 m = new RealMatrixImpl(rows, columns); 900 m.walkInOptimizedOrder(new SetVisitor(), 1, rows - 2, 1, columns - 2); 901 getVisitor = new GetVisitor(); 902 m.walkInRowOrder(getVisitor, 1, rows - 2, 1, columns - 2); 903 assertEquals((rows - 2) * (columns - 2), getVisitor.getCount()); 904 for (int i = 0; i < rows; ++i) { 905 assertEquals(0.0, m.getEntry(i, 0), 0); 906 assertEquals(0.0, m.getEntry(i, columns - 1), 0); 907 } 908 for (int j = 0; j < columns; ++j) { 909 assertEquals(0.0, m.getEntry(0, j), 0); 910 assertEquals(0.0, m.getEntry(rows - 1, j), 0); 911 } 912 913 m = new RealMatrixImpl(rows, columns); 914 m.walkInOptimizedOrder(new SetVisitor()); 915 getVisitor = new GetVisitor(); 916 m.walkInColumnOrder(getVisitor); 917 assertEquals(rows * columns, getVisitor.getCount()); 918 919 m = new RealMatrixImpl(rows, columns); 920 m.walkInOptimizedOrder(new SetVisitor(), 1, rows - 2, 1, columns - 2); 921 getVisitor = new GetVisitor(); 922 m.walkInColumnOrder(getVisitor, 1, rows - 2, 1, columns - 2); 923 assertEquals((rows - 2) * (columns - 2), getVisitor.getCount()); 924 for (int i = 0; i < rows; ++i) { 925 assertEquals(0.0, m.getEntry(i, 0), 0); 926 assertEquals(0.0, m.getEntry(i, columns - 1), 0); 927 } 928 for (int j = 0; j < columns; ++j) { 929 assertEquals(0.0, m.getEntry(0, j), 0); 930 assertEquals(0.0, m.getEntry(rows - 1, j), 0); 931 } 932 933 } 934 935 public void testSerial() { 936 RealMatrixImpl m = new RealMatrixImpl(testData); 937 assertEquals(m,TestUtils.serializeAndRecover(m)); 938 } 939 940 941 private static class SetVisitor extends DefaultRealMatrixChangingVisitor { 942 @Override 943 public double visit(int i, int j, double value) { 944 return i + j / 1024.0; 945 } 946 } 947 948 private static class GetVisitor extends DefaultRealMatrixPreservingVisitor { 949 private int count = 0; 950 @Override 951 public void visit(int i, int j, double value) { 952 ++count; 953 assertEquals(i + j / 1024.0, value, 0.0); 954 } 955 public int getCount() { 956 return count; 957 } 958 } 959 960 //--------------- -----------------Protected methods 961 962 /** extracts the l and u matrices from compact lu representation */ 963 protected void splitLU(RealMatrix lu, double[][] lowerData, double[][] upperData) throws InvalidMatrixException { 964 if (!lu.isSquare() || lowerData.length != lowerData[0].length || upperData.length != upperData[0].length || 965 lowerData.length != upperData.length 966 || lowerData.length != lu.getRowDimension()) { 967 throw new InvalidMatrixException("incorrect dimensions"); 968 } 969 int n = lu.getRowDimension(); 970 for (int i = 0; i < n; i++) { 971 for (int j = 0; j < n; j++) { 972 if (j < i) { 973 lowerData[i][j] = lu.getEntry(i, j); 974 upperData[i][j] = 0d; 975 } else if (i == j) { 976 lowerData[i][j] = 1d; 977 upperData[i][j] = lu.getEntry(i, j); 978 } else { 979 lowerData[i][j] = 0d; 980 upperData[i][j] = lu.getEntry(i, j); 981 } 982 } 983 } 984 } 985 986 /** Returns the result of applying the given row permutation to the matrix */ 987 protected RealMatrix permuteRows(RealMatrix matrix, int[] permutation) { 988 if (!matrix.isSquare() || matrix.getRowDimension() != permutation.length) { 989 throw new IllegalArgumentException("dimension mismatch"); 990 } 991 int n = matrix.getRowDimension(); 992 int m = matrix.getColumnDimension(); 993 double out[][] = new double[m][n]; 994 for (int i = 0; i < n; i++) { 995 for (int j = 0; j < m; j++) { 996 out[i][j] = matrix.getEntry(permutation[i], j); 997 } 998 } 999 return new RealMatrixImpl(out); 1000 } 1001 1002 // /** Useful for debugging */ 1003 // private void dumpMatrix(RealMatrix m) { 1004 // for (int i = 0; i < m.getRowDimension(); i++) { 1005 // String os = ""; 1006 // for (int j = 0; j < m.getColumnDimension(); j++) { 1007 // os += m.getEntry(i, j) + " "; 1008 // } 1009 // System.out.println(os); 1010 // } 1011 // } 1012 1013 } 1014