33namespace mcordingley \LinearAlgebra ;
44
55use ArrayAccess ;
6- use Exception ;
76
87class Matrix implements ArrayAccess
98{
@@ -294,14 +293,6 @@ public function inverse()
294293 throw new MatrixException ('This matrix has a zero determinant and is therefore not invertable: ' . print_r ($ this ->internal , true ));
295294 }
296295
297- if ($ this ->isSymmetric ()) {
298- try {
299- return $ this ->choleskyInverse ();
300- } catch (Exception $ exception ) {
301- // Allow this to fall through to the more general algorithm.
302- }
303- }
304-
305296 // Use LU decomposition for the general case.
306297 return $ this ->getLUDecomp ()->inverse ();
307298 }
@@ -363,49 +354,6 @@ public function isSymmetric()
363354 return true ;
364355 }
365356
366- /**
367- * @return Matrix
368- */
369- protected function choleskyInverse ()
370- {
371- //Translated from: http://adorio-research.org/wordpress/?p=4560
372-
373- $ t = $ this ->choleskyDecomposition ()->toArray ();
374-
375- $ B = [];
376-
377- for ($ i = 0 ; $ i < $ this ->rowCount ; ++$ i ) {
378- $ B [] = [];
379-
380- for ($ j = 0 ; $ j < $ this ->rowCount ; ++$ j ) {
381- $ B [$ i ][] = 0 ;
382- }
383- }
384-
385- for ($ j = $ this ->rowCount ; $ j --;) {
386- $ tjj = $ t [$ j ][$ j ];
387-
388- $ S = 0 ;
389- for ($ k = $ j + 1 ; $ k < $ this ->rowCount ; ++$ k ) {
390- $ S += $ t [$ j ][$ k ] * $ B [$ j ][$ k ];
391- }
392-
393- $ B [$ j ][$ j ] = 1 / pow ($ tjj , 2 ) - $ S / $ tjj ;
394-
395- for ($ i = $ j ; $ i --;) {
396- $ sum = 0 ;
397-
398- for ($ k = $ i + 1 ; $ k < $ this ->rowCount ; ++$ k ) {
399- $ sum += $ t [$ i ][$ k ] * $ B [$ k ][$ j ];
400- }
401-
402- $ B [$ j ][$ i ] = $ B [$ i ][$ j ] = -$ sum / $ t [$ i ][$ i ];
403- }
404- }
405-
406- return new Matrix ($ B );
407- }
408-
409357 /**
410358 * @return array
411359 */
@@ -414,81 +362,6 @@ public function toArray()
414362 return $ this ->internal ;
415363 }
416364
417- /**
418- * Returns the Cholesky decomposition of a matrix.
419- * Matrix must be square and symmetrical for this to work.
420- * Returns just the lower triangular matrix, as the upper is a mirror image
421- * of that.
422- *
423- * @return Matrix
424- * @throws MatrixException
425- */
426- protected function choleskyDecomposition ()
427- {
428- $ literal = $ this ->toArray ();
429- $ rows = count ($ literal );
430-
431- $ ztol = 1.0e-5 ;
432-
433- // Zero-fill an array-representation of a matrix
434- $ t = [];
435-
436- for ($ i = 0 ; $ i < $ rows ; ++$ i ) {
437- $ t [] = [];
438-
439- for ($ j = 0 ; $ j < $ rows ; ++$ j ) {
440- $ t [$ i ][] = 0 ;
441- }
442- }
443-
444- for ($ i = 0 ; $ i < $ rows ; ++$ i ) {
445- $ S = 0 ;
446-
447- for ($ k = 0 ; $ k < $ i ; ++$ k ) {
448- $ S += pow ($ t [$ k ][$ i ], 2 );
449- }
450-
451- $ d = $ this ->get ($ i , $ i ) - $ S ;
452-
453- if (abs ($ d ) < $ ztol ) {
454- $ t [$ i ][$ i ] = 0 ;
455- } else {
456- if ($ d < 0 ) {
457- throw new MatrixException ("Matrix not positive-definite " );
458- }
459-
460- $ t [$ i ][$ i ] = sqrt ($ d );
461- }
462-
463- for ($ j = $ i + 1 ; $ j < $ rows ; ++$ j ) {
464- $ S = 0 ;
465-
466- for ($ k = 0 ; $ k < $ i ; ++$ i ) {
467- if (!isset ($ t [$ k ]) || !isset ($ t [$ k ][$ i ]) || !isset ($ t [$ k ][$ j ])) {
468- break ;
469- }
470- $ S += $ t [$ k ][$ i ] * $ t [$ k ][$ j ];
471- }
472-
473- if (abs ($ S ) < $ ztol ) {
474- $ S = 0 ;
475- }
476-
477- try {
478- if (isset ($ t [$ i ]) && isset ($ t [$ i ][$ i ]) && isset ($ literal [$ i ]) && isset ($ literal [$ i ][$ j ])) {
479- $ t [$ i ][$ j ] = ($ literal [$ i ][$ j ] - $ S ) / $ t [$ i ][$ i ];
480- } else {
481- $ t [$ i ][$ j ] = $ S ;
482- }
483- } catch (Exception $ exception ) {
484- throw new MatrixException ("Zero diagonal " );
485- }
486- }
487- }
488-
489- return new Matrix ($ t );
490- }
491-
492365 /**
493366 * @param Matrix $other
494367 * @return Matrix
0 commit comments