CbmRoot
Loading...
Searching...
No Matches
KfTrackKalmanFilter.h
Go to the documentation of this file.
1/* Copyright (C) 2017-2021 GSI Helmholtzzentrum fuer Schwerionenforschung, Darmstadt
2 SPDX-License-Identifier: GPL-3.0-only
3 Authors: Sergey Gorbunov [committer], Maksym Zyzak */
4
5
10
11#pragma once // include this header only once per compilation unit
12
13#include "KfFieldRegion.h"
14#include "KfMeasurementTime.h"
15#include "KfMeasurementU.h"
16#include "KfMeasurementXy.h"
17#include "KfSimd.h"
18#include "KfTrackParam.h"
19#include "KfUtils.h"
20
21#include <type_traits>
22
23namespace cbm::algo::kf
24{
30
35
36 template<typename T>
38 LinearizationFull() = default;
40 : x(p.GetX())
41 , y(p.GetY())
42 , tx(p.GetTx())
43 , ty(p.GetTy())
44 , qp(p.GetQp())
45 , time(p.GetTime())
46 , vi(p.GetVi())
47 {
48 }
49
50 T x{T(0.)};
51 T y{T(0.)};
52 T tx{T(0.)};
53 T ty{T(0.)};
54 T qp{T(0.)};
55 T time{T(0.)};
56 T vi{T(0.)};
57 };
58
59
60 template<typename T>
62 LinearizationQp() = default;
63 LinearizationQp(const TrackParam<T> p) : qp(p.GetQp()) {}
64
65 T qp;
66 };
67
68 template<template<typename T> class LinearizationT_ = LinearizationQp, DoFitTime FlagFitTime = DoFitTime::Y>
70 template<typename T>
71 using LinearizationT = LinearizationT_<T>;
72 static constexpr bool kDoFitTime = (FlagFitTime == DoFitTime::Y);
73 };
74
77
78 template<typename DataT, class Settings = FilterSettings<>>
80
81 public:
82 using Linearization_t = typename Settings::template LinearizationT<DataT>;
85
86 static constexpr int kNactiveParams = 5 + (Settings::kDoFitTime ? 2 : 0);
87
88
89 TrackKalmanFilter() = default;
90
92
93 template<typename T>
95 {
96 SetTrack(t);
97 }
98
99 void SetMask(const DataTmask& m) { fMask = m; }
100
101 template<typename T>
103 {
104 fTr.Set(t);
106 }
107
108 void SetTrack(DataT z, const LinearizationFull<DataT>& lin)
109 {
110 fTr.SetX(lin.x);
111 fTr.SetY(lin.y);
112 fTr.SetZ(z);
113 fTr.SetTx(lin.tx);
114 fTr.SetTy(lin.ty);
115 fTr.SetQp(lin.qp);
116 if constexpr (Settings::kDoFitTime) {
117 fTr.SetTime(lin.time);
118 fTr.SetVi(lin.vi);
119 }
121 }
122
124
126
128
129 void SetOneEntry(const int i0, const TrackKalmanFilter& T1, const int i1);
130
131 std::string ToString(int i = -1);
132
135
137 void SetParticleMass(DataT mass)
138 {
139 fMass = mass;
140 fMass2 = mass * mass;
141 }
142
144 DataT GetParticleMass() const { return fMass; }
145
147 DataT GetParticleMass2() const { return fMass2; }
148
150 void SetMaxExtrapolationStep(double step) { fMaxExtrapolationStep = DataT(step); }
151
154
156 void Filter1d(const kf::MeasurementU<DataT>& m);
157
159 void FilterXY(const kf::MeasurementXy<DataT>& m, bool skipUnmeasuredCoordinates = false);
160
162 void FilterTime(DataT t, DataT dt2, const DataTmask& m);
163
165 void FilterTime(kf::MeasurementTime<DataT> mt) { FilterTime(mt.T(), mt.Dt2(), DataTmask(mt.NdfT() > DataT(0.))); }
166
168 void FilterVi(DataT vi);
169
172
177 void Extrapolate(DataT z, const kf::FieldRegion<DataT>& F);
178
182
184 void ExtrapolateNoField(DataT z);
185
186
188 void ExtrapolateLineInField(DataT z_out, const kf::FieldRegion<DataT>& F);
189
193 void EnergyLossCorrection(DataT radThick, FitDirection direction);
194
203 void EnergyLossCorrection(int atomicZ, DataTscal atomicA, DataTscal rho, DataTscal radLen, DataT radThick,
204 FitDirection direction);
205
206
208 void MultipleScattering(DataT radThick, DataT tx0, DataT ty0, DataT qp0);
209
211 void MultipleScattering(DataT radThick)
212 {
213 MultipleScattering(radThick, fTr.GetTx(), fTr.GetTy(), fLinearisation.qp);
214 }
215
217 void MultipleScatteringInThickMaterial(DataT radThick, DataT thickness, bool fDownstream);
218
221
223 void GetMeasurementModelAtZline(DataT zm, const kf::FieldRegion<DataT>& Field, std::array<DataT, 5>& Jx,
224 std::array<DataT, 5>& Jy) const;
225
230 void FilterExtrapolatedXY(const kf::MeasurementXy<DataT>& m, const std::array<DataT, 5>& Jx,
231 const std::array<DataT, 5>& Jy);
232
233
234 void FilterExtrapolatedY(const kf::MeasurementXy<DataT>& m, const std::array<DataT, 5>& Jy);
235
236 void FilterExtrapolatedY(const kf::MeasurementXy<DataT>& mL, const std::array<DataT, 5>& jL,
237 const kf::MeasurementXy<DataT>& mM, DataT msM, const kf::MeasurementXy<DataT>& mR,
238 const std::array<DataT, 5>& jR);
239
240 void FilterExtrapolatedYChi2(const kf::MeasurementXy<DataT>& mL, const std::array<DataT, 5>& jL,
241 const kf::MeasurementXy<DataT>& mM, DataT msM, const kf::MeasurementXy<DataT>& mR,
242 const std::array<DataT, 5>& jR);
243
247 std::pair<DataT, DataT> ExtrapolateLineXdX2(DataT z_out) const;
248
252 std::pair<DataT, DataT> ExtrapolateLineYdY2(DataT z_out) const;
253
257 DataT ExtrapolateLineDxy(DataT z_out) const;
258
262 static DataT ApproximateBetheBloch(DataT bg2);
263
272 static DataT ApproximateBetheBloch(DataT bg2, DataT kp0, DataT kp1, DataT kp2, DataT kp3, DataT kp4);
273
283 static std::tuple<DataT, DataT> GetChi2XChi2U(kf::MeasurementXy<DataT> m, DataT x, DataT y, DataT C00, DataT C10,
284 DataT C11);
285
296 void GuessTrack(const DataT& trackZ, const DataT hitX[], const DataT hitY[], const DataT hitZ[], const DataT hitT[],
297 const DataT By[], const DataTmask hitW[], const DataTmask hitWtime[], int NHits);
298
299 private:
301
302 typedef const DataT cnst;
303
306
308
311
312 DataT fMass{0.10565800};
313 DataT fMass2{fMass * fMass};
314
316
318
319 // =============================================================================================
320
321 template<typename DataT, class Settings>
323 {
324 return fTr.ToString(i);
325 }
326
327
328 template<typename DataT, class Settings>
329 inline void TrackKalmanFilter<DataT, Settings>::SetOneEntry(const int i0, const TrackKalmanFilter& T1, const int i1)
330 {
331 fTr.SetOneEntry(i0, T1.fTr, i1);
333 }
334
335 template<typename DataT, class Settings>
336 inline std::pair<DataT, DataT> TrackKalmanFilter<DataT, Settings>::ExtrapolateLineXdX2(DataT z_out) const
337 {
338 DataT dz = (z_out - fTr.GetZ());
339 return std::pair(fTr.GetX() + fTr.GetTx() * dz, fTr.C00() + dz * (2 * fTr.C20() + dz * fTr.C22()));
340 }
341
342 template<typename DataT, class Settings>
343 inline std::pair<DataT, DataT> TrackKalmanFilter<DataT, Settings>::ExtrapolateLineYdY2(DataT z_out) const
344 {
345 DataT dz = (z_out - fTr.GetZ());
346 return std::pair(fTr.GetY() + fTr.GetTy() * dz, fTr.C11() + dz * (DataT(2.) * fTr.C31() + dz * fTr.C33()));
347 }
348
349 template<typename DataT, class Settings>
351 {
352 DataT dz = (z_out - fTr.GetZ());
353 return fTr.C10() + dz * (fTr.C21() + fTr.C30() + dz * fTr.C32());
354 }
355
356
357 template<typename DataT, class Settings>
359 {
360 // extrapolates the track to z
361 // - makes several steps when the distance is larger than fMaxExtrapolationStep
362 if (F.GetFieldType() == kf::EFieldType::Null) {
364 }
365 else {
366 DataT sgn = kf::utils::iif(fTr.GetZ() < z, DataT(1.), DataT(-1.));
367 DataT step = sgn * fMaxExtrapolationStep;
368 DataT zLastLoop = z - step;
369 DataT zNext = kf::utils::iif(fMask, fTr.GetZ() + step, z);
370 while (!kf::utils::isFull(sgn * (zLastLoop - zNext) <= DataT(0.))) {
371 ExtrapolateInOneStep(zNext, F);
372 zNext = kf::utils::iif(fMask, fTr.GetZ() + step, z);
373 }
375 }
376 }
377
378 template<typename DataT, class Settings>
380 {
381 if constexpr (!Settings::kDoFitTime) {
382 for (int j = 0; j < 5; j++) {
383 fTr.C(5, j) = DataT(0.);
384 }
385 for (int j = 0; j < 6; j++) {
386 fTr.C(6, j) = DataT(0.);
387 }
388 }
389 }
390
391
392} // namespace cbm::algo::kf
Magnetic flux density interpolation along the track vs. z-coordinate (header)
Definition of the KfMeasurementXy class.
#define _fvecalignment
Implementation selection for the SIMD utilities (VS or pseudo)
Magnetic field region, corresponding to a hit triplet.
Magnetic field manager class.
Definition KfField.h:272
The class describes a time measurement.
The class describes a 1D - measurement U in XY coordinate system.
The class describes a 2D - measurement (x, y) in XY coordinate system.
void FilterTime(DataT t, DataT dt2, const DataTmask &m)
filter the track with the time measurement
void SetMaxExtrapolationStep(double step)
set max extrapolation step [cm]
DataT ExtrapolateLineDxy(DataT z_out) const
DataT GetParticleMass() const
get the particle mass
void SetTrack(DataT z, const LinearizationFull< DataT > &lin)
void EnergyLossCorrection(DataT radThick, FitDirection direction)
void ExtrapolateNoField(DataT z)
extrapolate the track to the given Z assuming no magnetic field
void FilterTime(kf::MeasurementTime< DataT > mt)
filter the track with the time measurement
void FilterExtrapolatedXY(const kf::MeasurementXy< DataT > &m, const std::array< DataT, 5 > &Jx, const std::array< DataT, 5 > &Jy)
void SetLinearization(const Linearization_t &lin)
kf::TrackParam< DataT > fTr
track parameters
kf::utils::masktype< DataT > DataTmask
void SetOneEntry(const int i0, const TrackKalmanFilter &T1, const int i1)
Linearization_t fLinearisation
linearization parameters
void Filter1d(const kf::MeasurementU< DataT > &m)
filter the track with the 1d measurement
void FilterExtrapolatedY(const kf::MeasurementXy< DataT > &m, const std::array< DataT, 5 > &Jy)
void Extrapolate(DataT z, const kf::FieldRegion< DataT > &F)
static DataT ApproximateBetheBloch(DataT bg2)
Approximate mean energy loss with Bethe-Bloch formula.
DataT fMass
particle mass (muon mass by default)
void MultipleScattering(DataT radThick)
apply multiple scattering correction to the track
DataT GetMaxExtrapolationStep() const
get the particle mass
kf::utils::scaltype< DataT > DataTscal
void MultipleScattering(DataT radThick, DataT tx0, DataT ty0, DataT qp0)
apply multiple scattering correction to the track with the given Qp0
void SetParticleMass(DataT mass)
set particle mass for the fit
TrackKalmanFilter(const kf::TrackParam< T > &t)
kf::TrackParam< DataT > & Tr()
typename Settings::template LinearizationT< DataT > Linearization_t
void FilterExtrapolatedYChi2(const kf::MeasurementXy< DataT > &mL, const std::array< DataT, 5 > &jL, const kf::MeasurementXy< DataT > &mM, DataT msM, const kf::MeasurementXy< DataT > &mR, const std::array< DataT, 5 > &jR)
static std::tuple< DataT, DataT > GetChi2XChi2U(kf::MeasurementXy< DataT > m, DataT x, DataT y, DataT C00, DataT C10, DataT C11)
git two chi^2 components of the track fit to measurement
DataT GetParticleMass2() const
get the particle mass squared
void GuessTrack(const DataT &trackZ, const DataT hitX[], const DataT hitY[], const DataT hitZ[], const DataT hitT[], const DataT By[], const DataTmask hitW[], const DataTmask hitWtime[], int NHits)
fast guess of track parameterts based on its hits
void FilterXY(const kf::MeasurementXy< DataT > &m, bool skipUnmeasuredCoordinates=false)
filter the track with the XY measurement
void SetTrack(const kf::TrackParam< T > &t)
void ExtrapolateInOneStep(DataT z, const kf::FieldRegion< DataT > &Field)
void MultipleScatteringInThickMaterial(DataT radThick, DataT thickness, bool fDownstream)
apply multiple scattering correction in thick material to the track
std::pair< DataT, DataT > ExtrapolateLineXdX2(DataT z_out) const
void MeasureVelocityWithQp()
measure the track velocity with the track Qp and the mass
std::pair< DataT, DataT > ExtrapolateLineYdY2(DataT z_out) const
DataT fMaxExtrapolationStep
max extrapolation step [cm]
void FilterVi(DataT vi)
filter the inverse speed
DataTmask fMask
mask of active elements in simd vectors
void ExtrapolateLineInField(DataT z_out, const kf::FieldRegion< DataT > &F)
extrapolate the track to the given Z using linearization at the straight line
void GetMeasurementModelAtZline(DataT zm, const kf::FieldRegion< DataT > &Field, std::array< DataT, 5 > &Jx, std::array< DataT, 5 > &Jy) const
extrapolate track as a line, return the extrapolated X, Y and the Jacobians
TrackKalmanFilter(const kf::TrackParam< DataT > &t)
TrackParam classes of different types.
static void CopyEntries(TdataA &a, int ia, const TdataB &b, int ib)
Definition KfUtils.h:181
typename std::conditional< std::is_same< T, fvec >::value, fmask, bool >::type masktype
Definition KfUtils.h:27
typename std::conditional< std::is_same< T, fvec >::value, fscal, T >::type scaltype
Definition KfUtils.h:24
fvec iif(const fmask &m, const fvec &t, const fvec &f)
Definition KfUtils.h:29
bool isFull(const T &m)
Definition KfUtils.h:45
FitDirection operator!(FitDirection d)
@ Y
Fit the time component.
Definition KfDefs.h:134
@ Null
No magnetic field.
Definition KfDefs.h:128
fscal sgn(fscal x)
LinearizationT_< T > LinearizationT
T y
y coordinate at the linearization point
T ty
ty = py/pz at the linearization point
T x
x coordinate at the linearization point
T qp
qp = q/pz at the linearization point
T vi
inverse speed at the linearization point
LinearizationFull(const TrackParam< T > p)
T time
time at the linearization point
T tx
tx = px/pz at the linearization point
T qp
qp = q/pz at the linearization point
LinearizationQp(const TrackParam< T > p)