00001
00002
00003
00004
00005
00006
00007
00008
00009
00010 #include "matrixFunctionInterface.h"
00011
00012 using namespace std;
00013
00014 using namespace O_SESSAME;
00015
00016
00017
00018
00019
00020
00021
00022
00023 void eigenValues( Matrix _Matrix, Matrix &_EigenVectors, Vector &_RealEigenValues, Vector &_ImaginaryEigenValues )
00024 {
00025
00026 int rows = _Matrix[1].getIndexCount();
00027 int columns = _Matrix[2].getIndexCount();
00028
00029
00030 if ( rows != columns )
00031 {
00032 cerr << "WARNING: Not a square matrix. Not able to determine EigenValues in the eigenValues function." <<endl;
00033 return;
00034 }
00035
00036
00037 void *vmblock;
00038 REAL **matrix;
00039 REAL **eigenVectors;
00040 REAL *realEigenValues;
00041 REAL *imaginaryEigenValues;
00042 int *count;
00043
00044
00045 vmblock = vminit();
00046 matrix = (REAL **) vmalloc( vmblock, MATRIX, rows, columns );
00047 matrix = convertMatrix( _Matrix );
00048 eigenVectors = (REAL **) vmalloc( vmblock, MATRIX, rows, columns );
00049 realEigenValues = (REAL *) vmalloc( vmblock, VEKTOR, rows, 0 );
00050 imaginaryEigenValues = (REAL *) vmalloc( vmblock, VEKTOR, rows, 0 );
00051 count = (int *) vmalloc( vmblock, VVEKTOR, rows, sizeof( *count ) );
00052
00053
00054 eigen( 1, 1, 1, rows, matrix, eigenVectors, realEigenValues, imaginaryEigenValues, count );
00055
00056
00057 _EigenVectors = convertMatrix(eigenVectors, rows);
00058 _RealEigenValues = convertVector(realEigenValues, rows);
00059 _ImaginaryEigenValues = convertVector(imaginaryEigenValues, rows);
00060
00061 return;
00062 }
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073 bool greatestEigenValue( Matrix _Matrix, double &_EigenValue, Vector &_EigenVector, int _MaxIterations )
00074 {
00075
00076 int NMAX = 26;
00077
00078
00079 double eps = .0000000001;
00080
00081
00082 double dta = .00001;
00083
00084
00085 int isError;
00086
00087
00088 int rows = _Matrix[1].getIndexCount();
00089 int columns = _Matrix[2].getIndexCount();
00090
00091
00092 if ( rows != columns )
00093 {
00094 cerr << "WARNING: Not a square matrix. Not able to determine EigenValues in the eigenValues function." <<endl;
00095 return false;
00096 }
00097
00098
00099 int i, j, iterator;
00100
00101
00102 double phi, s;
00103
00104
00105 Vector eigenVectorTemp( NMAX );
00106
00107
00108 _EigenVector = eigenVectorTemp;
00109
00110 for( i = 1; i <= rows; i++ )
00111 eigenVectorTemp(i) = 1.0 / sqrt( double(i) );
00112 isError = -1;
00113 iterator = 1;
00114
00115 while ( isError == -1 && iterator <= _MaxIterations )
00116 {
00117 _EigenValue = 0.0;
00118 for ( i = 1; i <= rows; i++ )
00119 {
00120 _EigenVector(i) = 0.0;
00121 for ( j = 1; j <= rows; j++ )
00122 _EigenVector(i) += _Matrix(i,j) * eigenVectorTemp(j);
00123 if ( fabs( _EigenVector(i) ) > fabs( _EigenValue ) )
00124 _EigenValue = _EigenVector(i);
00125 }
00126
00127 if ( fabs( _EigenValue ) < eps )
00128 isError = 0;
00129 else
00130 {
00131 for ( i = 1; i <= rows; i++ )
00132 _EigenVector(i) /= _EigenValue;
00133 phi = 0.0;
00134 for ( i = 1; i <= rows; i++ )
00135 {
00136 s = fabs( _EigenVector(i) - eigenVectorTemp(i) );
00137 if ( s > phi )
00138 phi = s;
00139 }
00140 if ( phi < dta )
00141 isError = 1;
00142 else
00143 {
00144 for ( i = 1; i <= rows; i++ )
00145 eigenVectorTemp(i) = _EigenVector(i);
00146 iterator++;
00147 }
00148 }
00149
00150 }
00151
00152
00153 switch(isError+1) {
00154 case 0: cerr << "WARNING: No convergence.\n";
00155 return false;
00156 case 1: cerr << "WARNING: Method does not apply.\n"; break;
00157 return false;
00158 }
00159
00160
00161 return true;
00162 }
00163
00164
00165
00166
00167
00168
00169 double norm2( Matrix _Matrix )
00170 {
00171
00172 Vector eigenVector;
00173 double largestEigenValue = 0;
00174
00175
00176 Matrix transposeMatrix = ~_Matrix;
00177
00178
00179 double norm2;
00180
00181
00182 if( greatestEigenValue( ( transposeMatrix * _Matrix ), largestEigenValue, eigenVector, 20 ) )
00183 {
00184
00185
00186 }
00187 else
00188 {
00189 cerr << "Trying alternate method for max eigenvalue." << endl;
00190 Matrix _EigenVectors(3,3);
00191 Vector _RealEigenValues(3);
00192 Vector _ImaginaryEigenValues(3);
00193 eigenValues( transposeMatrix * _Matrix, _EigenVectors, _RealEigenValues, _ImaginaryEigenValues );
00194
00195 largestEigenValue = _RealEigenValues.maxAbs( );
00196
00197 if( largestEigenValue < 1e-4 )
00198 {
00199
00200 cerr << "WARNING: Largest eigenvalue cannot be found. Set to zero." << endl;
00201 }
00202 }
00203
00204
00205 norm2 = sqrt( largestEigenValue );
00206
00207 return( norm2 );
00208
00209 }
00210
00211
00212
00213
00214
00215 REAL ** convertMatrix( Matrix _Matrix )
00216 {
00217 int n = _Matrix[1].getIndexCount();
00218 void *vmblock;
00219 REAL **finalMatrix;
00220
00221 vmblock = vminit();
00222 finalMatrix = (REAL **) vmalloc( vmblock, MATRIX, n, n );
00223
00224 for( int i = 1; i <= n ; i++ )
00225 {
00226 for( int j = 1; j <= n ; j++ )
00227 {
00228 finalMatrix[i-1][j-1] = _Matrix(i,j);
00229 }
00230 }
00231 return finalMatrix;
00232 }
00233
00234
00235
00236
00237
00238 REAL * convertVector( Vector _Vector )
00239 {
00240 int n = _Vector.getIndexCount();
00241 void *vmblock;
00242 REAL *finalVector;
00243
00244 vmblock = vminit();
00245 finalVector = (REAL *) vmalloc( vmblock, VEKTOR, n, 0 );
00246
00247 for( int i = 1; i <= n; i++ )
00248 {
00249 finalVector[i-1] = _Vector(i);
00250 }
00251 return finalVector;
00252 }
00253
00254
00255
00256
00257
00258 Matrix convertMatrix( REAL **_Matrix, int n )
00259 {
00260 Matrix finalMatrix(n,n);
00261
00262 for( int i = 1; i <= n ; i++ )
00263 {
00264 for( int j = 1; j <= n ; j++ )
00265 {
00266 finalMatrix(i,j) = _Matrix[i-1][j-1];
00267 }
00268 }
00269 return finalMatrix;
00270 }
00271
00272
00273
00274
00275
00276 Vector convertVector( REAL *_Vector, int n )
00277 {
00278 Vector finalVector(n);
00279
00280 for( int i = 1; i <= n; i++ )
00281 {
00282 finalVector(i) = _Vector[i-1];
00283 }
00284 return finalVector;
00285 }
00286
00287
00288
00289
00290
00291 Matrix matrixInv3x3( Matrix _A )
00292 {
00293
00294 Matrix _coFactor(3,3);
00295 Matrix _temp(2,2);
00296 _temp(_(1,2),_(1,2) ) = _A( _(2,3),_(2,3) );
00297 _coFactor(1,1) = matrixDet( _temp );
00298 _temp( _(1,2),1 ) = _A( _(2,3),1 );
00299 _temp(_(1,2),2) = _A( _(2,3),3 );
00300 _coFactor(1,2) = matrixDet( _temp );
00301 _temp(_(1,2),_(1,2) ) = _A( _(2,3),_(1,2) );
00302 _coFactor(1,3) = matrixDet( _temp );
00303
00304 _temp( 1,_(1,2) ) = _A( 1,_(2,3) );
00305 _temp( 2,_(1,2) ) = _A( 3,_(2,3) );
00306 _coFactor(2,1) = matrixDet( _temp );
00307 _temp(1,1) = _A(1,1);
00308 _temp(1,2) = _A(1,3);
00309 _temp(2,1) = _A(3,1);
00310 _temp(2,2) = _A(3,3);
00311 _coFactor(2,2) = matrixDet( _temp );
00312 _temp( 1,_(1,2) ) = _A( 1,_(1,2) );
00313 _temp( 2,_(1,2) ) = _A( 3,_(1,2) );
00314 _coFactor(2,3) = matrixDet( _temp );
00315
00316 _temp(_(1,2),_(1,2) ) = _A( _(1,2),_(2,3) );
00317 _coFactor(3,1) = matrixDet( _temp );
00318 _temp(_(1,2),1) = _A( _(1,2),1 );
00319 _temp(_(1,2),2) = _A( _(1,2),3 );
00320 _coFactor(3,2) = matrixDet( _temp );
00321 _temp(_(1,2),_(1,2) ) = _A( _(1,2),_(1,2) );
00322 _coFactor(3,3) = matrixDet( _temp );
00323
00324
00325 double det = _A(1,1)*_coFactor(1,1) - _A(2,1)*_coFactor(2,1) + _A(3,1)*_coFactor(3,1);
00326
00327
00328 _coFactor(1,2) = -_coFactor(1,2);
00329 _coFactor(2,1) = -_coFactor(2,1);
00330 _coFactor(2,3) = -_coFactor(2,3);
00331 _coFactor(3,2) = -_coFactor(3,2);
00332
00333
00334 Matrix invPart = ~_coFactor;
00335
00336
00337 Matrix _Ainv = invPart/det;
00338
00339 return ( _Ainv );
00340 }
00341
00342
00343
00344
00345
00346 double matrixDet( Matrix _A )
00347 {
00348
00349 int rows = _A[1].getIndexCount( );
00350 double _det;
00351 Matrix _Aa(2,2);
00352 switch (rows)
00353 {
00354 case 1:
00355 _det = _A(1,1);
00356 break;
00357 case 2:
00358 _det = matrixDet2x2( _A );
00359 break;
00360 case 3:
00361 _Aa(1,1) = _A(2,1); _Aa(1,2) = _A(2,3);
00362 _Aa(2,1) = _A(3,1); _Aa(2,2) = _A(3,3);
00363 _det = _A(1,1)*matrixDet2x2( _A( _(2,3),_(2,3) ) ) - _A(1,2)*matrixDet2x2( _Aa ) + _A(1,3)*matrixDet2x2( _A( _(2,3), _(1,2) ) );
00364 break;
00365 default:
00366 cerr << "Error: Matrix dimension exceeds current ability of det." << endl;
00367 _det = 0;
00368 break;
00369 }
00370 return ( _det );
00371 }
00372
00373
00374
00375
00376
00377 double matrixDet2x2( Matrix _A )
00378 {
00379 double _det = _A(1,1)*_A(2,2)-_A(1,2)*_A(2,1);
00380 return ( _det );
00381 }
00382
00383
00384
00385
00386
00387
00388
00389
00390
00391
00392
00393
00394
00395
00396
00397
00398
00399
00400
00401
00402