00001
00002
00003
00004
00005
00006
00007
00008
00013 #ifndef external_matrix_h
00014 #define external_matrix_h
00015
00016 #include <cml/core/external_2D.h>
00017 #include <cml/matrix/matrix_expr.h>
00018 #include <cml/matrix/class_ops.h>
00019 #include <cml/matrix/matrix_unroller.h>
00020 #include <cml/matrix/dynamic.h>
00021
00022 namespace cml {
00023
00025 template<typename Element, int Rows, int Cols,
00026 typename BasisOrient, typename Layout>
00027 class matrix<Element,external<Rows,Cols>,BasisOrient,Layout>
00028 : public external_2D<Element,Rows,Cols,Layout>
00029 {
00030 public:
00031
00032
00033 typedef external<Rows,Cols> generator_type;
00034
00035
00036 typedef external_2D<Element,Rows,Cols,Layout> array_type;
00037
00038
00039 typedef matrix<Element,generator_type,BasisOrient,Layout> matrix_type;
00040
00041
00042 typedef matrix_type expr_type;
00043
00044
00045 typedef matrix<Element,fixed<Rows,Cols>,BasisOrient,Layout> temporary_type;
00046
00047
00048
00049
00050
00051 typedef typename array_type::value_type value_type;
00052 typedef typename array_type::reference reference;
00053 typedef typename array_type::const_reference const_reference;
00054
00055 typedef matrix_type& expr_reference;
00056 typedef const matrix_type& expr_const_reference;
00057
00058
00059 typedef BasisOrient basis_orient;
00060
00061
00062 typedef typename array_type::layout layout;
00063
00064
00065 typedef typename array_type::memory_tag memory_tag;
00066
00067
00068 typedef typename array_type::size_tag size_tag;
00069
00070
00071 typedef typename array_type::resizing_tag resizing_tag;
00072
00073
00074 typedef cml::et::matrix_result_tag result_tag;
00075
00076
00077 typedef cml::et::assignable_tag assignable_tag;
00078
00079
00080 typedef matrix<
00081 Element,
00082 typename array_type::transposed_type::generator_type,
00083 BasisOrient,
00084 Layout
00085 > transposed_type;
00086
00087
00088 typedef vector<
00089 Element,
00090 typename array_type::row_array_type::generator_type
00091 > row_vector_type;
00092
00093 typedef vector<
00094 Element,
00095 typename array_type::col_array_type::generator_type
00096 > col_vector_type;
00097
00098
00099 public:
00100
00102 matrix_type& zero() {
00103 typedef cml::et::OpAssign<Element,Element> OpT;
00104 cml::et::UnrollAssignment<OpT>(*this,Element(0));
00105 return *this;
00106 }
00107
00113 matrix_type& identity() {
00114 for(size_t i = 0; i < this->rows(); ++ i) {
00115 for(size_t j = 0; j < this->cols(); ++ j) {
00116 (*this)(i,j) = value_type((i == j)?1:0);
00117 }
00118 }
00119 return *this;
00120 }
00121
00127 matrix_type& transpose() {
00128
00129 *this = transpose(*this);
00130 return *this;
00131 }
00132
00138 matrix_type& inverse() {
00139
00140 *this = cml::inverse(*this);
00141 return *this;
00142 }
00143
00144
00145
00146 #if 0
00147
00148 template<typename E, class AT, typename L>
00149 void minimize(const matrix<E,AT,basis_orient,L>& v) {
00150
00151 for (size_t i = 0; i < this->rows(); ++i) {
00152 for (size_t j = 0; j < this->cols(); ++j) {
00153 (*this)(i,j) = std::min((*this)(i,j),v(i,j));
00154 }
00155 }
00156 }
00157
00159 template<typename E, class AT, typename L>
00160 void maximize(const matrix<E,AT,basis_orient,L>& v) {
00161
00162 for (size_t i = 0; i < this->rows(); ++i) {
00163 for (size_t j = 0; j < this->cols(); ++j) {
00164 (*this)(i,j) = std::max((*this)(i,j),v(i,j));
00165 }
00166 }
00167 }
00168 #endif
00169
00170
00171 void random(ELEMENT_ARG_TYPE min, ELEMENT_ARG_TYPE max) {
00172 for(size_t i = 0; i < this->rows(); ++i) {
00173 for(size_t j = 0; j < this->cols(); ++j) {
00174 (*this)(i,j) = random_real(min,max);
00175 }
00176 }
00177 }
00178
00179
00180 public:
00181
00192 explicit matrix(value_type ptr[Rows][Cols]) : array_type(ptr) {}
00193
00204 explicit matrix(value_type* ptr) : array_type(ptr) {}
00205
00206
00207 public:
00208
00210 matrix_size size() const {
00211 return matrix_size(this->rows(),this->cols());
00212 }
00213
00215 value_type basis_element(size_t i, size_t j) const {
00216 return basis_element(i,j,basis_orient());
00217 }
00218
00220 void set_basis_element(size_t i, size_t j, ELEMENT_ARG_TYPE s) {
00221 set_basis_element(i,j,s,basis_orient());
00222 }
00223
00225 void set_row(size_t i, const row_vector_type& row) {
00226 for(size_t j = 0; j < this->cols(); ++ j) (*this)(i,j) = row[j];
00227 }
00228
00230 void set_col(size_t j, const col_vector_type& col) {
00231 for(size_t i = 0; i < this->rows(); ++ i) (*this)(i,j) = col[i];
00232 }
00233
00234
00235 public:
00236
00237 CML_ASSIGN_MAT_22
00238 CML_ASSIGN_MAT_33
00239 CML_ASSIGN_MAT_44
00240
00241
00242
00243
00244 CML_MAT_ASSIGN_FROM_MATTYPE
00245
00246 CML_MAT_ASSIGN_FROM_MAT(=, et::OpAssign)
00247 CML_MAT_ASSIGN_FROM_MAT(+=, et::OpAddAssign)
00248 CML_MAT_ASSIGN_FROM_MAT(-=, et::OpSubAssign)
00249
00250 CML_MAT_ASSIGN_FROM_MATXPR(=, et::OpAssign)
00251 CML_MAT_ASSIGN_FROM_MATXPR(+=, et::OpAddAssign)
00252 CML_MAT_ASSIGN_FROM_MATXPR(-=, et::OpSubAssign)
00253
00254 CML_MAT_ASSIGN_FROM_SCALAR(*=, et::OpMulAssign)
00255 CML_MAT_ASSIGN_FROM_SCALAR(/=, et::OpDivAssign)
00256
00257 CML_ACCUMULATED_MATRIX_MULT(const matrix_type&)
00258
00259 template<typename E, class AT, typename BO, typename L>
00260 CML_ACCUMULATED_MATRIX_MULT(const TEMPLATED_MATRIX_MACRO&)
00261
00262 template<class XprT>
00263 CML_ACCUMULATED_MATRIX_MULT(MATXPR_ARG_TYPE)
00264
00265
00266 protected:
00267
00268 value_type basis_element(size_t i, size_t j, row_basis) const {
00269 return (*this)(i,j);
00270 }
00271
00272 value_type basis_element(size_t i, size_t j, col_basis) const {
00273 return (*this)(j,i);
00274 }
00275
00276 void set_basis_element(size_t i, size_t j, ELEMENT_ARG_TYPE s, row_basis) {
00277 (*this)(i,j) = s;
00278 }
00279
00280 void set_basis_element(size_t i, size_t j, ELEMENT_ARG_TYPE s, col_basis) {
00281 (*this)(j,i) = s;
00282 }
00283
00284
00285 public:
00286
00287
00288 #if defined(CML_ENABLE_MATRIX_BRACES)
00289 CML_MATRIX_BRACE_OPERATORS
00290 #endif
00291 };
00292
00294 template<typename Element, typename BasisOrient, typename Layout>
00295 class matrix<Element,external<-1,-1>,BasisOrient,Layout>
00296 : public external_2D<Element,-1,-1,Layout>
00297 {
00298 public:
00299
00300
00301 typedef external<> generator_type;
00302
00303
00304 typedef external_2D<Element,-1,-1,Layout> array_type;
00305
00306
00307 typedef matrix<Element,generator_type,BasisOrient,Layout> matrix_type;
00308
00309
00310 typedef matrix_type expr_type;
00311
00312
00313 typedef matrix<Element,dynamic<>,BasisOrient,Layout> temporary_type;
00314
00315
00316
00317
00318
00319 typedef typename array_type::value_type value_type;
00320 typedef typename array_type::reference reference;
00321 typedef typename array_type::const_reference const_reference;
00322
00323 typedef matrix_type& expr_reference;
00324 typedef const matrix_type& expr_const_reference;
00325
00326
00327 typedef BasisOrient basis_orient;
00328
00329
00330 typedef typename array_type::layout layout;
00331
00332
00333 typedef typename array_type::memory_tag memory_tag;
00334
00335
00336 typedef typename array_type::size_tag size_tag;
00337
00338
00339 typedef typename array_type::resizing_tag resizing_tag;
00340
00341
00342 typedef cml::et::matrix_result_tag result_tag;
00343
00344
00345 typedef cml::et::assignable_tag assignable_tag;
00346
00347
00348 typedef matrix<
00349 Element,
00350 typename array_type::transposed_type::generator_type,
00351 BasisOrient,
00352 Layout
00353 > transposed_type;
00354
00355
00356 typedef vector<
00357 Element,
00358 typename array_type::row_array_type::generator_type
00359 > row_vector_type;
00360
00361 typedef vector<
00362 Element,
00363 typename array_type::col_array_type::generator_type
00364 > col_vector_type;
00365
00366
00367 public:
00368
00370 matrix_type& zero() {
00371 typedef cml::et::OpAssign<Element,Element> OpT;
00372 cml::et::UnrollAssignment<OpT>(*this,Element(0));
00373 return *this;
00374 }
00375
00381 matrix_type& identity() {
00382 for(size_t i = 0; i < this->rows(); ++ i) {
00383 for(size_t j = 0; j < this->cols(); ++ j) {
00384 (*this)(i,j) = value_type((i == j)?1:0);
00385 }
00386 }
00387 return *this;
00388 }
00389
00395 matrix_type& transpose() {
00396
00397 *this = cml::transpose(*this);
00398 return *this;
00399 }
00400
00406 matrix_type& inverse() {
00407
00408 *this = inverse(*this);
00409 return *this;
00410 }
00411
00413 template<typename E, class AT, typename L>
00414 void minimize(const matrix<E,AT,basis_orient,L>& v) {
00415
00416 for (size_t i = 0; i < this->rows(); ++i) {
00417 for (size_t j = 0; j < this->cols(); ++j) {
00418 (*this)[i] = std::min((*this)(i,j),v(i,j));
00419 }
00420 }
00421 }
00422
00424 template<typename E, class AT, class BO, typename L>
00425 void maximize(const matrix<E,AT,basis_orient,L>& v) {
00426
00427 for (size_t i = 0; i < this->rows(); ++i) {
00428 for (size_t j = 0; j < this->cols(); ++j) {
00429 (*this)[i] = std::max((*this)(i,j),v(i,j));
00430 }
00431 }
00432 }
00433
00434
00435 void random(ELEMENT_ARG_TYPE min, ELEMENT_ARG_TYPE max) {
00436 for(size_t i = 0; i < this->rows(); ++i) {
00437 for(size_t j = 0; j < this->cols(); ++j) {
00438 (*this)(i,j) = cml::random_real(min,max);
00439 }
00440 }
00441 }
00442
00443
00444 public:
00445
00458 explicit matrix(value_type* const ptr, size_t rows, size_t cols)
00459 : array_type(ptr,rows,cols) {}
00460
00461
00462 public:
00463
00465 matrix_size size() const {
00466 return matrix_size(this->rows(),this->cols());
00467 }
00468
00470 value_type basis_element(size_t i, size_t j) const {
00471 return basis_element(i,j,basis_orient());
00472 }
00473
00475 void set_basis_element(size_t i, size_t j, ELEMENT_ARG_TYPE s) {
00476 set_basis_element(i,j,s,basis_orient());
00477 }
00478
00479
00480 public:
00481
00482 CML_ASSIGN_MAT_22
00483 CML_ASSIGN_MAT_33
00484 CML_ASSIGN_MAT_44
00485
00486
00487
00488
00489 CML_MAT_ASSIGN_FROM_MATTYPE
00490
00491 CML_MAT_ASSIGN_FROM_MAT(=, et::OpAssign)
00492 CML_MAT_ASSIGN_FROM_MAT(+=, et::OpAddAssign)
00493 CML_MAT_ASSIGN_FROM_MAT(-=, et::OpSubAssign)
00494
00495 CML_MAT_ASSIGN_FROM_MATXPR(=, et::OpAssign)
00496 CML_MAT_ASSIGN_FROM_MATXPR(+=, et::OpAddAssign)
00497 CML_MAT_ASSIGN_FROM_MATXPR(-=, et::OpSubAssign)
00498
00499 CML_MAT_ASSIGN_FROM_SCALAR(*=, et::OpMulAssign)
00500 CML_MAT_ASSIGN_FROM_SCALAR(/=, et::OpDivAssign)
00501
00502 CML_ACCUMULATED_MATRIX_MULT(const matrix_type&)
00503
00504 template<typename E, class AT, typename BO, typename L>
00505 CML_ACCUMULATED_MATRIX_MULT(const TEMPLATED_MATRIX_MACRO&)
00506
00507 template<class XprT>
00508 CML_ACCUMULATED_MATRIX_MULT(MATXPR_ARG_TYPE)
00509
00510
00511 protected:
00512
00513 value_type basis_element(size_t i, size_t j, row_basis) const {
00514 return (*this)(i,j);
00515 }
00516
00517 value_type basis_element(size_t i, size_t j, col_basis) const {
00518 return (*this)(j,i);
00519 }
00520
00521 void set_basis_element(size_t i, size_t j, ELEMENT_ARG_TYPE s, row_basis) {
00522 (*this)(i,j) = s;
00523 }
00524
00525 void set_basis_element(size_t i, size_t j, ELEMENT_ARG_TYPE s, col_basis) {
00526 (*this)(j,i) = s;
00527 }
00528
00529
00530 public:
00531
00532
00533 #if defined(CML_ENABLE_MATRIX_BRACES)
00534 CML_MATRIX_BRACE_OPERATORS
00535 #endif
00536 };
00537
00538 }
00539
00540 #endif
00541
00542
00543