work/mixpp/libKF.h

Go to the documentation of this file.
00001 
00013 #ifndef KF_H
00014 #define KF_H
00015 
00016 #include <itpp/itbase.h>
00017 #include "libBM.h"
00018 #include "libDC.h"
00019 
00020 
00021 using namespace itpp;
00022 
00026 class KalmanFull : public BM { 
00027         int dimx, dimy, dimu;
00028         mat A, B, C, D, R, Q;
00029         
00030         //cache 
00031         mat _Pp, _Ry, _iRy, _K;
00032 public:
00033         //posterior 
00035         vec mu;
00037         mat P;
00038 
00039 public:
00041         KalmanFull ( mat A, mat B, mat C, mat D, mat R, mat Q, mat P0, vec mu0);
00043         void bayes(const vec &dt, bool evalll=true); 
00044 
00045         friend std::ostream &operator<< ( std::ostream &os, const KalmanFull &kf );
00046 
00047 };
00048 
00049 
00053 template<class sq_T>
00054 class Kalman : public BM { 
00055         int dimx, dimy, dimu;
00056         mat A, B, C, D;
00057         sq_T R, Q;
00058         
00059         //cache
00060         mat _K;
00061         vec _yp;
00062         sq_T _Ry,_iRy;
00063 public:
00064         //posterior 
00066         vec mu;
00068         sq_T P;
00069 
00070 public:
00072         Kalman ( mat A0, mat B0, mat C0, mat D0, sq_T R0, sq_T Q0, sq_T P0, vec mu0 );
00074         void bayes(const vec &dt, bool evalll=true); 
00075 
00076         friend std::ostream &operator<< ( std::ostream &os, const KalmanFull &kf );
00077 
00078 };
00079 
00081 
00082 template<class sq_T>
00083 Kalman<sq_T>::Kalman( mat A0, mat B0, mat C0, mat D0, sq_T R0, sq_T Q0, sq_T P0, vec mu0 ) {
00084         dimx = A0.rows();
00085         dimu = B0.cols();
00086         dimy = C0.rows();
00087 
00088         it_assert_debug( A0.cols()==dimx, "Kalman: A is not square" );
00089         it_assert_debug( B0.rows()==dimx, "Kalman: B is not compatible" );
00090         it_assert_debug( C0.cols()==dimx, "Kalman: C is not square" );
00091         it_assert_debug(( D0.rows()==dimy ) || ( D0.cols()==dimu ),     "Kalman: D is not compatible" );
00092         it_assert_debug(( R0.cols()==dimy ) || ( R0.rows()==dimy ), "Kalman: R is not compatible" );
00093         it_assert_debug(( Q0.cols()==dimx ) || ( Q0.rows()==dimx ), "Kalman: Q is not compatible" );
00094 
00095         A = A0;
00096         B = B0;
00097         C = C0;
00098         D = D0;
00099         R = R0;
00100         Q = Q0;
00101         mu = mu0;
00102         P = P0;
00103 
00104         ll = 0;
00105 //Fixme should we assign cache??
00106         _iRy = eye(dimy); // needed in inv(_iRy)
00107 }
00108 
00109 template<class sq_T>
00110 void Kalman<sq_T>::bayes( const vec &dt , bool evalll) {
00111         it_assert_debug( dt.length()==( dimy+dimu ),"KalmanFull::bayes wrong size of dt" );
00112 
00113         vec u = dt.get( dimy,dimy+dimu-1 );
00114         vec y = dt.get( 0,dimy-1 );
00115         //Time update
00116         mu = A*mu + B*u;
00117         //P  = A*P*A.transpose() + Q; in sq_T
00118         P.mult_sym( A );
00119         P+=Q;
00120 
00121         //Data update
00122         //_Ry = C*P*C.transpose() + R; in sq_T
00123         _Ry.mult_sym( C, P);
00124         _Ry+=R;
00125 
00126         mat Pfull = P.to_mat();
00127         
00128         _Ry.inv( _iRy ); // result is in _iRy;
00129         _K = Pfull*C.transpose()*(_iRy.to_mat());
00130         P -= _K*C*Pfull; // P = P -KCP;
00131         _yp = y-C*mu-D*u; //y prediction
00132         mu += _K*( _yp );
00133         
00134         if (evalll==true) {
00135         ll+= -0.5*(_Ry.cols()*0.79817986835811504957 \
00136         +_Ry.logdet() +_iRy.qform(_yp));
00137         }
00138 };
00139 
00140 //extern template class Kalman<ldmat>; 
00141 
00142 
00143 #endif // KF_H
00144 
00145 

Generated on Wed Jan 23 11:30:10 2008 for mixpp by  doxygen 1.5.3