00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00033 #ifndef ACADO_TOOLKIT_T_MATRIX_HPP
00034 #define ACADO_TOOLKIT_T_MATRIX_HPP
00035
00036
00037 BEGIN_NAMESPACE_ACADO
00038
00052 template <typename T>
00053 class Tmatrix
00055 {
00056 template <typename U> friend class Tmatrix;
00057 template <typename U> friend std::ostream& operator<<
00058 ( std::ostream&, const Tmatrix<U>& );
00059 template <typename U> friend Tmatrix<U> operator+
00060 ( const Tmatrix<U>& );
00061 template <typename U, typename V> friend Tmatrix<U> operator+
00062 ( const Tmatrix<U>&, const V& );
00063 template <typename U, typename V> friend Tmatrix<U> operator+
00064 ( const V&, const Tmatrix<U>& );
00065 template <typename U, typename V> friend Tmatrix<U> operator+
00066 ( const Tmatrix<U>&, const Tmatrix<V>& );
00067 template <typename U> friend Tmatrix<U> operator-
00068 ( const Tmatrix<U>& );
00069 template <typename U, typename V> friend Tmatrix<U> operator-
00070 ( const Tmatrix<U>&, const V& );
00071 template <typename U, typename V> friend Tmatrix<U> operator-
00072 ( const U&, const Tmatrix<V>& );
00073 template <typename U, typename V> friend Tmatrix<U> operator-
00074 ( const Tmatrix<U>&, const Tmatrix<V>& );
00075 template <typename U, typename V> friend Tmatrix<U> operator*
00076 ( const Tmatrix<U>&, const V& );
00077 template <typename U, typename V> friend Tmatrix<U> operator*
00078 ( const V&, const Tmatrix<U>& );
00079 template <typename U, typename V> friend Tmatrix<U> operator*
00080 ( const Tmatrix<U>&, const Tmatrix<V>& );
00081 template <typename U, typename V> friend Tmatrix<U> operator/
00082 ( const Tmatrix<U>&, const V& );
00083
00084 public:
00085
00089
00090 Tmatrix():
00091 _nr(0), _nc(0), _sub(false), _pcol(0), _prow(0), _pblock(0)
00092 {}
00094 Tmatrix
00095 ( const unsigned int nr, const unsigned int nc=1, const bool alloc=true ):
00096 _nr(nr), _nc(nc), _sub(!alloc), _pcol(0), _prow(0), _pblock(0)
00097 {
00098 unsigned int ne = nr*nc;
00099 for( unsigned int ie=0; ie<ne; ie++ ){
00100 T*pvall = ( alloc? new T: 0 );
00101 _data.push_back( pvall );
00102 }
00103 }
00105 template <typename U> Tmatrix
00106 ( const unsigned int nr, const unsigned int nc, const U&v,
00107 const bool alloc=true ):
00108 _nr(nr), _nc(nc), _sub(!alloc), _pcol(0), _prow(0), _pblock(0)
00109 {
00110 unsigned int ne = nr*nc;
00111 for( unsigned int ie=0; ie<ne; ie++ ){
00112 T*pvall = ( alloc? new T(v): 0 );
00113 _data.push_back( pvall );
00114 }
00115 }
00117 Tmatrix
00118 ( const Tmatrix<T>&M ):
00119 _nr(M._nr), _nc(M._nc), _sub(false), _pcol(0), _prow(0), _pblock(0)
00120 {
00121 typename std::vector<T*>::const_iterator it = M._data.begin();
00122 for( ; it!=M._data.end(); it++ ){
00123 T*pvall = new T(**it);
00124 _data.push_back( pvall );
00125 }
00126 }
00128 template <typename U> Tmatrix
00129 ( const Tmatrix<U>&M ):
00130 _nr(M._nr), _nc(M._nc), _sub(false), _pcol(0), _prow(0), _pblock(0)
00131 {
00132 typename std::vector<U*>::const_iterator it = M._data.begin();
00133 for( ; it!=M._data.end(); it++ ){
00134 T*pvall = new T(**it);
00135 _data.push_back( pvall );
00136 }
00137 }
00139 ~Tmatrix()
00140 {
00141 delete _pcol;
00142 delete _prow;
00143 delete _pblock;
00144 if( !_sub ) _reset();
00145 }
00146
00148 void resize
00149 ( const unsigned int nr, const unsigned int nc=1, const bool alloc=true )
00150 {
00151 delete _pcol;
00152 delete _prow;
00153 delete _pblock;
00154 if( !_sub ) _reset();
00155 _nr = nr; _nc = nc; _sub = !alloc;
00156 _pcol = _prow = _pblock = 0;
00157 unsigned int ne = nr*nc;
00158 for( unsigned int ie=0; ie<ne; ie++ ){
00159 T*pvall = ( alloc? new T: 0 );
00160 _data.push_back( pvall );
00161 }
00162 }
00164 Tmatrix<T>& col
00165 ( const unsigned int ic );
00167 Tmatrix<T>& row
00168 ( const unsigned int ir );
00170 T*& pval
00171 ( const unsigned int ir, const unsigned int ic );
00173 unsigned int col() const
00174 { return _nc; };
00176 unsigned int row() const
00177 { return _nr; };
00179 T* array() const;
00181 void array
00182 ( const T*pM );
00183
00184 unsigned int getDim() const{ return _nc*_nr; }
00185 unsigned int getNumRows() const{ return _nr; }
00186 unsigned int getNumCols() const{ return _nc; }
00187
00188
00190 Tmatrix<unsigned int> sort();
00191 T& operator()
00192 ( const unsigned int ir, const unsigned int ic );
00193 const T& operator()
00194 ( const unsigned int ir, const unsigned int ic ) const;
00195 T& operator()
00196 ( const unsigned int ie );
00197 const T& operator()
00198 ( const unsigned int ie ) const;
00199 Tmatrix<T>& operator=
00200 ( const Tmatrix<T>&M );
00201 Tmatrix<T>& operator=
00202 ( const T&m );
00203 template <typename U> Tmatrix<T>& operator+=
00204 ( const Tmatrix<U>&M );
00205 template <typename U> Tmatrix<T>& operator+=
00206 ( const U&m );
00207 template <typename U> Tmatrix<T>& operator-=
00208 ( const Tmatrix<U>&M );
00209 template <typename U> Tmatrix<T>& operator-=
00210 ( const U&m );
00211 template <typename U> Tmatrix<T>& operator*=
00212 ( const Tmatrix<U>&M );
00213 template <typename U> Tmatrix<T>& operator*=
00214 ( const U&m );
00215 template <typename U> Tmatrix<T>& operator/=
00216 ( const U&m );
00217
00218 private:
00219
00221 unsigned int _nr;
00223 unsigned int _nc;
00225 std::vector<T*> _data;
00227 bool _sub;
00229 Tmatrix<T>* _pcol;
00231 Tmatrix<T>* _prow;
00233 Tmatrix<T>* _pblock;
00234
00236 T& _val
00237 ( const unsigned int ir, const unsigned int ic );
00238 const T& _val
00239 ( const unsigned int ir, const unsigned int ic ) const;
00240 T& _val
00241 ( const unsigned int ie );
00242 const T& _val
00243 ( const unsigned int ie ) const;
00245 T*& _pval
00246 ( const unsigned int ie );
00248 void _reset();
00250 static unsigned int _digits
00251 ( unsigned int n );
00252 };
00253
00255
00256 template <typename T> inline T&
00257 Tmatrix<T>::operator()
00258 ( const unsigned int ir, const unsigned int ic )
00259 {
00260 return _val(ic*_nr+ir);
00261 }
00262
00263 template <typename T> inline const T&
00264 Tmatrix<T>::operator()
00265 ( const unsigned int ir, const unsigned int ic ) const
00266 {
00267 return _val(ic*_nr+ir);
00268 }
00269
00270 template <typename T> inline T&
00271 Tmatrix<T>::operator()
00272 ( const unsigned int ie )
00273 {
00274 return _val(ie);
00275 }
00276
00277 template <typename T> inline const T&
00278 Tmatrix<T>::operator()
00279 ( const unsigned int ie ) const
00280 {
00281 return _val(ie);
00282 }
00283
00284 template <typename T> inline T&
00285 Tmatrix<T>::_val
00286 ( const unsigned int ir, const unsigned int ic )
00287 {
00288 return _val(ic*_nr+ir);
00289 }
00290
00291 template <typename T> inline const T&
00292 Tmatrix<T>::_val
00293 ( const unsigned int ir, const unsigned int ic ) const
00294 {
00295 return _val(ic*_nr+ir);
00296 }
00297
00298 template <typename T> inline T&
00299 Tmatrix<T>::_val
00300 ( const unsigned int ie )
00301 {
00302 ASSERT( ie<_nr*_nc && ie>=0 );
00303 return *(_data[ie]);
00304 }
00305
00306 template <typename T> inline const T&
00307 Tmatrix<T>::_val
00308 ( const unsigned int ie ) const
00309 {
00310 ASSERT( ie<_nr*_nc && ie>=0 );
00311 return *(_data[ie]);
00312 }
00313
00314 template <typename T> inline T*&
00315 Tmatrix<T>::pval
00316 ( const unsigned int ir, const unsigned int ic )
00317 {
00318 return _pval(ic*_nr+ir);
00319 }
00320
00321 template <typename T> inline T*&
00322 Tmatrix<T>::_pval
00323 ( const unsigned int ie )
00324 {
00325 ASSERT( ie<_nr*_nc && ie>=0 );
00326 return _data[ie];
00327 }
00328
00329 template <typename T> inline void
00330 Tmatrix<T>::_reset()
00331 {
00332 typename std::vector<T*>::iterator it = _data.begin();
00333 for( ; it!=_data.end(); it++ ) delete *it;
00334 }
00335
00336 template <typename T> inline Tmatrix<T>&
00337 Tmatrix<T>::col
00338 ( const unsigned int ic )
00339 {
00340 ASSERT( ic<_nc && ic>=0 );
00341 if( !_pcol ) _pcol = new Tmatrix<T>( _nr, 1, false );
00342 for( unsigned int ir=0; ir<_nr; ir++ ){
00343 _pcol->pval(ir,0) = pval(ir,ic);
00344 #ifdef DEBUG__MATRIX_COL
00345 std::cout << ir << " , 0 : " << pval(ir,ic) << " "
00346 << _pcol->pval(ir,0) << std::endl;
00347 #endif
00348 }
00349 #ifdef DEBUG__MATRIX_COL
00350 std::cout << std::endl;
00351 #endif
00352 return *_pcol;
00353 }
00354
00355 template <typename T> inline Tmatrix<T>&
00356 Tmatrix<T>::row
00357 ( const unsigned int ir )
00358 {
00359 ASSERT( ir<_nr && ir>=0 );
00360 if( !_prow ) _prow = new Tmatrix<T>( 1, _nc, false );
00361 for( unsigned int ic=0; ic<_nc; ic++ ){
00362 _prow->pval(0,ic) = pval(ir,ic);
00363 #ifdef DEBUG__MATRIX_ROW
00364 std::cout << "0 , " << ic << " : " << pval(ir,ic) << " "
00365 << _prow->pval(0,ic) << std::endl;
00366 #endif
00367 }
00368 #ifdef DEBUG__MATRIX_ROW
00369 std::cout << std::endl;
00370 #endif
00371 return *_prow;
00372 }
00373
00374 template <typename T> inline Tmatrix<T>&
00375 Tmatrix<T>::operator=
00376 ( const Tmatrix<T>&M )
00377 {
00378 if( M._nr!=_nr || M._nc!=_nc )
00379 resize( M._nr, M._nc );
00380 for( unsigned int ie=0; ie!=_nr*_nc; ie++ ){
00381 _val(ie) = M._val(ie);
00382 }
00383 return *this;
00384 }
00385
00386 template <typename T> inline Tmatrix<T>&
00387 Tmatrix<T>::operator=
00388 ( const T&m )
00389 {
00390 for( unsigned int ie=0; ie!=_nr*_nc; ie++ ){
00391 _val(ie) = m;
00392 }
00393 return *this;
00394 }
00395
00396 template <typename T> template <typename U> inline Tmatrix<T>&
00397 Tmatrix<T>::operator+=
00398 ( const Tmatrix<U>&M )
00399 {
00400 ASSERT( M._nr==_nr && M._nc==_nc );
00401 for( unsigned int ie=0; ie!=_nr*_nc; ie++ )
00402 _val(ie) += M._val(ie);
00403 return *this;
00404 }
00405
00406 template <typename T> template <typename U> inline Tmatrix<T>&
00407 Tmatrix<T>::operator+=
00408 ( const U&m )
00409 {
00410 for( unsigned int ie=0; ie!=_nr*_nc; ie++ )
00411 _val(ie) += m;
00412 return *this;
00413 }
00414
00415 template <typename T> template <typename U> inline Tmatrix<T>&
00416 Tmatrix<T>::operator-=
00417 ( const Tmatrix<U>&M )
00418 {
00419 ASSERT( M._nr==_nr && M._nc==_nc );
00420 for( unsigned int ie=0; ie!=_nr*_nc; ie++ )
00421 _val(ie) -= M._val(ie);
00422 return *this;
00423 }
00424
00425 template <typename T> template <typename U> inline Tmatrix<T>&
00426 Tmatrix<T>::operator-=
00427 ( const U&m )
00428 {
00429 for( unsigned int ie=0; ie!=_nr*_nc; ie++ )
00430 _val(ie) -= m;
00431 return *this;
00432 }
00433
00434 template <typename T> template <typename U> inline Tmatrix<T>&
00435 Tmatrix<T>::operator*=
00436 ( const Tmatrix<U>&M )
00437 {
00438 ASSERT( M._nr==M._nc && M._nr==_nc );
00439 for( unsigned int ir=0; ir<_nr; ir++ ){
00440 Tmatrix<T> irow = row(ir);
00441 for( unsigned int ic=0; ic<_nc; ic++ ){
00442 _val(ir,ic) = irow(0)*M(0,ic);
00443 for( unsigned int k=1; k<_nc; k++ ){
00444 _val(ir,ic) += irow(k)*M(k,ic);
00445 }
00446 }
00447 }
00448 return *this;
00449 }
00450
00451 template <typename T> template <typename U> inline Tmatrix<T>&
00452 Tmatrix<T>::operator*=
00453 ( const U&m )
00454 {
00455 for( unsigned int ie=0; ie!=_nr*_nc; ie++ )
00456 _val(ie) *= m;
00457 return *this;
00458 }
00459
00460 template <typename T> template <typename U> inline Tmatrix<T>&
00461 Tmatrix<T>::operator/=
00462 ( const U&m )
00463 {
00464 for( unsigned int ie=0; ie!=_nr*_nc; ie++ )
00465 _val(ie) /= m;
00466 return *this;
00467 }
00468
00469 template <typename T> inline Tmatrix<T>
00470 operator+
00471 ( const Tmatrix<T>&M )
00472 {
00473 return M;
00474 }
00475
00476 template <typename T, typename U> inline Tmatrix<T>
00477 operator+
00478 ( const Tmatrix<T>&M, const Tmatrix<U>&N )
00479 {
00480 Tmatrix<T> P( M );
00481 P += N;
00482 return P;
00483 }
00484
00485 template <typename T, typename U> inline Tmatrix<T>
00486 operator+
00487 ( const Tmatrix<T>&M, const U&n )
00488 {
00489 Tmatrix<T> P( M );
00490 P += n;
00491 return P;
00492 }
00493
00494 template <typename T, typename U> inline Tmatrix<T>
00495 operator+
00496 ( const U&m, const Tmatrix<T>&N )
00497 {
00498 return N+m;
00499 }
00500
00501 template <typename T> inline Tmatrix<T>
00502 operator-
00503 ( const Tmatrix<T>&M )
00504 {
00505 return -M;
00506 }
00507
00508 template <typename T, typename U> inline Tmatrix<T>
00509 operator-
00510 ( const Tmatrix<T>&M, const Tmatrix<U>&N )
00511 {
00512 Tmatrix<T> P( M );
00513 P -= N;
00514 return P;
00515 }
00516
00517 template <typename T, typename U> inline Tmatrix<T>
00518 operator-
00519 ( const Tmatrix<T>&M, const U&n )
00520 {
00521 Tmatrix<T> P( M );
00522 P -= n;
00523 return P;
00524 }
00525
00526 template <typename T, typename U> inline Tmatrix<T>
00527 operator-
00528 ( const T&m, const Tmatrix<U>&N )
00529 {
00530 Tmatrix<T> P( -N );
00531 P += m;
00532 return P;
00533 }
00534
00535 template <typename T, typename U> inline Tmatrix<T>
00536 operator*
00537 ( const Tmatrix<T>&M, const Tmatrix<U>&N )
00538 {
00539 ASSERT( M._nc==N._nr );
00540 Tmatrix<T> P( M._nr, N._nc );
00541 for( unsigned int ir=0; ir<M._nr; ir++ ){
00542 for( unsigned int ic=0; ic<N._nc; ic++ ){
00543 P(ir,ic) = M(ir,0)*N(0,ic);
00544 for( unsigned int k=1; k<M._nc; k++ ){
00545 P(ir,ic) += M(ir,k)*N(k,ic);
00546 }
00547 }
00548 }
00549 return P;
00550 }
00551
00552 template <typename T, typename U> inline Tmatrix<T>
00553 operator*
00554 ( const Tmatrix<T>&M, const U&n )
00555 {
00556 Tmatrix<T> P( M );
00557 P *= n;
00558 return P;
00559 }
00560
00561 template <typename T, typename U> inline Tmatrix<T>
00562 operator*
00563 ( const U&m, const Tmatrix<T>&N )
00564 {
00565 return N*m;
00566 }
00567
00568 template <typename T, typename U> inline Tmatrix<T>
00569 operator/
00570 ( const Tmatrix<T>&M, const U&n )
00571 {
00572 Tmatrix<T> P( M );
00573 P /= n;
00574 return P;
00575 }
00576
00577 template <typename T> inline std::ostream&
00578 operator<<
00579 ( std::ostream& os, const Tmatrix<T>&M )
00580 {
00581 for( unsigned int ir=0; ir<M._nr; ir++ )
00582 for( unsigned int ic=0; ic<M._nc; ic++ )
00583 os << ir << " , " << ic << " : " << M(ir,ic) << std::endl;
00584 return os;
00585 }
00586
00587 template <typename T> inline T*
00588 Tmatrix<T>::array() const
00589 {
00590 T*pM = new T[_nr*_nc];
00591 for( unsigned int ic=0, ie=0; ic<_nc; ic++ )
00592 for( unsigned int ir=0; ir<_nr; ir++, ie++ )
00593 pM[ie] = _val (ir,ic);
00594 return pM;
00595 }
00596
00597 template <typename T> inline void
00598 Tmatrix<T>::array
00599 ( const T*pM )
00600 {
00601 for( unsigned int ic=0, ie=0; ic<_nc; ic++ )
00602 for( unsigned int ir=0; ir<_nr; ir++, ie++ )
00603 _val(ir,ic) = pM[ie];
00604 }
00605
00606
00607 template <typename T> inline unsigned int
00608 Tmatrix<T>::_digits
00609 ( unsigned int n )
00610 {
00611 if( n == 0 ) return 1;
00612 int l = 0;
00613 while( n > 0 ){
00614 ++l;
00615 n /= 10;
00616 }
00617 return l;
00618 }
00619
00620
00621
00622 CLOSE_NAMESPACE_ACADO
00623
00624
00625 #endif // ACADO_TOOLKIT_T_MATRIX_HPP
00626
00627
00628
00629