latest version v1.9 - last update 10 Apr 2010 |
00001 /* 00002 * Copyright (C) 2001, 2002, 2003, 2004, 2005, 2006 00003 * Lehrstuhl fuer Technische Informatik, RWTH-Aachen, Germany 00004 * 00005 * This file is part of the LTI-Computer Vision Library (LTI-Lib) 00006 * 00007 * The LTI-Lib is free software; you can redistribute it and/or 00008 * modify it under the terms of the GNU Lesser General Public License (LGPL) 00009 * as published by the Free Software Foundation; either version 2.1 of 00010 * the License, or (at your option) any later version. 00011 * 00012 * The LTI-Lib is distributed in the hope that it will be 00013 * useful, but WITHOUT ANY WARRANTY; without even the implied warranty 00014 * of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00015 * GNU Lesser General Public License for more details. 00016 * 00017 * You should have received a copy of the GNU Lesser General Public 00018 * License along with the LTI-Lib; see the file LICENSE. If 00019 * not, write to the Free Software Foundation, Inc., 59 Temple Place - 00020 * Suite 330, Boston, MA 02111-1307, USA. 00021 */ 00022 00023 00024 /*---------------------------------------------------------------- 00025 * project ....: LTI Digital Image/Signal Processing Library 00026 * file .......: ltiKalmanTracker.h 00027 * authors ....: Joerg Zieren 00028 * organization: LTI, RWTH Aachen 00029 * creation ...: 19.04.2001 00030 * revisions ..: $Id: ltiKalmanTracker.h,v 1.9 2006/02/08 11:21:00 ltilib Exp $ 00031 */ 00032 00033 #ifndef _LTI_KALMAN_TRACKER_H_ 00034 #define _LTI_KALMAN_TRACKER_H_ 00035 00036 #include "ltiKalmanFilter.h" 00037 00038 namespace lti { 00039 00040 /** 00041 * A tracker implementation making use of the class 00042 * kalmanFilter. It tracks a 2D point, using a system state vector 00043 * that contains x and y coordinate as well as x and y velocity 00044 * (denoted by vx and vy) and, optionally, x and y acceleration (ax and ay) 00045 * of this point. These state vectors correspond to the assumption of 00046 * constant velocity and constant acceleration, respectively. The state 00047 * vector is structured like this: (x,vx,y,vy), 00048 * or (x,vx,y,vy,ax,ay). The measured x and y coordinate are given 00049 * to the apply method, which returns the estimated x and y coordinates at 00050 * the next time step. 00051 * 00052 * These matrices (contained in the parameters) must be specified: 00053 * 00054 * matrix<float> measurementNoiseCovariance (\f$R\f$; 2x2)<BR> 00055 * matrix<float> processNoiseCovariance (\f$Q\f$; 4x4 / 6x6) 00056 * 00057 * These matrices (contained in the parameters) should be specified, 00058 * but are initialized to default values that should be sufficient for 00059 * a first try: 00060 * 00061 * vector<float> initialSystemState (\f$\hat{x}^{-}\f$; 4 / 6)<BR> 00062 * matrix<float> initialErrorCovariance (\f$P^{-}\f$ and \f$P\f$; 4x4 / 6x6) 00063 * 00064 * The parantheses contain notation and dimensionality of the matrices for 00065 * the constant velocity / constant acceleration case. 00066 */ 00067 class kalmanTracker : public functor { 00068 public: 00069 00070 /** 00071 * The parameters for the class kalmanTracker. 00072 */ 00073 class parameters : public functor::parameters { 00074 public: 00075 /** 00076 * Initializes all matrices/vectors (except for measurement 00077 * and process noise covariance) for an n-dimensional system state. 00078 * Currently n may be 4 or 6. Default is 4. 00079 */ 00080 parameters(const int& stateDimensions = 4); 00081 00082 /** 00083 * copy constructor 00084 * @param other the parameters %object to be copied 00085 */ 00086 parameters(const parameters& other); 00087 00088 /** 00089 * destructor 00090 */ 00091 ~parameters(); 00092 00093 /** 00094 * returns name of this type 00095 */ 00096 const char* getTypeName() const; 00097 00098 /** 00099 * copy the contents of a parameters %object 00100 * @param other the parameters %object to be copied 00101 * @return a reference to this parameters %object 00102 */ 00103 parameters& copy(const parameters& other); 00104 00105 /** 00106 * copy the contents of a parameters %object 00107 * @param other the parameters %object to be copied 00108 * @return a reference to this parameters %object 00109 */ 00110 parameters& operator=(const parameters& other); 00111 00112 /** 00113 * returns a pointer to a clone of the parameters 00114 */ 00115 virtual lti::functor::parameters* clone() const; 00116 00117 /** 00118 * The initial system state (used to initialize the tracker) 00119 * (4x1 / 6x1 for constant-velocity/constant-acceleration). 00120 * If you want to automatically initialize the tracker with the 00121 * first measurement, use autoInitialize. Default value is 0. Specifying 00122 * an initial system state is a good idea, but is not generally required. 00123 */ 00124 vector<float> initialSystemState; 00125 00126 /** 00127 * Measurement %noise covariance matrix (R; 2x2). This matrix 00128 * has no default value and must be supplied! 00129 */ 00130 matrix<float> measurementNoiseCovariance; 00131 00132 /** 00133 * Process %noise covariance matrix (Q; 4x4 / 6x6 for 00134 * constant-velocity/constant-acceleration). This matrix 00135 * has no default value and must be supplied! 00136 */ 00137 matrix<float> processNoiseCovariance; 00138 00139 /** 00140 * Initial value for the estimate error covariance matrix 00141 * (P; 4x4 / 6x6 for constant-velocity/constant-acceleration). 00142 * This value is used to initialize both the a priori and the a posteriori 00143 * error covariance (\f$P\f$ and \f$P^{-}\f$). Depending on whether the first 00144 * update is a time/measurement update, the latter/former will be overwritten. 00145 * This matrix has a default value of 1 (unity). It should be specified 00146 * considering the uncertainty of the supplied initial system state. 00147 */ 00148 matrix<float> initialErrorCovariance; 00149 00150 /** 00151 * AutoInitialization means that the tracker uses the first actual 00152 * measurement as initial system state (i.e.\ x and y are set to 00153 * the first measurement, while all other state variables are set to zero). 00154 * 00155 * Default is false. 00156 */ 00157 bool autoInitialize; 00158 00159 /** 00160 * write the parameters in the given ioHandler 00161 * @param handler the ioHandler to be used 00162 * @param complete if true (the default) the enclosing begin/end will 00163 * be also written, otherwise only the data block will be written. 00164 * @return true if write was successful 00165 */ 00166 virtual bool read(ioHandler& handler,const bool complete=true); 00167 00168 /** 00169 * write the parameters in the given ioHandler 00170 * @param handler the ioHandler to be used 00171 * @param complete if true (the default) the enclosing begin/end will 00172 * be also written, otherwise only the data block will be written. 00173 * @return true if write was successful 00174 */ 00175 virtual bool write(ioHandler& handler, const bool complete=true) const; 00176 00177 # ifdef _LTI_MSC_6 00178 /** 00179 * this function is required by MSVC only, as a workaround for a 00180 * very awful bug, which exists since MSVC V.4.0, and still by 00181 * V.6.0 with all bugfixes (so called "service packs") remains 00182 * there... This method is public due to another bug!, so please 00183 * NEVER EVER call this method directly 00184 */ 00185 virtual bool readMS(ioHandler& handler,const bool complete=true); 00186 00187 /** 00188 * this function is required by MSVC only, as a workaround for a 00189 * very awful bug, which exists since MSVC V.4.0, and still by 00190 * V.6.0 with all bugfixes (so called "service packs") remains 00191 * there... This method is public due to another bug!, so please 00192 * NEVER EVER call this method directly 00193 */ 00194 virtual bool writeMS(ioHandler& handler,const bool complete=true) const; 00195 # endif 00196 }; 00197 00198 /** 00199 * constructor for n-dimensional system state (n may be 4 or 6). 00200 * default is 4. 00201 */ 00202 kalmanTracker(const int& stateDimensions = 4); 00203 00204 /** 00205 * copy constructor 00206 * @param other the %object to be copied 00207 */ 00208 kalmanTracker(const kalmanTracker& other); 00209 00210 /** 00211 * destructor 00212 */ 00213 virtual ~kalmanTracker(); 00214 00215 /** 00216 * returns the name of this type ("kalmanTracker") 00217 */ 00218 virtual const char* getTypeName() const; 00219 00220 /** 00221 * Return the number of system state dimensions (currently either 00222 * 4 or 6). 00223 */ 00224 int getSystemStateDimensions() const; 00225 00226 /** 00227 * Perform a measurement update and then a time update, resulting 00228 * in a prediction of x and y coordinates for the next time step, 00229 * which are then returned. 00230 */ 00231 bool apply(const float& xMeasurement, 00232 const float& yMeasurement, 00233 float& xPredictionApriori, 00234 float& yPredictionApriori); 00235 00236 /** 00237 * Perform only a time update (i.e. no new measurement available), resulting 00238 * in a prediction of x and y coordinates for the next time step, 00239 * which are then returned. 00240 */ 00241 bool apply(float& xPredictionApriori, 00242 float& yPredictionApriori); 00243 00244 /** 00245 * copy data of "other" functor. 00246 * @param other the functor to be copied 00247 * @return a reference to this functor %object 00248 */ 00249 kalmanTracker& copy(const kalmanTracker& other); 00250 00251 /** 00252 * returns a pointer to a clone of this functor. 00253 */ 00254 virtual functor* clone() const; 00255 00256 /** 00257 * returns used parameters 00258 */ 00259 const parameters& getParameters(void) const; 00260 00261 /** 00262 * set parameters of this Kalman tracker 00263 */ 00264 bool updateParameters(); 00265 00266 /** 00267 * set a new measurement %noise covariance, e.g. because future 00268 * measurements are less/more reliable (overlapping starts/ends) 00269 */ 00270 void setMeasurementNoiseCovariance(const matrix<float>& r); 00271 00272 /** 00273 * Get the (a priori) system state estimate (\f$\hat{x}^{-}\f$). 00274 * This is the prediction one would normally be interested in. 00275 */ 00276 const vector<float>& getEstimate() const; 00277 00278 /** 00279 * Get the a posteriori system state estimate (\f$\hat{x}\f$). 00280 */ 00281 const vector<float>& getEstimateAposteriori() const; 00282 00283 /** 00284 * Get the a priori error covariance (\f$P^{-}\f$). 00285 */ 00286 const matrix<float>& getErrorCovarianceApriori() const; 00287 00288 /** 00289 * Get the a posteriori error covariance (\f$P\f$). 00290 */ 00291 const matrix<float>& getErrorCovarianceAposteriori() const; 00292 00293 /** 00294 * Reset the filter state (\f$x\f$) and error covariance (\f$P\f$). The 00295 * tracker is left in an un-initialized state. 00296 */ 00297 void reset(void); 00298 00299 /** 00300 * Tell if this tracker is initialized, i.e. if any of the apply methods 00301 * has been called after the creation of this object or a call to reset(). 00302 */ 00303 bool isInitialized() const; 00304 00305 protected: 00306 /** 00307 * The kalmanFilter used by this tracker. 00308 */ 00309 kalmanFilter kalman; 00310 00311 /** 00312 * Perform time update 00313 */ 00314 bool performTimeUpdate(); 00315 00316 /** 00317 * Perform measurement update 00318 */ 00319 bool performMeasurementUpdate(const float& xMeasurement, 00320 const float& yMeasurement); 00321 00322 /** 00323 * Initialization status of this tracker. Set to false after object 00324 * creation or call to reset(). Set to true after the first update, 00325 * i.e. call to an apply method. 00326 */ 00327 bool initialized; 00328 00329 /** 00330 * This temporary variable wraps two floats (the x/y measurement) 00331 * in a vector. 00332 */ 00333 lti::vector<float> measurement; 00334 00335 /** 00336 * This temporary variable wraps two floats (the x/y prediction) 00337 * in a vector. 00338 */ 00339 lti::vector<float> prediction; 00340 }; 00341 } 00342 00343 #endif