Changeset 6ed8c4 in git
- Timestamp:
- Jul 19, 2011, 4:45:41 PM (12 years ago)
- Branches:
- (u'jengelh-datetime', 'ceac47cbc86fe4a15902392bdbb9bd2ae0ea02c6')(u'spielwiese', 'a800fe4b3e9d37a38c5a10cc0ae9dfa0c15a4ee6')
- Children:
- 1f637e0cf55bac728426f222f498b81de378e159
- Parents:
- bb5c2849ef4e9115c1f69238f0aaf689e2be7e2d
- git-author:
- mlee <martinlee84@web.de>2011-07-19 16:45:41+02:00
- git-committer:
- Mohamed Barakat <mohamed.barakat@rwth-aachen.de>2011-11-09 12:52:40+01:00
- Files:
-
- 1 added
- 5 edited
Legend:
- Unmodified
- Added
- Removed
-
kernel/linearAlgebra.cc
rbb5c28 r6ed8c4 17 17 18 18 // include header files 19 #include <kernel/mod2.h> 19 #include "mod2.h" 20 21 #include <coeffs/coeffs.h> 22 #include <coeffs/numbers.h> 23 24 #include <coeffs/mpr_complex.h> 25 #include <polys/monomials/p_polys.h> 26 #include <polys/simpleideals.h> 27 #include <polys/matpol.h> 28 29 // #include <polys/polys.h> 30 20 31 #include <kernel/structs.h> 21 #include <polys/polys.h>22 32 #include <kernel/ideals.h> 23 #include <coeffs/numbers.h>24 #include <polys/matpol.h>25 #include <coeffs/mpr_complex.h>26 33 #include <kernel/linearAlgebra.h> 27 34 … … 39 46 * the negative of nSize will be returned. 40 47 **/ 41 int pivotScore(number n )42 { 43 int s = n Size(n);44 if (rField_is_long_C( currRing) ||45 rField_is_long_R( currRing) ||46 rField_is_R( currRing))48 int pivotScore(number n, const ring r) 49 { 50 int s = n_Size(n, r->cf); 51 if (rField_is_long_C(r) || 52 rField_is_long_R(r) || 53 rField_is_R(r)) 47 54 return -s; 48 55 else … … 58 65 **/ 59 66 bool pivot(const matrix aMat, const int r1, const int r2, const int c1, 60 const int c2, int* bestR, int* bestC )67 const int c2, int* bestR, int* bestC, const ring R) 61 68 { 62 69 int bestScore; int score; bool foundBestScore = false; poly matEntry; … … 69 76 if (matEntry != NULL) 70 77 { 71 score = pivotScore(pGetCoeff(matEntry) );78 score = pivotScore(pGetCoeff(matEntry), R); 72 79 if ((!foundBestScore) || (score < bestScore)) 73 80 { … … 84 91 } 85 92 86 bool unitMatrix(const int n, matrix &unitMat )93 bool unitMatrix(const int n, matrix &unitMat, const ring R) 87 94 { 88 95 if (n < 1) return false; 89 96 unitMat = mpNew(n, n); 90 for (int r = 1; r <= n; r++) MATELEM(unitMat, r, r) = p One();97 for (int r = 1; r <= n; r++) MATELEM(unitMat, r, r) = p_One(R); 91 98 return true; 92 99 } 93 100 94 void luDecomp(const matrix aMat, matrix &pMat, matrix &lMat, matrix &uMat) 101 void luDecomp(const matrix aMat, matrix &pMat, matrix &lMat, matrix &uMat, 102 const ring R) 95 103 { 96 104 int rr = aMat->rows(); … … 101 109 for (int r = 1; r <= rr; r++) 102 110 for (int c = 1; c <= cc; c++) 103 MATELEM(uMat, r, c) = p Copy(aMat->m[c - 1 + (r - 1) * cc]);111 MATELEM(uMat, r, c) = p_Copy(aMat->m[c - 1 + (r - 1) * cc], R); 104 112 105 113 /* we use an int array to store all row permutations; … … 109 117 110 118 /* fill lMat with the (rr x rr) unit matrix */ 111 unitMatrix(rr, lMat );119 unitMatrix(rr, lMat,R); 112 120 113 121 int bestR; int bestC; int intSwap; poly pSwap; int cOffset = 0; … … 116 124 if (r > cc) break; 117 125 while ((r + cOffset <= cc) && 118 (!pivot(uMat, r, rr, r + cOffset, r + cOffset, &bestR, &bestC )))126 (!pivot(uMat, r, rr, r + cOffset, r + cOffset, &bestR, &bestC, R))) 119 127 cOffset++; 120 128 if (r + cOffset <= cc) … … 155 163 if (p != NULL) 156 164 { 157 n = n Div(pGetCoeff(p), pivotElement);158 n Normalize(n);165 n = n_Div(pGetCoeff(p), pivotElement, R->cf); 166 n_Normalize(n,R->cf); 159 167 160 168 /* filling lMat; 161 169 old entry was zero, so no need to call pDelete(.) */ 162 MATELEM(lMat, rGauss, r) = p NSet(nCopy(n));170 MATELEM(lMat, rGauss, r) = p_NSet(n_Copy(n,R->cf),R); 163 171 164 172 /* adjusting uMat: */ 165 MATELEM(uMat, rGauss, r + cOffset) = NULL; p Delete(&p);166 n = n Neg(n);173 MATELEM(uMat, rGauss, r + cOffset) = NULL; p_Delete(&p,R); 174 n = n_Neg(n,R->cf); 167 175 for (int cGauss = r + cOffset + 1; cGauss <= cc; cGauss++) 168 176 { 169 177 MATELEM(uMat, rGauss, cGauss) 170 = p Add(MATELEM(uMat, rGauss, cGauss),171 pp Mult_nn(MATELEM(uMat, r, cGauss), n));172 p Normalize(MATELEM(uMat, rGauss, cGauss));178 = p_Add_q(MATELEM(uMat, rGauss, cGauss), 179 pp_Mult_nn(MATELEM(uMat, r, cGauss), n, R), R); 180 p_Normalize(MATELEM(uMat, rGauss, cGauss),R); 173 181 } 174 182 175 n Delete(&n); /* clean up n */183 n_Delete(&n,R->cf); /* clean up n */ 176 184 } 177 185 } … … 181 189 /* building the permutation matrix from 'permut' */ 182 190 for (int r = 1; r <= rr; r++) 183 MATELEM(pMat, r, permut[r]) = p One();191 MATELEM(pMat, r, permut[r]) = p_One(R); 184 192 delete[] permut; 185 193 … … 192 200 * is given by its LU-decomposition. 193 201 **/ 194 bool luInverse(const matrix aMat, matrix &iMat )202 bool luInverse(const matrix aMat, matrix &iMat, const ring R) 195 203 { /* aMat is guaranteed to be an (n x n)-matrix */ 196 204 matrix pMat; 197 205 matrix lMat; 198 206 matrix uMat; 199 luDecomp(aMat, pMat, lMat, uMat );200 bool result = luInverseFromLUDecomp(pMat, lMat, uMat, iMat );207 luDecomp(aMat, pMat, lMat, uMat, R); 208 bool result = luInverseFromLUDecomp(pMat, lMat, uMat, iMat, R); 201 209 202 210 /* clean-up */ 203 id Delete((ideal*)&pMat);204 id Delete((ideal*)&lMat);205 id Delete((ideal*)&uMat);211 id_Delete((ideal*)&pMat,R); 212 id_Delete((ideal*)&lMat,R); 213 id_Delete((ideal*)&uMat,R); 206 214 207 215 return result; … … 222 230 } 223 231 224 int luRank(const matrix aMat, const bool isRowEchelon )232 int luRank(const matrix aMat, const bool isRowEchelon, const ring R) 225 233 { 226 234 if (isRowEchelon) return rankFromRowEchelonForm(aMat); … … 231 239 matrix lMat; 232 240 matrix uMat; 233 luDecomp(aMat, pMat, lMat, uMat );241 luDecomp(aMat, pMat, lMat, uMat,R); 234 242 int result = rankFromRowEchelonForm(uMat); 235 243 236 244 /* clean-up */ 237 id Delete((ideal*)&pMat);238 id Delete((ideal*)&lMat);239 id Delete((ideal*)&uMat);245 id_Delete((ideal*)&pMat,R); 246 id_Delete((ideal*)&lMat,R); 247 id_Delete((ideal*)&uMat,R); 240 248 241 249 return result; … … 244 252 245 253 bool upperRightTriangleInverse(const matrix uMat, matrix &iMat, 246 bool diagonalIsOne )254 bool diagonalIsOne, const ring R) 247 255 { 248 256 int d = uMat->rows(); … … 270 278 { 271 279 if (diagonalIsOne) 272 MATELEM(iMat, r, r) = p One();280 MATELEM(iMat, r, r) = p_One(R); 273 281 else 274 MATELEM(iMat, r, r) = p NSet(nInvers(pGetCoeff(MATELEM(uMat, r, r))));282 MATELEM(iMat, r, r) = p_NSet(n_Invers(p_GetCoeff(MATELEM(uMat, r, r),R),R->cf),R); 275 283 for (int c = r + 1; c <= d; c++) 276 284 { … … 278 286 for (int k = r + 1; k <= c; k++) 279 287 { 280 q = pp Mult_qq(MATELEM(uMat, r, k), MATELEM(iMat, k, c));281 p = p Add(p, q);288 q = pp_Mult_qq(MATELEM(uMat, r, k), MATELEM(iMat, k, c),R); 289 p = p_Add_q(p, q,R); 282 290 } 283 p = p Neg(p);284 p = p Mult(p, pCopy(MATELEM(iMat, r, r)));285 p Normalize(p);291 p = p_Neg(p,R); 292 p = p_Mult_q(p, p_Copy(MATELEM(iMat, r, r),R),R); 293 p_Normalize(p,R); 286 294 MATELEM(iMat, r, c) = p; 287 295 } … … 345 353 **/ 346 354 bool luInverseFromLUDecomp(const matrix pMat, const matrix lMat, 347 const matrix uMat, matrix &iMat )355 const matrix uMat, matrix &iMat, const ring R) 348 356 { /* uMat is guaranteed to be quadratic */ 349 357 //int d = uMat->rows(); … … 359 367 entries equal to 1 */ 360 368 lowerLeftTriangleInverse(lMat, lMatInverse, true); 361 iMat = mp Mult(mpMult(uMatInverse, lMatInverse), pMat);369 iMat = mp_Mult(mp_Mult(uMatInverse, lMatInverse,R), pMat,R); 362 370 363 371 /* clean-up */ … … 892 900 893 901 void hessenberg(const matrix aMat, matrix &pMat, matrix &hessenbergMat, 894 const number tolerance )902 const number tolerance, const ring R) 895 903 { 896 904 int n = MATROWS(aMat); … … 934 942 idDelete((ideal*)&u); idDelete((ideal*)&pTmp); 935 943 /* now include pTmpFull in pMat (by letting it act from the left) */ 936 pTmp = mp Mult(pTmpFull, pMat); idDelete((ideal*)&pMat);944 pTmp = mp_Mult(pTmpFull, pMat,R); idDelete((ideal*)&pMat); 937 945 pMat = pTmp; 938 946 /* now let pTmpFull act on hessenbergMat from the left and from the 939 947 right (note that pTmpFull is self-inverse) */ 940 pTmp = mp Mult(pTmpFull, hessenbergMat);948 pTmp = mp_Mult(pTmpFull, hessenbergMat,R); 941 949 idDelete((ideal*)&hessenbergMat); 942 hessenbergMat = mp Mult(pTmp, pTmpFull);950 hessenbergMat = mp_Mult(pTmp, pTmpFull, R); 943 951 idDelete((ideal*)&pTmp); idDelete((ideal*)&pTmpFull); 944 952 /* as there may be inaccuracy, we erase those entries of hessenbergMat … … 964 972 matrix &H, /**< [in/out] the matrix to be transformed */ 965 973 int it, /**< [in] iteration index */ 966 const number tolerance /**< [in] accuracy for square roots */ 974 const number tolerance,/**< [in] accuracy for square roots */ 975 const ring R 967 976 ) 968 977 { … … 1048 1057 tmp1 = hessenbergStep(c, uVec, hMat, tolerance); nDelete(&tmp1); 1049 1058 /* now replace H by hMat * H * hMat: */ 1050 matrix wMat = mp Mult(hMat, H); idDelete((ideal*)&H);1051 matrix H1 = mp Mult(wMat, hMat);1059 matrix wMat = mp_Mult(hMat, H,R); idDelete((ideal*)&H); 1060 matrix H1 = mp_Mult(wMat, hMat,R); 1052 1061 idDelete((ideal*)&wMat); idDelete((ideal*)&hMat); 1053 1062 /* now need to re-establish Hessenberg form of H1 and put it in H */ 1054 hessenberg(H1, wMat, H, tolerance );1063 hessenberg(H1, wMat, H, tolerance,R); 1055 1064 idDelete((ideal*)&wMat); idDelete((ideal*)&H1); 1056 1065 } … … 1078 1087 int& eigenValuesL, 1079 1088 const number tol1, 1080 const number tol2 1089 const number tol2, 1090 const ring R 1081 1091 ) 1082 1092 { … … 1114 1124 /* bring currentMat into Hessenberg form to fasten computations: */ 1115 1125 matrix mm1; matrix mm2; 1116 hessenberg(currentMat, mm1, mm2, tol2 );1126 hessenberg(currentMat, mm1, mm2, tol2,R); 1117 1127 idDelete((ideal*)¤tMat); idDelete((ideal*)&mm1); 1118 1128 currentMat = mm2; … … 1143 1153 else /* no deflation found yet */ 1144 1154 { 1145 mpTrafo(currentMat, it, tol2 );1155 mpTrafo(currentMat, it, tol2,R); 1146 1156 it++; /* try again */ 1147 1157 } … … 1197 1207 } 1198 1208 1199 lists qrDoubleShift(const matrix A, const number tol1, const number tol2,1200 const number tol3)1201 {1202 int n = MATROWS(A);1203 matrix* queue = new matrix[n];1204 queue[0] = mpCopy(A); int queueL = 1;1205 number* eigenVs = new number[n]; int eigenL = 0;1206 /* here comes the main call: */1207 bool worked = qrDS(n, queue, queueL, eigenVs, eigenL, tol1, tol2);1208 lists result = (lists)omAlloc(sizeof(slists));1209 if (!worked)1210 {1211 for (int i = 0; i < eigenL; i++)1212 nDelete(&eigenVs[i]);1213 delete [] eigenVs;1214 for (int i = 0; i < queueL; i++)1215 idDelete((ideal*)&queue[i]);1216 delete [] queue;1217 result->Init(1);1218 result->m[0].rtyp = INT_CMD;1219 result->m[0].data = (void*)0; /* a list with a single entry1220 which is the int zero */1221 }1222 else1223 {1224 /* now eigenVs[0..eigenL-1] contain all eigenvalues; among them, there1225 may be equal entries */1226 number* distinctEVs = new number[n]; int distinctC = 0;1227 int* mults = new int[n];1228 for (int i = 0; i < eigenL; i++)1229 {1230 int index = similar(distinctEVs, distinctC, eigenVs[i], tol3);1231 if (index == -1) /* a new eigenvalue */1232 {1233 distinctEVs[distinctC] = nCopy(eigenVs[i]);1234 mults[distinctC++] = 1;1235 }1236 else mults[index]++;1237 nDelete(&eigenVs[i]);1238 }1239 delete [] eigenVs;1240 1241 lists eigenvalues = (lists)omAlloc(sizeof(slists));1242 eigenvalues->Init(distinctC);1243 lists multiplicities = (lists)omAlloc(sizeof(slists));1244 multiplicities->Init(distinctC);1245 for (int i = 0; i < distinctC; i++)1246 {1247 eigenvalues->m[i].rtyp = NUMBER_CMD;1248 eigenvalues->m[i].data = (void*)nCopy(distinctEVs[i]);1249 multiplicities->m[i].rtyp = INT_CMD;1250 multiplicities->m[i].data = (void*)mults[i];1251 nDelete(&distinctEVs[i]);1252 }1253 delete [] distinctEVs; delete [] mults;1254 1255 result->Init(2);1256 result->m[0].rtyp = LIST_CMD;1257 result->m[0].data = (char*)eigenvalues;1258 result->m[1].rtyp = LIST_CMD;1259 result->m[1].data = (char*)multiplicities;1260 }1261 return result;1262 }1263 1264 1209 /* This codes assumes that there are at least two variables in the current 1265 1210 base ring. No assumption is made regarding the monomial ordering. */ … … 1440 1385 { 1441 1386 t = gg; 1442 gg = nGcd(t, pGetCoeff(MATELEM(uMat, r, col)) , currRing);1387 gg = nGcd(t, pGetCoeff(MATELEM(uMat, r, col))); 1443 1388 nDelete(&t); 1444 1389 } … … 1460 1405 { 1461 1406 number g = nGcd(pGetCoeff(MATELEM(uMat, row, col)), 1462 pGetCoeff(MATELEM(uMat, r, col)) , currRing);1407 pGetCoeff(MATELEM(uMat, r, col))); 1463 1408 number f1 = nDiv(pGetCoeff(MATELEM(uMat, r, col)), g); 1464 1409 nNormalize(f1); /* this division works without remainder */ -
kernel/linearAlgebra.h
rbb5c28 r6ed8c4 50 50 matrix &pMat, /**< [out] the row permutation matrix P */ 51 51 matrix &lMat, /**< [out] the lower triangular matrix L */ 52 matrix &uMat /**< [out] the upper row echelon matrix U */ 52 matrix &uMat, /**< [out] the upper row echelon matrix U */ 53 const ring r= currRing /**< [in] current ring */ 53 54 ); 54 55 … … 62 63 **/ 63 64 int pivotScore( 64 number n /**< [in] a non-zero matrix entry */ 65 number n, /**< [in] a non-zero matrix entry */ 66 const ring r= currRing /**< [in] current ring */ 65 67 ); 66 68 … … 87 89 int* bestR, /**< [out] address of row index of best 88 90 pivot element */ 89 int* bestC 91 int* bestC, /**< [out] address of column index of 90 92 best pivot element */ 93 const ring r= currRing /**< [in] current ring */ 91 94 ); 92 95 … … 108 111 bool luInverse( 109 112 const matrix aMat, /**< [in] matrix to be inverted */ 110 matrix &iMat 113 matrix &iMat, /**< [out] inverse of aMat if 111 114 invertible */ 115 const ring r=currRing /**< [in] current ring */ 112 116 ); 113 117 … … 136 140 triangular form */ 137 141 matrix &iMat, /**< [out] inverse of uMat if invertible */ 138 bool diagonalIsOne 142 bool diagonalIsOne,/**< [in] if true, then all diagonal 139 143 entries of uMat are 1 */ 144 const ring r= currRing /**< [in] current ring */ 140 145 ); 141 146 … … 197 202 const matrix uMat, /**< [in] upper right matrix of an LU- 198 203 decomposition */ 199 matrix &iMat /**< [out] inverse of A if invertible */ 204 matrix &iMat, /**< [out] inverse of A if invertible */ 205 const ring r= currRing 200 206 ); 201 207 … … 215 221 int luRank( 216 222 const matrix aMat, /**< [in] input matrix */ 217 const bool isRowEchelon 223 const bool isRowEchelon,/**< [in] if true then aMat is assumed to be 218 224 already in row echelon form */ 225 const ring r= currRing 219 226 ); 220 227 … … 337 344 bool unitMatrix( 338 345 const int n, /**< [in] size of the matrix */ 339 matrix &unitMat /**< [out] the new (nxn) unit matrix */ 346 matrix &unitMat, /**< [out] the new (nxn) unit matrix */ 347 const ring r= currRing /** [in] current ring */ 340 348 ); 341 349 … … 457 465 matrix &pMat, /**< [out] the transformation matrix */ 458 466 matrix &hessenbergMat, /**< [out] the Hessenberg form of aMat */ 459 const number tolerance /**< [in] accuracy */ 467 const number tolerance, /**< [in] accuracy */ 468 const ring r 460 469 ); 461 470 … … 484 493 ); 485 494 486 /**487 * Computes all eigenvalues of a given real quadratic matrix with488 * multiplicites.489 *490 * The method assumes that the current ground field is the complex numbers.491 * Computations are based on the QR double shift algorithm involving492 * Hessenberg form and householder transformations.493 * If the algorithm works, then it returns a list with two entries which494 * are again lists of the same size:495 * _[1][i] is the i-th mutually distinct eigenvalue that was found,496 * _[2][i] is the (int) multiplicity of _[1][i].497 * If the algorithm does not work (due to an ill-posed matrix), a list with498 * the single entry (int)0 is returned.499 * 'tol1' is used for detection of deflation in the actual qr double shift500 * algorithm.501 * 'tol2' is used for ending Heron's iteration whenever square roots502 * are being computed.503 * 'tol3' is used to distinguish between distinct eigenvalues: When504 * the Euclidean distance between two computed eigenvalues is less then505 * tol3, then they will be regarded equal, resulting in a higher506 * multiplicity of the corresponding eigenvalue.507 *508 * @return a list with one entry (int)0, or two entries which are again lists509 **/510 lists qrDoubleShift(511 const matrix A, /**< [in] the quadratic matrix */512 const number tol1, /**< [in] tolerance for deflation */513 const number tol2, /**< [in] tolerance for square roots */514 const number tol3 /**< [in] tolerance for distinguishing515 eigenvalues */516 );517 495 518 496 /** -
libpolys/coeffs/numbers.h
rbb5c28 r6ed8c4 10 10 #include <coeffs/coeffs.h> 11 11 12 /*13 12 // the access methods 14 13 // … … 28 27 #define nIsMOne(n) n_IsMOne(n, currRing->cf) 29 28 #define nGreaterZero(n) n_GreaterZero(n, currRing->cf) 29 #define nGreater(a, b) n_Greater (a,b,currRing->cf) 30 30 #define nWrite(n) n_Write(n,currRing->cf) 31 31 #define nNormalize(n) n_Normalize(n,currRing->cf) … … 44 44 45 45 #define nSetMap(R) n_SetMap(R,currRing->cf) 46 */47 46 48 47 -
libpolys/polys/monomials/ring.h
rbb5c28 r6ed8c4 30 30 struct p_Procs_s; 31 31 typedef struct p_Procs_s p_Procs_s; 32 class slists;33 typedef slists * lists;32 //class slists; 33 //typedef slists * lists; 34 34 class kBucket; 35 35 typedef kBucket* kBucket_pt; … … 716 716 void rSetWeightVec(ring r, int64 *wv); 717 717 718 lists rDecompose(const ring r);719 ring rCompose(const lists L);718 //lists rDecompose(const ring r); 719 //ring rCompose(const lists L); 720 720 ///////////////////////////// 721 721 // Auxillary functions -
libpolys/polys/polys.h
rbb5c28 r6ed8c4 18 18 * 19 19 ***************************************************************/ 20 /* 20 21 21 // deletes old coeff before setting the new one 22 22 #define pSetCoeff(p,n) p_SetCoeff(p,n,currRing) … … 39 39 #define pGetExpSum(p1, p2, i) p_GetExpSum(p1, p2, i, currRing) 40 40 #define pGetExpDiff(p1, p2, i) p_GetExpDiff(p1, p2, i, currRing) 41 */ 41 42 42 43 43 /***************************************************************
Note: See TracChangeset
for help on using the changeset viewer.