From d5052f1c296dddf51b3e83d59bf3e3c1952cb2d0 Mon Sep 17 00:00:00 2001 From: cathook Date: Sun, 1 Jun 2014 13:56:57 +0800 Subject: big chnage --- doc/html/Matrix_8h_source.html | 414 +++++++++++++++++++++++++++++++++++++++++ 1 file changed, 414 insertions(+) create mode 100644 doc/html/Matrix_8h_source.html (limited to 'doc/html/Matrix_8h_source.html') diff --git a/doc/html/Matrix_8h_source.html b/doc/html/Matrix_8h_source.html new file mode 100644 index 0000000..2a12c80 --- /dev/null +++ b/doc/html/Matrix_8h_source.html @@ -0,0 +1,414 @@ + + + + + + + +Templates -- Meow: meowpp/math/Matrix.h Source File + + + + + + + + + + + +
+
+ + + + + + + +
+
Templates -- Meow +  1.1.2 +
+
不能,也不應該先編譯成obj-file的templates
+
+
+ + +
+
+ +
+
+
+ +
+
+
+
Matrix.h
+
+
+Go to the documentation of this file.
1 #ifndef math_Matrix_H__
+
2 #define math_Matrix_H__
+
3 
+
4 #include "utility.h"
+
5 
+
6 #include "../Self.h"
+
7 
+
8 #include <vector>
+
9 #include <algorithm>
+
10 
+
11 #include <cstdlib>
+
12 
+
13 namespace meow {
+
19 template<class Entry>
+
20 class Matrix {
+
21 private:
+
22  struct Myself {
+
23  size_t rows_;
+
24  size_t cols_;
+
25  std::vector<Entry> entries_;
+
26  Myself(): rows_(0), cols_(0), entries_(0) {
+
27  }
+
28  ~Myself() {
+
29  }
+
30  size_t index(size_t r, size_t c) const {
+
31  return r * cols_ + c;
+
32  }
+
33  Myself& copyFrom(Myself const& m) {
+
34  rows_ = m. rows_;
+
35  cols_ = m. cols_;
+
36  entries_ = m.entries_;
+
37  return *this;
+
38  }
+
39  };
+
40  Self<Myself> const self;
+
41 public:
+
48  Matrix(): self(true) { }
+
49 
+
57  Matrix(Matrix const& m): self(false) { self().copyFrom(m.self); }
+
58 
+
68  Matrix(size_t r, size_t c, Entry const& e): self(true) { reset(r, c, e); }
+
69 
+
71  ~Matrix() { }
+
72 
+
81  Matrix& copyFrom(Matrix const& m) {
+
82  self().copyFrom(m.self);
+
83  return *this;
+
84  }
+
85 
+ +
95  self().referenceFrom(m.self);
+
96  return *this;
+
97  }
+
98 
+
100  void reset(size_t r, size_t c, Entry const& e) {
+
101  self()->rows_ = r;
+
102  self()->cols_ = c;
+
103  self()->entries_.clear();
+
104  self()->entries_.resize(r * c, e);
+
105  }
+
106 
+
108  bool valid() const {
+
109  return (rows() > 0 && cols() > 0);
+
110  }
+
111 
+
113  size_t rows() const {
+
114  return self->rows_;
+
115  }
+
116 
+
118  size_t cols() const {
+
119  return self->cols_;
+
120  }
+
121 
+
123  size_t size() const {
+
124  return rows() * cols();
+
125  }
+
126 
+
136  size_t rows(size_t r, Entry const& e) {
+
137  if (r != rows()) {
+
138  self()->entries_.resize(r * cols(), e);
+
139  self()->rows_ = r;
+
140  }
+
141  return rows();
+
142  }
+
143 
+
153  size_t cols(size_t c, Entry const& e) {
+
154  if (c != cols()) {
+
155  Self<Myself> const old(false);
+
156  old().copyFrom(self);
+
157  self()->entries_.resize(rows() * c);
+
158  self()->cols_ = c;
+
159  for (size_t i = 0, I = rows(); i < I; i++) {
+
160  size_t j, J1 = std::min(old->cols_, cols()), J2 = cols();
+
161  for (j = 0; j < J1; j++)
+
162  self()->entries_[self->index(i, j)] = old->entries_[old->index(i, j)];
+
163  for (j = J1; j < J2; j++)
+
164  self()->entries_[self->index(i, j)] = e;
+
165  }
+
166  }
+
167  return cols();
+
168  }
+
169 
+
180  size_t size(size_t r, size_t c, Entry const& e) {
+
181  cols(c, e);
+
182  rows(r, e);
+
183  return rows() * cols();
+
184  }
+
185 
+
187  Entry entry(size_t r, size_t c) const {
+
188  return self->entries_[self->index(r, c)];
+
189  }
+
190 
+
192  Entry entry(size_t r, size_t c, Entry const& e) {
+
193  self()->entries_[self->index(r, c)] = e;
+
194  return entry(r, c);
+
195  }
+
196 
+
207  void entries(ssize_t rFirst, ssize_t rLast,
+
208  ssize_t cFirst, ssize_t cLast,
+
209  Entry const& e) {
+
210  for (ssize_t r = rFirst; r <= rLast; r++) {
+
211  for (ssize_t c = cFirst; c <=cFirst; c++) {
+
212  entry(r, c, e);
+
213  }
+
214  }
+
215  }
+
216 
+
228  Matrix subMatrix(size_t rFirst, size_t rLast,
+
229  size_t cFirst, size_t cLast) const {
+
230  if (rFirst > rLast || cFirst > cLast) return Matrix();
+
231  if (rFirst == 0 || cFirst == 0) {
+
232  Matrix ret(*this);
+
233  ret.size(rLast + 1, cLast + 1, Entry(0));
+
234  return ret;
+
235  }
+
236  Matrix ret(rLast - rFirst + 1, cLast - cFirst + 1, entry(rFirst, cFirst));
+
237  for (size_t r = rFirst; r <= rLast; r++)
+
238  for (size_t c = cFirst; c <= cLast; c++)
+
239  ret.entry(r - rFirst, c - cFirst, entry(r, c));
+
240  return ret;
+
241  }
+
242 
+
244  Matrix row(size_t r) const {
+
245  return subMatrix(r, r, 0, cols() - 1);
+
246  }
+
247 
+
249  Matrix col(size_t c) const {
+
250  return subMatrix(0, rows() - 1, c, c);
+
251  }
+
252 
+
254  Matrix positive() const {
+
255  return *this;
+
256  }
+
257 
+
259  Matrix negative() const {
+
260  Matrix ret(*this);
+
261  for (size_t r = 0, R = rows(); r < R; r++)
+
262  for (size_t c = 0, C = cols(); c < C; c++)
+
263  ret.entry(r, c, -ret.entry(r, c));
+
264  return ret;
+
265  }
+
266 
+
271  Matrix add(Matrix const& m) const {
+
272  if (rows() != m.rows() || cols() != m.cols()) return Matrix();
+
273  Matrix ret(*this);
+
274  for (size_t r = 0, R = rows(); r < R; r++)
+
275  for (size_t c = 0, C = cols(); c < C; c++)
+
276  ret.entry(r, c, ret.entry(r, c) + m.entry(r, c));
+
277  return ret;
+
278  }
+
279 
+
284  Matrix sub(Matrix const& m) const {
+
285  if (rows() != m.rows() || cols() != m.cols()) return Matrix();
+
286  Matrix ret(*this);
+
287  for (size_t r = 0, R = rows(); r < R; r++)
+
288  for (size_t c = 0, C = cols(); c < C; c++)
+
289  ret.entry(r, c, ret.entry(r, c) - m.entry(r, c));
+
290  return ret;
+
291  }
+
292 
+
297  Matrix mul(Matrix const& m) const {
+
298  if (cols() != m.rows()) return Matrix();
+
299  Matrix ret(rows(), m.cols(), Entry(0));
+
300  for (size_t r = 0, R = rows(); r < R; r++)
+
301  for (size_t c = 0, C = m.cols(); c < C; c++)
+
302  for (size_t k = 0, K = cols(); k < K; k++)
+
303  ret.entry(r, c, ret.entry(r, c) + entry(r, k) * m.entry(k, c));
+
304  return ret;
+
305  }
+
306 
+
308  Matrix mul(Entry const& s) const {
+
309  Matrix ret(*this);
+
310  for (size_t r = 0, R = rows(); r < R; r++)
+
311  for (size_t c = 0, C = cols(); c < C; c++)
+
312  ret.entry(r, c, ret.entry(r, c) * s);
+
313  return ret;
+
314  }
+
315 
+
317  Matrix div(Entry const& s) const {
+
318  Matrix ret(*this);
+
319  for (size_t r = 0, R = rows(); r < R; r++)
+
320  for (size_t c = 0, C = cols(); c < C; c++)
+
321  ret.entry(r, c, ret.entry(r, c) / s);
+
322  return ret;
+
323  }
+
324 
+
326  Matrix identity() const {
+
327  Matrix ret(*this);
+
328  ret.identitied();
+
329  return ret;
+
330  }
+
331 
+ +
338  for (size_t r = 0, R = rows(); r < R; r++)
+
339  for (size_t c = 0, C = cols(); c < C; c++)
+
340  entry(r, c, (r == c ? Entry(1) : Entry(0)));
+
341  return *this;
+
342  }
+
343 
+
349  Matrix inverse() const {
+
350  if (rows() != cols() || rows() == 0) return Matrix<Entry>();
+
351  Matrix tmp(rows(), cols() * 2, Entry(0));
+
352  for (size_t r = 0, R = rows(); r < R; r++) {
+
353  for (size_t c = 0, C = cols(); c < C; c++) {
+
354  tmp.entry(r, c, entry(r, c));
+
355  tmp.entry(r, c + cols(), (r == c ? Entry(1) : Entry(0)));
+
356  }
+
357  }
+
358  tmp.triangulared();
+
359  for (ssize_t r = rows() - 1; r >= 0; r--) {
+
360  if (tmp(r, r) == Entry(0)) return Matrix<Entry>();
+
361  for (ssize_t r2 = r - 1; r2 >= 0; r2--) {
+
362  Entry rat(-tmp.entry(r2, r) / tmp.entry(r, r));
+
363  for (size_t c = r, C = tmp.cols(); c < C; c++) {
+
364  tmp.entry(r2, c, tmp.entry(r2, c) + rat * tmp(r, c));
+
365  }
+
366  }
+
367  Entry rat(tmp.entry(r, r));
+
368  for (size_t c = cols(), C = tmp.cols(); c < C; c++) {
+
369  tmp.entry(r, c - cols(), tmp.entry(r, c) / rat);
+
370  }
+
371  }
+
372  tmp.size(cols(), rows(), Entry(0));
+
373  return tmp;
+
374  }
+
375 
+ +
378  copyFrom(inverse());
+
379  return *this;
+
380  }
+
381 
+
383  Matrix transpose () const {
+
384  Matrix ret(cols(), rows(), Entry(0));
+
385  for (size_t r = 0, R = cols(); r < R; r++)
+
386  for (size_t c = 0, C = rows(); c < C; c++)
+
387  ret.entry(r, c, entry(c, r));
+
388  return ret;
+
389  }
+
390 
+ +
393  copyFrom(transpose());
+
394  return *this;
+
395  }
+
396 
+
398  Matrix triangular() const {
+
399  Matrix<Entry> ret(*this);
+
400  ret.triangulared();
+
401  return ret;
+
402  }
+
403 
+ +
406  for (size_t r = 0, c = 0, R = rows(), C = cols(); r < R && c < C; r++) {
+
407  ssize_t maxR;
+
408  for ( ; c < C; c++) {
+
409  maxR = -1;
+
410  for (size_t r2 = r; r2 < R; r2++)
+
411  if (maxR == -1 || tAbs(entry(r2, c)) > tAbs(entry(maxR, c)))
+
412  maxR = r2;
+
413  if (entry(maxR, c) != Entry(0)) break;
+
414  }
+
415  if (c >= C) break;
+
416  if (maxR != (ssize_t)r) {
+
417  for (size_t c2 = c; c2 < C; c2++)
+
418  std::swap(self()->entries_[self->index( r, c2)],
+
419  self()->entries_[self->index(maxR, c2)]);
+
420  }
+
421  for (size_t r2 = r + 1; r2 < R; r2++) {
+
422  Entry rati = -entry(r2, c) / entry(r, c);
+
423  entry(r2, c, Entry(0));
+
424  for (size_t c2 = c + 1; c2 < C; c2++)
+
425  entry(r2, c2, entry(r2, c2) + entry(r, c2) * rati);
+
426  }
+
427  }
+
428  return *this;
+
429  }
+
430 
+
432  Matrix& operator=(Matrix const& m) {
+
433  return copyFrom(m);
+
434  }
+
435 
+
437  Entry operator()(size_t r, size_t c) const {
+
438  return entry(r, c);
+
439  }
+
440 
+
442  Entry operator()(size_t r, size_t c, Entry const& e) {
+
443  return entry(r, c, e);
+
444  }
+
445 
+
447  Matrix operator+() const {
+
448  return positive();
+
449  }
+
450 
+
452  Matrix operator-() const {
+
453  return negative();
+
454  }
+
455 
+
457  Matrix operator+(Matrix const& m) const {
+
458  return add(m);
+
459  }
+
460 
+
462  Matrix operator-(Matrix const& m) const {
+
463  return sub(m);
+
464  }
+
465 
+
467  Matrix operator*(Matrix const& m) const {
+
468  return mul(m);
+
469  }
+
470 
+
472  Matrix operator*(Entry const& s) const {
+
473  return mul(s);
+
474  }
+
475 
+
477  Matrix operator/(Entry const& s) const {
+
478  return div(s);
+
479  }
+
480 };
+
481 
+
482 }
+
483 
+
484 #endif // math_Matrix_H__
+
+
+ + + + + -- cgit v1.2.3