hholder.cppGo to the documentation of this file.00001
00002
00003
00004
00005 #define WANT_MATH
00006
00007
00008 #include "include.h"
00009
00010 #include "newmatap.h"
00011
00012 #ifdef use_namespace
00013 namespace NEWMAT {
00014 #endif
00015
00016 #ifdef DO_REPORT
00017 #define REPORT { static ExeCounter ExeCount(__LINE__,16); ++ExeCount; }
00018 #else
00019 #define REPORT {}
00020 #endif
00021
00022
00023
00024
00025 inline Real square(Real x) { return x*x; }
00026
00027 void QRZT(Matrix& X, LowerTriangularMatrix& L)
00028 {
00029 REPORT
00030 Tracer et("QRZT(1)");
00031 int n = X.Ncols(); int s = X.Nrows(); L.ReSize(s);
00032 if (n == 0 || s == 0) { L = 0.0; return; }
00033 Real* xi = X.Store(); int k;
00034 for (int i=0; i<s; i++)
00035 {
00036 Real sum = 0.0;
00037 Real* xi0=xi; k=n; while(k--) { sum += square(*xi++); }
00038 sum = sqrt(sum);
00039 if (sum == 0.0)
00040 {
00041 REPORT
00042 k=n; while(k--) { *xi0++ = 0.0; }
00043 for (int j=i; j<s; j++) L.element(j,i) = 0.0;
00044 }
00045 else
00046 {
00047 L.element(i,i) = sum;
00048 Real* xj0=xi0; k=n; while(k--) { *xj0++ /= sum; }
00049 for (int j=i+1; j<s; j++)
00050 {
00051 sum=0.0;
00052 xi=xi0; Real* xj=xj0; k=n; while(k--) { sum += *xi++ * *xj++; }
00053 xi=xi0; k=n; while(k--) { *xj0++ -= sum * *xi++; }
00054 L.element(j,i) = sum;
00055 }
00056 }
00057 }
00058 }
00059
00060 void QRZT(const Matrix& X, Matrix& Y, Matrix& M)
00061 {
00062 REPORT
00063 Tracer et("QRZT(2)");
00064 int n = X.Ncols(); int s = X.Nrows(); int t = Y.Nrows();
00065 if (Y.Ncols() != n)
00066 { Throw(ProgramException("Unequal row lengths",X,Y)); }
00067 M.ReSize(t,s);
00068 Real* xi = X.Store(); int k;
00069 for (int i=0; i<s; i++)
00070 {
00071 Real* xj0 = Y.Store(); Real* xi0 = xi;
00072 for (int j=0; j<t; j++)
00073 {
00074 Real sum=0.0;
00075 xi=xi0; Real* xj=xj0; k=n; while(k--) { sum += *xi++ * *xj++; }
00076 xi=xi0; k=n; while(k--) { *xj0++ -= sum * *xi++; }
00077 M.element(j,i) = sum;
00078 }
00079 }
00080 }
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111 void QRZ(Matrix& X, UpperTriangularMatrix& U)
00112 {
00113 REPORT
00114 Tracer et("QRZ(1)");
00115 int n = X.Nrows(); int s = X.Ncols(); U.ReSize(s); U = 0.0;
00116 if (n == 0 || s == 0) return;
00117 Real* xi0 = X.Store(); Real* u0 = U.Store(); Real* u;
00118 int j, k; int J = s; int i = s;
00119 while (i--)
00120 {
00121 Real* xj0 = xi0; Real* xi = xi0; k = n;
00122 if (k) for (;;)
00123 {
00124 u = u0; Real Xi = *xi; Real* xj = xj0;
00125 j = J; while(j--) *u++ += Xi * *xj++;
00126 if (!(--k)) break;
00127 xi += s; xj0 += s;
00128 }
00129
00130 Real sum = sqrt(*u0); *u0 = sum; u = u0+1;
00131 if (sum == 0.0)
00132 {
00133 REPORT
00134 j = J - 1; while(j--) *u++ = 0.0;
00135
00136 xj0 = xi0++; k = n;
00137 if (k) for (;;)
00138 {
00139 *xj0 = 0.0;
00140 if (!(--k)) break;
00141 xj0 += s;
00142 }
00143 u0 += J--;
00144 }
00145 else
00146 {
00147 int J1 = J-1; j = J1; while(j--) *u++ /= sum;
00148
00149 xj0 = xi0; xi = xi0++; k = n;
00150 if (k) for (;;)
00151 {
00152 u = u0+1; Real Xi = *xi; Real* xj = xj0;
00153 Xi /= sum; *xj++ = Xi;
00154 j = J1; while(j--) *xj++ -= *u++ * Xi;
00155 if (!(--k)) break;
00156 xi += s; xj0 += s;
00157 }
00158 u0 += J--;
00159 }
00160 }
00161 }
00162
00163 void QRZ(const Matrix& X, Matrix& Y, Matrix& M)
00164 {
00165 REPORT
00166 Tracer et("QRZ(2)");
00167 int n = X.Nrows(); int s = X.Ncols(); int t = Y.Ncols();
00168 if (Y.Nrows() != n)
00169 { Throw(ProgramException("Unequal column lengths",X,Y)); }
00170 M.ReSize(s,t); M = 0;Real* m0 = M.Store(); Real* m;
00171 Real* xi0 = X.Store();
00172 int j, k; int i = s;
00173 while (i--)
00174 {
00175 Real* xj0 = Y.Store(); Real* xi = xi0; k = n;
00176 if (k) for (;;)
00177 {
00178 m = m0; Real Xi = *xi; Real* xj = xj0;
00179 j = t; while(j--) *m++ += Xi * *xj++;
00180 if (!(--k)) break;
00181 xi += s; xj0 += t;
00182 }
00183
00184 xj0 = Y.Store(); xi = xi0++; k = n;
00185 if (k) for (;;)
00186 {
00187 m = m0; Real Xi = *xi; Real* xj = xj0;
00188 j = t; while(j--) *xj++ -= *m++ * Xi;
00189 if (!(--k)) break;
00190 xi += s; xj0 += t;
00191 }
00192 m0 += t;
00193 }
00194 }
00195
00196
00197
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216
00217
00218
00219
00220
00221
00222
00223 void UpdateQRZT(Matrix& X, LowerTriangularMatrix& L)
00224 {
00225 REPORT
00226 Tracer et("UpdateQRZT");
00227 int n = X.Ncols(); int s = X.Nrows();
00228 if (s != L.Nrows())
00229 Throw(ProgramException("Incompatible dimensions",X,L));
00230 if (n == 0 || s == 0) return;
00231 Real* xi = X.Store(); int k;
00232 for (int i=0; i<s; i++)
00233 {
00234 Real r = L.element(i,i);
00235 Real sum = 0.0;
00236 Real* xi0=xi; k=n; while(k--) { sum += square(*xi++); }
00237 sum = sqrt(sum + square(r));
00238 if (sum == 0.0)
00239 {
00240 REPORT
00241 k=n; while(k--) { *xi0++ = 0.0; }
00242 for (int j=i; j<s; j++) L.element(j,i) = 0.0;
00243 }
00244 else
00245 {
00246 Real frs = fabs(r) + sum;
00247 Real a0 = sqrt(frs / sum); Real alpha = a0 / frs;
00248 if (r <= 0) { REPORT L.element(i,i) = sum; alpha = -alpha; }
00249 else { REPORT L.element(i,i) = -sum; }
00250 Real* xj0=xi0; k=n; while(k--) { *xj0++ *= alpha; }
00251 for (int j=i+1; j<s; j++)
00252 {
00253 sum = 0.0;
00254 xi=xi0; Real* xj=xj0; k=n; while(k--) { sum += *xi++ * *xj++; }
00255 sum += a0 * L.element(j,i);
00256 xi=xi0; k=n; while(k--) { *xj0++ -= sum * *xi++; }
00257 L.element(j,i) -= sum * a0;
00258 }
00259 }
00260 }
00261 }
00262
00263 void UpdateQRZ(Matrix& X, UpperTriangularMatrix& U)
00264 {
00265 REPORT
00266 Tracer et("UpdateQRZ");
00267 int n = X.Nrows(); int s = X.Ncols();
00268 if (s != U.Ncols())
00269 Throw(ProgramException("Incompatible dimensions",X,U));
00270 if (n == 0 || s == 0) return;
00271 Real* xi0 = X.Store(); Real* u0 = U.Store(); Real* u;
00272 RowVector V(s); Real* v0 = V.Store(); Real* v; V = 0.0;
00273 int j, k; int J = s; int i = s;
00274 while (i--)
00275 {
00276 Real* xj0 = xi0; Real* xi = xi0; k = n;
00277 if (k) for (;;)
00278 {
00279 v = v0; Real Xi = *xi; Real* xj = xj0;
00280 j = J; while(j--) *v++ += Xi * *xj++;
00281 if (!(--k)) break;
00282 xi += s; xj0 += s;
00283 }
00284
00285 Real r = *u0;
00286 Real sum = sqrt(*v0 + square(r));
00287
00288 if (sum == 0.0)
00289 {
00290 REPORT
00291 u = u0; v = v0;
00292 j = J; while(j--) { *u++ = 0.0; *v++ = 0.0; }
00293 xj0 = xi0++; k = n;
00294 if (k) for (;;)
00295 {
00296 *xj0 = 0.0;
00297 if (!(--k)) break;
00298 xj0 += s;
00299 }
00300 u0 += J--;
00301 }
00302 else
00303 {
00304 Real frs = fabs(r) + sum;
00305 Real a0 = sqrt(frs / sum); Real alpha = a0 / frs;
00306 if (r <= 0) { REPORT alpha = -alpha; *u0 = sum; }
00307 else { REPORT *u0 = -sum; }
00308
00309 j = J - 1; v = v0 + 1; u = u0 + 1;
00310 while (j--)
00311 { *v = a0 * *u + alpha * *v; *u -= a0 * *v; ++v; ++u; }
00312
00313 xj0 = xi0; xi = xi0++; k = n;
00314 if (k) for (;;)
00315 {
00316 v = v0 + 1; Real Xi = *xi; Real* xj = xj0;
00317 Xi *= alpha; *xj++ = Xi;
00318 j = J - 1; while(j--) *xj++ -= *v++ * Xi;
00319 if (!(--k)) break;
00320 xi += s; xj0 += s;
00321 }
00322
00323 j = J; v = v0;
00324 while (j--) *v++ = 0.0;
00325
00326 u0 += J--;
00327 }
00328 }
00329 }
00330
00331
00332 #ifdef use_namespace
00333 }
00334 #endif
00335
|