@@ -156,40 +156,6 @@ inline OUDiscreteCoeffs<T> safe_phi_A_coeffs(T h, T tau) {
156
156
return c;
157
157
}
158
158
159
- // Generic rank-3 Joseph update (3D measurement)
160
- template <typename T, int NX>
161
- static inline void joseph_update_rank3 (
162
- Eigen::Matrix<T,NX,1 >& x, // state vector
163
- Eigen::Matrix<T,NX,NX>& P, // covariance
164
- const Eigen::Matrix<T,3 ,NX>& C, // measurement Jacobian (3×NX, usually sparse)
165
- const Eigen::Matrix<T,3 ,1 >& r, // innovation
166
- const Eigen::Matrix<T,3 ,3 >& R) // measurement noise
167
- {
168
- // Innovation covariance
169
- Eigen::Matrix<T,3 ,3 > S = C * P * C.transpose () + R;
170
- Eigen::LDLT<Eigen::Matrix<T,3 ,3 >> ldlt (S);
171
- if (ldlt.info () != Eigen::Success) {
172
- Eigen::Matrix<T,3 ,3 > S_reg = S + Eigen::Matrix<T,3 ,3 >::Identity () *
173
- std::max (std::numeric_limits<T>::epsilon (), T (1e-6 ) * R.norm ());
174
- ldlt.compute (S_reg);
175
- if (ldlt.info () != Eigen::Success) return ;
176
- }
177
-
178
- // Kalman gain
179
- Eigen::Matrix<T,NX,3 > K = P * C.transpose () * ldlt.solve (Eigen::Matrix<T,3 ,3 >::Identity ());
180
-
181
- // State update
182
- x.noalias () += K * r;
183
-
184
- // Joseph covariance update (rank-3 form)
185
- Eigen::Matrix<T,3 ,NX> CP = C * P; // 3×NX
186
- Eigen::Matrix<T,NX,NX> KC = K * CP; // NX×NX, rank ≤ 3
187
- P.noalias () = P - KC - KC.transpose () + K * R * K.transpose ();
188
-
189
- // Symmetrize
190
- P = T (0.5 ) * (P + P.transpose ());
191
- }
192
-
193
159
template <typename T = float , bool with_gyro_bias = true , bool with_accel_bias = true >
194
160
class EIGEN_ALIGN_MAX Kalman3D_Wave {
195
161
@@ -420,6 +386,31 @@ class EIGEN_ALIGN_MAX Kalman3D_Wave {
420
386
Eigen::Matrix<T,12 ,12 >& Qd) const ;
421
387
static void PhiAxis4x1_analytic (T tau, T h, Eigen::Matrix<T,4 ,4 >& Phi_axis);
422
388
static void QdAxis4x1_analytic (T tau, T h, T sigma2, Eigen::Matrix<T,4 ,4 >& Qd_axis);
389
+
390
+ static inline void joseph_update_rank3 (
391
+ Eigen::Matrix<T,NX,1 >& x,
392
+ Eigen::Matrix<T,NX,NX>& P,
393
+ const Eigen::Matrix<T,3 ,NX>& C,
394
+ const Eigen::Matrix<T,3 ,1 >& r,
395
+ const Eigen::Matrix<T,3 ,3 >& R)
396
+ {
397
+ Eigen::Matrix<T,3 ,3 > S = C * P * C.transpose () + R;
398
+ Eigen::LDLT<Eigen::Matrix<T,3 ,3 >> ldlt (S);
399
+ if (ldlt.info () != Eigen::Success) {
400
+ Eigen::Matrix<T,3 ,3 > S_reg = S + Eigen::Matrix<T,3 ,3 >::Identity () *
401
+ std::max (std::numeric_limits<T>::epsilon (), T (1e-6 ) * R.norm ());
402
+ ldlt.compute (S_reg);
403
+ if (ldlt.info () != Eigen::Success) return ;
404
+ }
405
+
406
+ Eigen::Matrix<T,NX,3 > K = P * C.transpose () * ldlt.solve (Eigen::Matrix<T,3 ,3 >::Identity ());
407
+ x.noalias () += K * r;
408
+
409
+ Eigen::Matrix<T,3 ,NX> CP = C * P;
410
+ Eigen::Matrix<T,NX,NX> KC = K * CP;
411
+ P.noalias () = P - KC - KC.transpose () + K * R * K.transpose ();
412
+ P = T (0.5 ) * (P + P.transpose ());
413
+ }
423
414
};
424
415
425
416
// Implementation
0 commit comments