SND@LHC Software
Loading...
Searching...
No Matches
VMatrix.cc
Go to the documentation of this file.
1/*
2 * VMatrix.cpp
3 *
4 * Created on: Feb 15, 2012
5 * Author: kleinwrt
6 */
7
8#include "VMatrix.h"
9
11namespace gbl {
12
13/*********** simple Matrix based on std::vector<double> **********/
14
15VMatrix::VMatrix(const unsigned int nRows, const unsigned int nCols) :
16 numRows(nRows), numCols(nCols), theVec(nRows * nCols) {
17}
18
19VMatrix::VMatrix(const VMatrix &aMatrix) :
20 numRows(aMatrix.numRows), numCols(aMatrix.numCols), theVec(
21 aMatrix.theVec) {
22
23}
24
27
29
33void VMatrix::resize(const unsigned int nRows, const unsigned int nCols) {
34 numRows = nRows;
35 numCols = nCols;
36 theVec.resize(nRows * nCols);
37}
38
40
44 VMatrix aResult(numCols, numRows);
45 for (unsigned int i = 0; i < numRows; ++i) {
46 for (unsigned int j = 0; j < numCols; ++j) {
47 aResult(j, i) = theVec[numCols * i + j];
48 }
49 }
50 return aResult;
51}
52
54
57unsigned int VMatrix::getNumRows() const {
58 return numRows;
59}
60
62
65unsigned int VMatrix::getNumCols() const {
66 return numCols;
67}
68
70void VMatrix::print() const {
71 std::cout << " VMatrix: " << numRows << "*" << numCols << std::endl;
72 for (unsigned int i = 0; i < numRows; ++i) {
73 for (unsigned int j = 0; j < numCols; ++j) {
74 if (j % 5 == 0) {
75 std::cout << std::endl << std::setw(4) << i << ","
76 << std::setw(4) << j << "-" << std::setw(4)
77 << std::min(j + 4, numCols) << ":";
78 }
79 std::cout << std::setw(13) << theVec[numCols * i + j];
80 }
81 }
82 std::cout << std::endl << std::endl;
83}
84
86VVector VMatrix::operator*(const VVector &aVector) const {
87 VVector aResult(numRows);
88 for (unsigned int i = 0; i < this->numRows; ++i) {
89 double sum = 0.0;
90 for (unsigned int j = 0; j < this->numCols; ++j) {
91 sum += theVec[numCols * i + j] * aVector(j);
92 }
93 aResult(i) = sum;
94 }
95 return aResult;
96}
97
99VMatrix VMatrix::operator*(const VMatrix &aMatrix) const {
100
101 VMatrix aResult(numRows, aMatrix.numCols);
102 for (unsigned int i = 0; i < numRows; ++i) {
103 for (unsigned int j = 0; j < aMatrix.numCols; ++j) {
104 double sum = 0.0;
105 for (unsigned int k = 0; k < numCols; ++k) {
106 sum += theVec[numCols * i + k] * aMatrix(k, j);
107 }
108 aResult(i, j) = sum;
109 }
110 }
111 return aResult;
112}
113
115VMatrix VMatrix::operator+(const VMatrix &aMatrix) const {
116 VMatrix aResult(numRows, numCols);
117 for (unsigned int i = 0; i < numRows; ++i) {
118 for (unsigned int j = 0; j < numCols; ++j) {
119 aResult(i, j) = theVec[numCols * i + j] + aMatrix(i, j);
120 }
121 }
122 return aResult;
123}
124
127 if (this != &aMatrix) { // Gracefully handle self assignment
128 numRows = aMatrix.getNumRows();
129 numCols = aMatrix.getNumCols();
130 theVec.resize(numRows * numCols);
131 for (unsigned int i = 0; i < numRows; ++i) {
132 for (unsigned int j = 0; j < numCols; ++j) {
133 theVec[numCols * i + j] = aMatrix(i, j);
134 }
135 }
136 }
137 return *this;
138}
139
140/*********** simple symmetric Matrix based on std::vector<double> **********/
141
142VSymMatrix::VSymMatrix(const unsigned int nRows) :
143 numRows(nRows), theVec((nRows * nRows + nRows) / 2) {
144}
145
148
150
153void VSymMatrix::resize(const unsigned int nRows) {
154 numRows = nRows;
155 theVec.resize((nRows * nRows + nRows) / 2);
156}
157
159
162unsigned int VSymMatrix::getNumRows() const {
163 return numRows;
164}
165
167void VSymMatrix::print() const {
168 std::cout << " VSymMatrix: " << numRows << "*" << numRows << std::endl;
169 for (unsigned int i = 0; i < numRows; ++i) {
170 for (unsigned int j = 0; j <= i; ++j) {
171 if (j % 5 == 0) {
172 std::cout << std::endl << std::setw(4) << i << ","
173 << std::setw(4) << j << "-" << std::setw(4)
174 << std::min(j + 4, i) << ":";
175 }
176 std::cout << std::setw(13) << theVec[(i * i + i) / 2 + j];
177 }
178 }
179 std::cout << std::endl << std::endl;
180}
181
184 VSymMatrix aResult(numRows);
185 for (unsigned int i = 0; i < numRows; ++i) {
186 for (unsigned int j = 0; j <= i; ++j) {
187 aResult(i, j) = theVec[(i * i + i) / 2 + j] - aMatrix(i, j);
188 }
189 }
190 return aResult;
191}
192
194VVector VSymMatrix::operator*(const VVector &aVector) const {
195 VVector aResult(numRows);
196 for (unsigned int i = 0; i < numRows; ++i) {
197 aResult(i) = theVec[(i * i + i) / 2 + i] * aVector(i);
198 for (unsigned int j = 0; j < i; ++j) {
199 aResult(j) += theVec[(i * i + i) / 2 + j] * aVector(i);
200 aResult(i) += theVec[(i * i + i) / 2 + j] * aVector(j);
201 }
202 }
203 return aResult;
204}
205
207VMatrix VSymMatrix::operator*(const VMatrix &aMatrix) const {
208 unsigned int nCol = aMatrix.getNumCols();
209 VMatrix aResult(numRows, nCol);
210 for (unsigned int l = 0; l < nCol; ++l) {
211 for (unsigned int i = 0; i < numRows; ++i) {
212 aResult(i, l) = theVec[(i * i + i) / 2 + i] * aMatrix(i, l);
213 for (unsigned int j = 0; j < i; ++j) {
214 aResult(j, l) += theVec[(i * i + i) / 2 + j] * aMatrix(i, l);
215 aResult(i, l) += theVec[(i * i + i) / 2 + j] * aMatrix(j, l);
216 }
217 }
218 }
219 return aResult;
220}
221
222/*********** simple Vector based on std::vector<double> **********/
223
224VVector::VVector(const unsigned int nRows) :
225 numRows(nRows), theVec(nRows) {
226}
227
228VVector::VVector(const VVector &aVector) :
229 numRows(aVector.numRows), theVec(aVector.theVec) {
230
231}
232
235
237
240void VVector::resize(const unsigned int nRows) {
241 numRows = nRows;
242 theVec.resize(nRows);
243}
244
246
251VVector VVector::getVec(unsigned int len, unsigned int start) const {
252 VVector aResult(len);
253 std::memcpy(&aResult.theVec[0], &theVec[start], sizeof(double) * len);
254 return aResult;
255}
256
258
262void VVector::putVec(const VVector &aVector, unsigned int start) {
263 std::memcpy(&theVec[start], &aVector.theVec[0],
264 sizeof(double) * aVector.numRows);
265}
266
268
271unsigned int VVector::getNumRows() const {
272 return numRows;
273}
274
276void VVector::print() const {
277 std::cout << " VVector: " << numRows << std::endl;
278 for (unsigned int i = 0; i < numRows; ++i) {
279
280 if (i % 5 == 0) {
281 std::cout << std::endl << std::setw(4) << i << "-" << std::setw(4)
282 << std::min(i + 4, numRows) << ":";
283 }
284 std::cout << std::setw(13) << theVec[i];
285 }
286 std::cout << std::endl << std::endl;
287}
288
290VVector VVector::operator-(const VVector &aVector) const {
291 VVector aResult(numRows);
292 for (unsigned int i = 0; i < numRows; ++i) {
293 aResult(i) = theVec[i] - aVector(i);
294 }
295 return aResult;
296}
297
300 if (this != &aVector) { // Gracefully handle self assignment
301 numRows = aVector.getNumRows();
302 theVec.resize(numRows);
303 for (unsigned int i = 0; i < numRows; ++i) {
304 theVec[i] = aVector(i);
305 }
306 }
307 return *this;
308}
309
310/*============================================================================
311 from mpnum.F (MillePede-II by V. Blobel, Univ. Hamburg)
312 ============================================================================*/
314
326unsigned int VSymMatrix::invert() {
327
328 const double eps = 1.0E-10;
329 unsigned int aSize = numRows;
330 std::vector<int> next(aSize);
331 std::vector<double> diag(aSize);
332 int nSize = aSize;
333
334 int first = 1;
335 for (int i = 1; i <= nSize; ++i) {
336 next[i - 1] = i + 1; // set "next" pointer
337 diag[i - 1] = fabs(theVec[(i * i + i) / 2 - 1]); // save abs of diagonal elements
338 }
339 next[aSize - 1] = -1; // end flag
340
341 unsigned int nrank = 0;
342 for (int i = 1; i <= nSize; ++i) { // start of loop
343 int k = 0;
344 double vkk = 0.0;
345
346 int jCandidate = first;
347 int previous = 0;
348 int last = previous;
349 // look for pivot
350 while (jCandidate > 0) {
351 int jj = (jCandidate * jCandidate + jCandidate) / 2 - 1;
352 if (fabs(theVec[jj]) > std::max(fabs(vkk), eps * diag[jCandidate - 1])) {
353 vkk = theVec[jj];
354 k = jCandidate;
355 last = previous;
356 }
357 previous = jCandidate;
358 jCandidate = next[jCandidate - 1];
359 }
360 // pivot found
361 if (k > 0) {
362 int kk = (k * k + k) / 2 - 1;
363 if (last <= 0) {
364 first = next[k - 1];
365 } else {
366 next[last - 1] = next[k - 1];
367 }
368 next[k - 1] = 0; // index is used, reset
369 nrank++; // increase rank and ...
370
371 vkk = 1.0 / vkk;
372 theVec[kk] = -vkk;
373 int jk = kk - k;
374 int jl = -1;
375 for (int j = 1; j <= nSize; ++j) { // elimination
376 if (j == k) {
377 jk = kk;
378 jl += j;
379 } else {
380 if (j < k) {
381 ++jk;
382 } else {
383 jk += j - 1;
384 }
385
386 double vjk = theVec[jk];
387 theVec[jk] = vkk * vjk;
388 int lk = kk - k;
389 if (j >= k) {
390 for (int l = 1; l <= k - 1; ++l) {
391 ++jl;
392 ++lk;
393 theVec[jl] -= theVec[lk] * vjk;
394 }
395 ++jl;
396 lk = kk;
397 for (int l = k + 1; l <= j; ++l) {
398 ++jl;
399 lk += l - 1;
400 theVec[jl] -= theVec[lk] * vjk;
401 }
402 } else {
403 for (int l = 1; l <= j; ++l) {
404 ++jl;
405 ++lk;
406 theVec[jl] -= theVec[lk] * vjk;
407 }
408 }
409 }
410 }
411 } else {
412 for (int n = 1; n <= nSize; ++n) {
413 if (next[n - 1] >= 0) {
414 int nn = (n * n - n) / 2 - 1;
415 for (int j = 1; j <= nSize; ++j) {
416 if (next[j - 1] >= 0) {
417 theVec[nn + j] = 0.0; // clear matrix row/col
418 }
419 }
420 }
421 }
422 throw 1; // singular
423 }
424 }
425 for (int ij = 0; ij < (nSize * nSize + nSize) / 2; ++ij) {
426 theVec[ij] = -theVec[ij]; // finally reverse sign of all matrix elements
427 }
428 return nrank;
429}
430}
Simple Matrix based on std::vector<double>
Definition VMatrix.h:42
unsigned int getNumCols() const
Get number of columns.
Definition VMatrix.cc:65
VMatrix transpose() const
Get transposed matrix.
Definition VMatrix.cc:43
VVector operator*(const VVector &aVector) const
Multiplication Matrix*Vector.
Definition VMatrix.cc:86
unsigned int numRows
Number of rows.
Definition VMatrix.h:59
unsigned int getNumRows() const
Get number of rows.
Definition VMatrix.cc:57
void resize(const unsigned int nRows, const unsigned int nCols)
Resize Matrix.
Definition VMatrix.cc:33
VMatrix operator+(const VMatrix &aMatrix) const
Addition Matrix+Matrix.
Definition VMatrix.cc:115
unsigned int numCols
Number of columns.
Definition VMatrix.h:60
VMatrix & operator=(const VMatrix &aMatrix)
Assignment Matrix=Matrix.
Definition VMatrix.cc:126
VMatrix(const unsigned int nRows=0, const unsigned int nCols=0)
Definition VMatrix.cc:15
std::vector< double > theVec
Data.
Definition VMatrix.h:61
void print() const
Print matrix.
Definition VMatrix.cc:70
virtual ~VMatrix()
Definition VMatrix.cc:25
Simple symmetric Matrix based on std::vector<double>
Definition VMatrix.h:65
VSymMatrix(const unsigned int nRows=0)
Definition VMatrix.cc:142
VVector operator*(const VVector &aVector) const
Multiplication SymMatrix*Vector.
Definition VMatrix.cc:194
void print() const
Print matrix.
Definition VMatrix.cc:167
unsigned int invert()
Matrix inversion.
Definition VMatrix.cc:326
unsigned int getNumRows() const
Get number of rows (= number of colums).
Definition VMatrix.cc:162
std::vector< double > theVec
Data (symmetric storage)
Definition VMatrix.h:80
unsigned int numRows
Number of rows.
Definition VMatrix.h:79
void resize(const unsigned int nRows)
Resize symmetric matrix.
Definition VMatrix.cc:153
virtual ~VSymMatrix()
Definition VMatrix.cc:146
VSymMatrix operator-(const VMatrix &aMatrix) const
Subtraction SymMatrix-(sym)Matrix.
Definition VMatrix.cc:183
Simple Vector based on std::vector<double>
Definition VMatrix.h:22
virtual ~VVector()
Definition VMatrix.cc:233
void putVec(const VVector &aVector, unsigned int start=0)
Put part of vector.
Definition VMatrix.cc:262
std::vector< double > theVec
Data.
Definition VMatrix.h:38
VVector getVec(unsigned int len, unsigned int start=0) const
Get part of vector.
Definition VMatrix.cc:251
VVector operator-(const VVector &aVector) const
Subtraction Vector-Vector.
Definition VMatrix.cc:290
void resize(const unsigned int nRows)
Resize vector.
Definition VMatrix.cc:240
VVector(const unsigned int nRows=0)
Definition VMatrix.cc:224
unsigned int numRows
Number of rows.
Definition VMatrix.h:37
void print() const
Print vector.
Definition VMatrix.cc:276
VVector & operator=(const VVector &aVector)
Assignment Vector=Vector.
Definition VMatrix.cc:299
unsigned int getNumRows() const
Get number of rows.
Definition VMatrix.cc:271
Namespace for the general broken lines package.