fmatvec  0.0.0
fixed_general_matrix.h
1/* Copyright (C) 2003-2005 Martin Förg
2
3 * This library is free software; you can redistribute it and/or
4 * modify it under the terms of the GNU Lesser General Public
5 * License as published by the Free Software Foundation; either
6 * version 2.1 of the License, or (at your option) any later version.
7 *
8 * This library is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 * Lesser General Public License for more details.
12 *
13 * You should have received a copy of the GNU Lesser General Public
14 * License along with this library; if not, write to the Free Software
15 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
16 *
17 * Contact:
18 * martin.o.foerg@googlemail.com
19 *
20 */
21
22#ifndef fixed_general_matrix_h
23#define fixed_general_matrix_h
24
25#include "types.h"
26#include "range.h"
27#include <vector>
28#include <cstdlib>
29#include <stdexcept>
30
31namespace fmatvec {
32
41 template <int M, int N, class AT> class Matrix<General,Fixed<M>,Fixed<N>,AT> {
42
43 public:
44 static constexpr bool isVector {false};
45
46 using iterator = AT *;
47 using const_iterator = const AT *;
48 using value_type = AT;
49 using shape_type = General;
50
52
53 protected:
54
55 AT ele[M][N];
56
57 template <class Type, class Row, class Col> inline Matrix<General,Fixed<M>,Fixed<N>,AT>& copy(const Matrix<Type,Row,Col,AT> &A);
58 template<class Row> inline Matrix<General,Fixed<M>,Fixed<N>,AT>& copy(const Matrix<Symmetric,Row,Row,AT> &A);
59
61
62 public:
63
64// Works with -std=gnu++0x only
65// template<class Ini=All<AT>>
66// Matrix(Ini ini=All<AT>()) {
67// init(ini);
68// }
69// template<class Ini=All<AT>>
70// Matrix(int m_, int n_, Ini ini=All<AT>()) {
71// init(ini);
72// }
73
74 explicit Matrix(Noinit) { }
75 explicit Matrix(Init ini=INIT, const AT &a=AT()) { init(a); }
76 explicit Matrix(Eye ini, const AT &a=1) { init(ini,a); }
77 explicit Matrix(int m, int n, Noinit) { FMATVEC_ASSERT(m==M && n==N, AT); }
78 explicit Matrix(int m, int n, Init ini=INIT, const AT &a=AT()) { FMATVEC_ASSERT(m==M && n==N, AT); init(a); }
79 explicit Matrix(int m, int n, Eye ini, const AT &a=1) { FMATVEC_ASSERT(m==M && n==N, AT); init(ini,a); }
80
86 Matrix(const Matrix<General,Fixed<M>,Fixed<N>,AT> &A) = default;
87
93 template<class Row, class Col>
95 FMATVEC_ASSERT(A.rows() == M, AT);
96 FMATVEC_ASSERT(A.cols() == N, AT);
97 copy(A);
98 }
99
105 template<class Type, class Row, class Col>
106 explicit Matrix(const Matrix<Type,Row,Col,AT> &A) {
107 FMATVEC_ASSERT(A.rows() == M, AT);
108 FMATVEC_ASSERT(A.cols() == N, AT);
109 copy(A);
110 }
111
124 Matrix(const std::string &strs);
125 Matrix(const char *strs);
126
134
141 template <class Type, class Row, class Col>
143 FMATVEC_ASSERT(A.rows() == M, AT);
144 FMATVEC_ASSERT(A.cols() == N, AT);
145 return copy(A);
146 }
147
154 template<class Type, class Row, class Col>
155 inline Matrix<General,Fixed<M>,Fixed<N>,AT>& operator<<=(const Matrix<Type,Row,Col,AT> &A) { return operator=(A); }
156
157 template <class AT2>
158 operator Matrix<General,Fixed<M>,Fixed<N>,AT2>() const {
159 Matrix<General,Fixed<M>,Fixed<N>,AT2> ret;
160 for(size_t r=0; r<M; ++r)
161 for(size_t c=0; c<N; ++c)
162 ret(r,c) = (*this)(r,c);
163 return ret;
164 }
165
166 iterator begin() { return &ele[0][0]; }
167 iterator end() { return &ele[M-1][N]; }
168 const_iterator begin() const { return &ele[0][0]; }
169 const_iterator end() const { return &ele[M-1][N]; }
170
180 AT& operator()(int i, int j) {
181 FMATVEC_ASSERT(i>=0, AT);
182 FMATVEC_ASSERT(j>=0, AT);
183 FMATVEC_ASSERT(i<M, AT);
184 FMATVEC_ASSERT(j<N, AT);
185
186 return e(i,j);
187 }
188
193 const AT& operator()(int i, int j) const {
194 FMATVEC_ASSERT(i>=0, AT);
195 FMATVEC_ASSERT(j>=0, AT);
196 FMATVEC_ASSERT(i<M, AT);
197 FMATVEC_ASSERT(j<N, AT);
198
199 return e(i,j);
200 }
201
202 AT& e(int i, int j) {
203 return ele[i][j];
204 }
205
210 const AT& e(int i, int j) const {
211 return ele[i][j];
212 }
213
219 AT* operator()() {return &(ele[0][0]);}
220
225 const AT* operator()() const {return &(ele[0][0]);}
226
231 constexpr int rows() const {return M;}
232
237 constexpr int cols() const {return N;}
238
243 int ldim() const {return N;}
244
247 void resize(int m, int n) {
248 if(m!=M || n!=N)
249 throw std::runtime_error("A fixed matrix cannot be resized.");
250 }
251
258 CBLAS_TRANSPOSE blasTrans() const {
259 return CblasNoTrans;
260 }
261
269 CBLAS_ORDER blasOrder() const {
270 return CblasRowMajor;
271 }
272
277 inline const Matrix<General,Var,Var,AT> operator()(const Range<Var,Var> &I, const Range<Var,Var> &J) const;
278
279 template <int M1, int M2, int N1, int N2>
280 inline const Matrix<General,Fixed<M2-M1+1>,Fixed<N2-N1+1>,AT> operator()(const Range<Fixed<M1>,Fixed<M2>> &I, const Range<Fixed<N1>,Fixed<N2>> &J) const;
281 template <int M1, int M2>
282 inline const Matrix<General,Fixed<M2-M1+1>,Var,AT> operator()(const Range<Fixed<M1>,Fixed<M2>> &I, const Range<Var,Var > &J) const;
283
284 template <int N1, int N2>
285 inline const Matrix<General,Var,Fixed<N2-N1+1>,AT> operator()(const Range<Var,Var> &I, const Range<Fixed<N1>,Fixed<N2>> &J) const;
286
287 inline const RowVector<Fixed<N>,AT> row(int i) const;
288 inline const Vector<Fixed<M>,AT> col(int j) const;
289
297 inline Matrix<General,Fixed<M>,Fixed<N>,AT>& init(const AT &val=AT());
298 inline Matrix<General,Fixed<M>,Fixed<N>,AT>& init(Init, const AT &a=AT()) { return init(a); }
299 inline Matrix<General,Fixed<M>,Fixed<N>,AT>& init(Eye, const AT &val=1);
300 inline Matrix<General,Fixed<M>,Fixed<N>,AT>& init(Noinit, const AT &a=AT()) { return *this; }
301
306 explicit inline operator std::vector<std::vector<AT>>() const;
307
313 explicit Matrix(const std::vector<std::vector<AT>> &m);
314
315// /*! \brief Cast to AT.
316// *
317// * \return The AT representation of the matrix
318// * */
319// explicit operator AT() const {
320// FMATVEC_ASSERT(M==1, AT);
321// FMATVEC_ASSERT(N==1, AT);
322// return ele[0][0];
323// }
324//
325// /*! \brief AT Constructor.
326// * Constructs and initializes a matrix with a AT object.
327// * \param v The AT the matrix will be initialized with.
328// * */
329// explicit Matrix(const AT &x) {
330// FMATVEC_ASSERT(M==1, AT);
331// FMATVEC_ASSERT(N==1, AT);
332// ele[0][0] = x;
333// }
334
335 inline const Matrix<General,Fixed<N>,Fixed<M>,AT> T() const;
336
340 template<class Row> inline void set(int j, const Vector<Row,AT> &x);
341
345 template<class Col> inline void set(int i, const RowVector<Col,AT> &x);
346
353 template<class Type, class Row, class Col> inline void set(const Range<Var,Var> &I, const Range<Var,Var> &J, const Matrix<Type,Row,Col,AT> &A);
354
358 template<class Row> inline void add(int j, const Vector<Row,AT> &x);
359
363 template<class Col> inline void add(int i, const RowVector<Col,AT> &x);
364
365 template<class Type, class Row, class Col> inline void add(const Range<Var,Var> &I, const Range<Var,Var> &J, const Matrix<Type,Row,Col,AT> &A);
366 };
367
368 template <int M, int N, class AT>
369 Matrix<General,Fixed<M>,Fixed<N>,AT>::Matrix(const std::string &strs) {
370 std::istringstream iss(strs);
371 iss>>*this;
372
373 // check end of stream
374 iss>>std::ws;
375 if(!iss.eof())
376 throw std::runtime_error("Input not fully read.");
377 }
378 template <int M, int N, class AT> Matrix<General,Fixed<M>,Fixed<N>,AT>::Matrix(const char *strs) :
379 Matrix<General,Fixed<M>,Fixed<N>,AT>::Matrix(std::string(strs)) {}
380
381 template <int M, int N, class AT>
383 for(int i=0; i<M; i++)
384 for(int j=0; j<N; j++)
385 e(i,j) = val;
386 return *this;
387 }
388
389 template <int M, int N, class AT>
390 inline Matrix<General,Fixed<M>,Fixed<N>,AT>& Matrix<General,Fixed<M>,Fixed<N>,AT>::init(Eye, const AT &val) {
391 for(int i=0; i<M; i++)
392 for(int j=0; j<N; j++)
393 e(i,j) = (i==j) ? val : 0;
394 return *this;
395 }
396
397 template <int M, int N, class AT>
398 inline const Matrix<General,Var,Var,AT> Matrix<General,Fixed<M>,Fixed<N>,AT>::operator()(const Range<Var,Var> &I, const Range<Var,Var> &J) const {
399 FMATVEC_ASSERT(I.end()<M, AT);
400 FMATVEC_ASSERT(J.end()<N, AT);
401 Matrix<General,Var,Var,AT> A(I.size(),J.size(),NONINIT);
402
403 for(int i=0; i<A.rows(); i++)
404 for(int j=0; j<A.cols(); j++)
405 A.e(i,j) = e(I.start()+i,J.start()+j);
406
407 return A;
408 }
409
410 template <int M, int N, class AT> template <int M1, int M2, int N1, int N2>
411 inline const Matrix<General,Fixed<M2-M1+1>,Fixed<N2-N1+1>,AT> Matrix<General,Fixed<M>,Fixed<N>,AT>::operator()(const Range<Fixed<M1>,Fixed<M2>> &I, const Range<Fixed<N1>,Fixed<N2>> &J) const {
412 FMATVEC_ASSERT(M2<M, AT);
413 FMATVEC_ASSERT(N2<N, AT);
414 Matrix<General,Fixed<M2-M1+1>,Fixed<N2-N1+1>,AT> A(NONINIT);
415
416 for(int i=0; i<A.rows(); i++)
417 for(int j=0; j<A.cols(); j++)
418 A.e(i,j) = e(M1+i,J.start()+j);
419
420 return A;
421 }
422
423 template <int M, int N, class AT> template <int M1, int M2>
424 inline const Matrix<General,Fixed<M2-M1+1>,Var,AT> Matrix<General,Fixed<M>,Fixed<N>,AT>::operator()(const Range<Fixed<M1>,Fixed<M2>> &I, const Range<Var,Var> &J) const {
425 FMATVEC_ASSERT(M2<M, AT);
426 FMATVEC_ASSERT(J.end()<N, AT);
427 Matrix<General,Fixed<M2-M1+1>,Var,AT> A(J.size(),NONINIT);
428
429 for(int i=0; i<A.rows(); i++)
430 for(int j=0; j<A.cols(); j++)
431 A.e(i,j) = e(I.start()+i,J.start()+j);
432
433 return A;
434 }
435
436 template <int M, int N, class AT> template <int N1, int N2>
437 inline const Matrix<General,Var,Fixed<N2-N1+1>,AT> Matrix<General,Fixed<M>,Fixed<N>,AT>::operator()(const Range<Var,Var> &I, const Range<Fixed<N1>,Fixed<N2>> &J) const {
438 FMATVEC_ASSERT(I.end()<M, AT);
439 FMATVEC_ASSERT(N2<N, AT);
440 Matrix<General,Var,Fixed<N2-N1+1>,AT> A(I.size(),NONINIT);
441
442 for(int i=0; i<A.rows(); i++)
443 for(int j=0; j<A.cols(); j++)
444 A.e(i,j) = e(I.start()+i,J.start()+j);
445
446 return A;
447 }
448
449 template <int M, int N, class AT>
450 inline const RowVector<Fixed<N>,AT> Matrix<General,Fixed<M>,Fixed<N>,AT>::row(int i) const {
451
452 FMATVEC_ASSERT(i>=0, AT);
453 FMATVEC_ASSERT(i<M, AT);
454
455 RowVector<Fixed<N>,AT> x(NONINIT);
456
457 for(int j=0; j<N; j++)
458 x.e(j) = e(i,j);
459
460 return x;
461 }
462
463 template <int M, int N, class AT>
464 inline const Vector<Fixed<M>,AT> Matrix<General,Fixed<M>,Fixed<N>,AT>::col(int j) const {
465
466 FMATVEC_ASSERT(j>=0, AT);
467 FMATVEC_ASSERT(j<N, AT);
468
469 Vector<Fixed<M>,AT> x(NONINIT);
470
471 for(int i=0; i<M; i++)
472 x.e(i) = e(i,j);
473
474 return x;
475 }
476
477 template <int M, int N, class AT>
478 inline const Matrix<General,Fixed<N>,Fixed<M>,AT> Matrix<General,Fixed<M>,Fixed<N>,AT>::T() const {
479 Matrix<General,Fixed<N>,Fixed<M>,AT> A(NONINIT);
480 for(int i=0; i<N; i++)
481 for(int j=0; j<M; j++)
482 A.e(i,j) = e(j,i);
483 return A;
484 }
485
486 template <int M, int N, class AT> template <class Row>
487 inline void Matrix<General,Fixed<M>,Fixed<N>,AT>::set(int j, const Vector<Row,AT> &x) {
488 FMATVEC_ASSERT(j<cols(), AT);
489 FMATVEC_ASSERT(rows()==x.size(), AT);
490 for(int i=0; i<rows(); i++)
491 e(i,j) = x.e(i);
492 }
493
494 template <int M, int N, class AT> template <class Col>
495 inline void Matrix<General,Fixed<M>,Fixed<N>,AT>::set(int i, const RowVector<Col,AT> &x) {
496 FMATVEC_ASSERT(i<rows(), AT);
497 FMATVEC_ASSERT(cols()==x.size(), AT);
498 for(int j=0; j<cols(); j++)
499 e(i,j) = x.e(j);
500 }
501
502 template <int M, int N, class AT> template<class Type, class Row, class Col>
503 inline void Matrix<General,Fixed<M>,Fixed<N>,AT>::set(const Range<Var,Var> &I, const Range<Var,Var> &J, const Matrix<Type,Row,Col,AT> &A) {
504
505 FMATVEC_ASSERT(I.end()<rows(), AT);
506 FMATVEC_ASSERT(J.end()<cols(), AT);
507 FMATVEC_ASSERT(I.size()==A.rows(), AT);
508 FMATVEC_ASSERT(J.size()==A.cols(), AT);
509
510 for(int i=I.start(), ii=0; i<=I.end(); i++, ii++)
511 for(int j=J.start(), jj=0; j<=J.end(); j++, jj++)
512 e(i,j) = A.e(ii,jj);
513 }
514
515 template <int M, int N, class AT> template <class Row>
516 inline void Matrix<General,Fixed<M>,Fixed<N>,AT>::add(int j, const Vector<Row,AT> &x) {
517 FMATVEC_ASSERT(j<cols(), AT);
518 FMATVEC_ASSERT(rows()==x.size(), AT);
519 for(int i=0; i<rows(); i++)
520 e(i,j) += x.e(i);
521 }
522
523 template <int M, int N, class AT> template <class Col>
524 inline void Matrix<General,Fixed<M>,Fixed<N>,AT>::add(int i, const RowVector<Col,AT> &x) {
525 FMATVEC_ASSERT(i<rows(), AT);
526 FMATVEC_ASSERT(cols()==x.size(), AT);
527 for(int j=0; j<cols(); j++)
528 e(i,j) += x.e(j);
529 }
530
531 template <int M, int N, class AT> template<class Type, class Row, class Col>
532 inline void Matrix<General,Fixed<M>,Fixed<N>,AT>::add(const Range<Var,Var> &I, const Range<Var,Var> &J, const Matrix<Type,Row,Col,AT> &A) {
533
534 FMATVEC_ASSERT(I.end()<rows(), AT);
535 FMATVEC_ASSERT(J.end()<cols(), AT);
536 FMATVEC_ASSERT(I.size()==A.rows(), AT);
537 FMATVEC_ASSERT(J.size()==A.cols(), AT);
538
539 for(int i=I.start(), ii=0; i<=I.end(); i++, ii++)
540 for(int j=J.start(), jj=0; j<=J.end(); j++, jj++)
541 e(i,j) += A.e(ii,jj);
542 }
543
544 template <int M, int N, class AT>
545 inline Matrix<General,Fixed<M>,Fixed<N>,AT>::operator std::vector<std::vector<AT>>() const {
546 std::vector<std::vector<AT>> ret(rows(),std::vector<AT>(cols()));
547 for(int r=0; r<rows(); r++) {
548 for(int c=0; c<cols(); c++)
549 ret[r][c]=e(r,c);
550 }
551 return ret;
552 }
553
554 template <int M, int N, class AT>
555 inline Matrix<General,Fixed<M>,Fixed<N>,AT>::Matrix(const std::vector<std::vector<AT>> &m) {
556 if(m.size() != M)
557 throw std::runtime_error("The input has "+std::to_string(m.size())+" rows but "+std::to_string(M)+" rows are required.");
558 if((m.empty()?0:m[0].size()) != N)
559 throw std::runtime_error("The input has "+std::to_string((m.empty()?0:m[0].size()))+" columne but "+std::to_string(N)+" columns are required.");
560 for(int r=0; r<rows(); r++) {
561 if(static_cast<int>(m[r].size())!=cols())
562 throw std::runtime_error("The rows of the input have different length.");
563 for(int c=0; c<cols(); c++)
564 e(r,c)=m[r][c];
565 }
566 }
567
569
570 template <int M, int N, class AT> template <class Type, class Row, class Col>
572 for(int i=0; i<M; i++)
573 for(int j=0; j<N; j++)
574 e(i,j) = A.e(i,j);
575 return *this;
576 }
577
578 template<int M, int N, class AT> template<class Row>
579 inline Matrix<General,Fixed<M>,Fixed<N>,AT>& Matrix<General,Fixed<M>,Fixed<N>,AT>::copy(const Matrix<Symmetric,Row,Row,AT> &A) {
580 for(int i=0; i<A.size(); i++) {
581 e(i,i) = A.ej(i,i);
582 for(int j=i+1; j<A.size(); j++)
583 e(i,j) = e(j,i) = A.ej(i,j);
584 }
585 return *this;
586 }
587
589
597 template<int M, class AT>
598 class Matrix<Rotation,Fixed<M>,Fixed<M>,AT> : public Matrix<General,Fixed<M>,Fixed<M>,AT> {
599 public:
600 using value_type = AT;
601 using shape_type = Rotation;
602 // Constructors are not inherited. Hence we must redefine all ctors here.
603
604 Matrix(Noinit ini) { }
605 Matrix(Init ini=INIT, const AT &a=0) { this->init(a); }
606 Matrix(Eye ini, const AT &a=1) { this->init(ini,a); }
607
608 Matrix(int m, int n) { }
609 Matrix(int m, int n, Noinit ini) { }
610 Matrix(int m, int n, Init ini, const AT &a=0) { this->init(a); }
611 Matrix(int m, int n, Eye ini, const AT &a=1) { this->init(ini,a); }
612
613 Matrix(const Matrix<Rotation,Fixed<M>,Fixed<M>,AT> &A) = default;
614
615 explicit Matrix(const Matrix<General,Fixed<M>,Fixed<M>,AT> &A) : Matrix<General,Fixed<M>,Fixed<M>,AT>(A) { }
616
617 template<class Row>
619
620 template<class Type, class Row, class Col>
621 explicit Matrix(const Matrix<Type,Row,Col,AT> &A) : Matrix<General,Fixed<M>,Fixed<M>,AT>(A) { }
622
623 explicit Matrix(const std::vector<std::vector<AT>> &m) : Matrix<General,Fixed<M>,Fixed<M>,AT>(m) { }
624
625 inline const Matrix<Rotation,Fixed<M>,Fixed<M>,AT> T() const;
626
627 using Matrix<General,Fixed<M>,Fixed<M>,AT>::e;
628
629 // TODO: we should add some overloaded member functions here which capitalize the special
630 // properties of rotation matrices, link "RotMat inv() { return trans(*this); }"
631 };
632
633 template <int M, class AT>
635 Matrix<Rotation,Fixed<M>,Fixed<M>,AT> A(NONINIT);
636 for(int i=0; i<M; i++)
637 for(int j=0; j<M; j++)
638 A.e(i,j) = e(j,i);
639 return A;
640 }
641
642}
643
644#endif
Definition: types.h:94
Definition: types.h:108
Shape class for general matrices.
Definition: types.h:116
Definition: types.h:93
Matrix(const Matrix< General, Row, Col, AT > &A)
Copy Constructor.
Definition: fixed_general_matrix.h:94
Matrix(const Matrix< Type, Row, Col, AT > &A)
Copy Constructor.
Definition: fixed_general_matrix.h:106
Matrix(const Matrix< General, Fixed< M >, Fixed< N >, AT > &A)=default
Copy Constructor.
constexpr int rows() const
Number of rows.
Definition: fixed_general_matrix.h:231
Matrix< General, Fixed< M >, Fixed< N >, AT > & operator=(const Matrix< General, Fixed< M >, Fixed< N >, AT > &A)=default
Assignment operator.
CBLAS_TRANSPOSE blasTrans() const
Transposed status.
Definition: fixed_general_matrix.h:258
void resize(int m, int n)
Definition: fixed_general_matrix.h:247
constexpr int cols() const
Number of columns.
Definition: fixed_general_matrix.h:237
AT & operator()(int i, int j)
Element operator.
Definition: fixed_general_matrix.h:180
int ldim() const
Leading dimension.
Definition: fixed_general_matrix.h:243
CBLAS_ORDER blasOrder() const
Storage convention.
Definition: fixed_general_matrix.h:269
const AT * operator()() const
Pointer operator.
Definition: fixed_general_matrix.h:225
const AT & operator()(int i, int j) const
Element operator.
Definition: fixed_general_matrix.h:193
AT * operator()()
Pointer operator.
Definition: fixed_general_matrix.h:219
const AT & e(int i, int j) const
Element operator.
Definition: fixed_general_matrix.h:210
This is a matrix class for general matrices.
Definition: var_general_matrix.h:41
constexpr int cols() const
Number of columns.
Definition: var_general_matrix.h:303
constexpr int rows() const
Number of rows.
Definition: var_general_matrix.h:297
This is the basic matrix class for arbitrary matrices.
Definition: matrix.h:52
int rows() const
Number of rows.
int cols() const
Number of columns.
AT & operator()(int i, int j)
Standard constructor.
Definition: matrix.h:84
Definition: types.h:92
This is an index class for creating submatrices.
Definition: range.h:44
int end() const
Last element.
Definition: range.h:91
int size() const
Size.
Definition: range.h:97
int start() const
First element.
Definition: range.h:85
This is an index class for creating submatrices.
Definition: range.h:35
Shape class for rotation matrices.
Definition: types.h:140
Definition: matrix.h:170
Definition: types.h:105
Definition: matrix.h:167
Namespace fmatvec.
Definition: _memory.cc:28