Belle II Software  release-06-01-15
TrackBuilder.cc
1 /**************************************************************************
2  * basf2 (Belle II Analysis Software Framework) *
3  * Author: The Belle II Collaboration *
4  * *
5  * See git log for contributors and copyright holders. *
6  * This file is licensed under LGPL-3.0, see LICENSE.md. *
7  **************************************************************************/
8 #include <tracking/trackFitting/trackBuilder/factories/TrackBuilder.h>
9 
10 
11 #include <framework/datastore/StoreArray.h>
12 #include <mdst/dataobjects/MCParticle.h>
13 #include <mdst/dataobjects/HitPatternVXD.h>
14 #include <mdst/dataobjects/HitPatternCDC.h>
15 #include <mdst/dataobjects/Track.h>
16 #include <mdst/dataobjects/TrackFitResult.h>
17 #include <cdc/dataobjects/CDCRecoHit.h>
18 #include <pxd/reconstruction/PXDRecoHit.h>
19 #include <svd/reconstruction/SVDRecoHit.h>
20 #include <svd/reconstruction/SVDRecoHit2D.h>
21 #include <tracking/dataobjects/RecoTrack.h>
22 
23 #include <TVector3.h>
24 #include <TMatrixDSym.h>
25 
26 #include <genfit/FitStatus.h>
27 #include <genfit/KalmanFitterInfo.h>
28 #include <genfit/Track.h>
29 #include <genfit/TrackPoint.h>
30 #include <genfit/MeasuredStateOnPlane.h>
31 #include <genfit/FieldManager.h>
32 
33 using namespace Belle2;
34 
36  const bool useClosestHitToIP, const bool useBFieldAtHit)
37 {
40 
41  const auto& trackReps = recoTrack.getRepresentations();
42  B2DEBUG(100, trackReps.size() << " track representations available.");
43  Track newTrack(recoTrack.getQualityIndicator());
44 
45  bool repAlreadySet = false;
46  unsigned int repIDPlusOne = 0;
47  for (const auto& trackRep : trackReps) {
48  repIDPlusOne++;
49 
50  // Check if the fitted particle type is in our charged stable set.
51  const Const::ParticleType particleType(std::abs(trackRep->getPDG()));
52  if (not Const::chargedStableSet.contains(particleType)) {
53  B2DEBUG(100, "Track fitted with hypothesis that is not a ChargedStable (PDG code = " << particleType.getPDGCode() << ")");
54  continue;
55  }
56 
57  // Check if the fit worked.
58  if (not recoTrack.wasFitSuccessful(trackRep)) {
59  B2DEBUG(100, "The fit with the given track representation (" << std::abs(trackRep->getPDG()) <<
60  ") was not successful. Skipping ...");
61  continue;
62  }
63 
64  if (not repAlreadySet) {
65  RecoTrackGenfitAccess::getGenfitTrack(recoTrack).setCardinalRep(repIDPlusOne - 1);
66  repAlreadySet = true;
67  }
68 
69  // Extrapolate the tracks to the perigee.
71  try {
72  if (useClosestHitToIP) {
73  msop = recoTrack.getMeasuredStateOnPlaneClosestTo(TVector3(0, 0, 0), trackRep);
74  } else {
75  msop = recoTrack.getMeasuredStateOnPlaneFromFirstHit(trackRep);
76  }
77  } catch (genfit::Exception& exception) {
78  B2WARNING(exception.what());
79  continue;
80  }
81 
82  genfit::MeasuredStateOnPlane extrapolatedMSoP = msop;
83  try {
84  extrapolatedMSoP.extrapolateToLine(m_beamSpot, m_beamAxis);
85  } catch (...) {
86  B2WARNING("Could not extrapolate the fit result for pdg " << particleType.getPDGCode() <<
87  " to the perigee point. Why, I don't know.");
88  continue;
89  }
90 
91  // Build track fit result.
92 
93  TVector3 poca(0., 0., 0.);
94  TVector3 dirInPoca(0., 0., 0.);
95  TMatrixDSym cov(6);
96  extrapolatedMSoP.getPosMomCov(poca, dirInPoca, cov);
97  B2DEBUG(149, "Point of closest approach: " << poca.x() << " " << poca.y() << " " << poca.z());
98  B2DEBUG(149, "Track direction in POCA: " << dirInPoca.x() << " " << dirInPoca.y() << " " << dirInPoca.z());
99 
100  const int charge = recoTrack.getTrackFitStatus(trackRep)->getCharge();
101  const double pValue = recoTrack.getTrackFitStatus(trackRep)->getPVal();
102  const int nDF = recoTrack.getTrackFitStatus(trackRep)->getNdf();
103 
104  double Bx, By, Bz; // In cgs units
105  if (useBFieldAtHit) {
106  const TVector3& hitPosition = msop.getPos();
107  genfit::FieldManager::getInstance()->getFieldVal(hitPosition.X(), hitPosition.Y(), hitPosition.Z(), Bx, By, Bz);
108  } else {
109  genfit::FieldManager::getInstance()->getFieldVal(poca.X(), poca.Y(), poca.Z(), Bx, By, Bz);
110  }
111  Bz = Bz / 10.; // In SI-Units
112 
113  const uint64_t hitPatternCDCInitializer = getHitPatternCDCInitializer(recoTrack);
114  const uint32_t hitPatternVXDInitializer = getHitPatternVXDInitializer(recoTrack);
115 
116  const auto newTrackFitResult = trackFitResults.appendNew(
117  poca, dirInPoca, cov, charge, particleType, pValue, Bz,
118  hitPatternCDCInitializer, hitPatternVXDInitializer, nDF
119  );
120 
121  const int newTrackFitResultArrayIndex = newTrackFitResult->getArrayIndex();
122  newTrack.setTrackFitResultIndex(particleType, newTrackFitResultArrayIndex);
123  }
124 
125  B2DEBUG(100, "Number of fitted hypothesis = " << newTrack.getNumberOfFittedHypotheses());
126  if (newTrack.getNumberOfFittedHypotheses() > 0) {
127  Track* addedTrack = tracks.appendNew(newTrack);
128  addedTrack->addRelationTo(&recoTrack);
129  const auto& mcParticleWithWeight = recoTrack.getRelatedToWithWeight<MCParticle>(m_mcParticleColName);
130  const MCParticle* mcParticle = mcParticleWithWeight.first;
131  if (mcParticle) {
132  B2DEBUG(200, "Relation to MCParticle set.");
133  addedTrack->addRelationTo(mcParticle, mcParticleWithWeight.second);
134  } else {
135  B2DEBUG(200, "Relation to MCParticle not set. No related MCParticle to RecoTrack.");
136  }
137  return true;
138  } else {
139  B2DEBUG(200, "Relation to MCParticle not set. No related MCParticle to RecoTrack.");
140  }
141  return true;
142 }
143 
144 
146 {
147  HitPatternVXD hitPatternVXD;
148 
149  const auto& hitPointsWithMeasurements = recoTrack.getHitPointsWithMeasurement();
150  int nNotFittedVXDhits = 0;
151 
152  for (const auto& trackPoint : hitPointsWithMeasurements) {
153 
154  for (size_t measurementId = 0; measurementId < trackPoint->getNumRawMeasurements(); measurementId++) {
155 
156  genfit::AbsMeasurement* absMeas = trackPoint->getRawMeasurement(measurementId);
157  genfit::KalmanFitterInfo* kalmanInfo = trackPoint->getKalmanFitterInfo();
158 
159  if (kalmanInfo) {
160  const double weight = kalmanInfo->getWeights().at(measurementId);
161  if (weight == 0)
162  continue;
163  } else {
164  ++nNotFittedVXDhits;
165  continue;
166  }
167 
168  PXDRecoHit* pxdHit = dynamic_cast<PXDRecoHit*>(absMeas);
169  if (pxdHit) {
170  const int layerNumber = pxdHit->getSensorID().getLayerNumber();
171  const int currentHits = hitPatternVXD.getPXDLayer(layerNumber, HitPatternVXD::PXDMode::normal);
172  hitPatternVXD.setPXDLayer(layerNumber, currentHits + 1, HitPatternVXD::PXDMode::normal);
173  }
174 
175  SVDRecoHit* svdHit = dynamic_cast<SVDRecoHit*>(absMeas);
176  SVDRecoHit2D* svdHit2D = dynamic_cast<SVDRecoHit2D*>(absMeas);
177  if (svdHit2D) {
178  const int layerNumber = svdHit2D->getSensorID().getLayerNumber();
179  const auto& currentHits = hitPatternVXD.getSVDLayer(layerNumber);
180  hitPatternVXD.setSVDLayer(layerNumber, currentHits.first + 1, currentHits.second + 1);
181  } else if (svdHit) {
182  const int layerNumber = svdHit->getSensorID().getLayerNumber();
183  const auto& currentHits = hitPatternVXD.getSVDLayer(layerNumber);
184 
185  if (svdHit->isU())
186  hitPatternVXD.setSVDLayer(layerNumber, currentHits.first + 1, currentHits.second);
187  else
188  hitPatternVXD.setSVDLayer(layerNumber, currentHits.first , currentHits.second + 1);
189  }
190 
191  }
192  }
193 
194  if (nNotFittedVXDhits > 0) {
195  B2DEBUG(100, " No KalmanFitterInfo associated to some TrackPoints with VXD hits, not filling the HitPatternVXD");
196  B2DEBUG(100, nNotFittedVXDhits << " had no FitterInfo");
197  }
198  return hitPatternVXD.getInteger();
199 }
200 
201 
203 {
204  HitPatternCDC hitPatternCDC;
205 
206  int nCDChits = 0;
207  int nNotFittedCDChits = 0;
208 
209  const auto& hitPointsWithMeasurements = recoTrack.getHitPointsWithMeasurement();
210 
211  for (const auto& trackPoint : hitPointsWithMeasurements) {
212 
213  for (size_t measurementId = 0; measurementId < trackPoint->getNumRawMeasurements(); measurementId++) {
214 
215  genfit::AbsMeasurement* absMeas = trackPoint->getRawMeasurement(measurementId);
216  genfit::KalmanFitterInfo* kalmanInfo = trackPoint->getKalmanFitterInfo();
217 
218  if (kalmanInfo) {
219  const double weight = kalmanInfo->getWeights().at(measurementId);
220  if (weight == 0)
221  continue;
222  } else {
223  ++nNotFittedCDChits;
224  continue;
225  }
226 
227  CDCRecoHit* cdcHit = dynamic_cast<CDCRecoHit*>(absMeas);
228 
229  if (cdcHit) {
230  WireID wire = cdcHit->getWireID();
231  hitPatternCDC.setLayer(wire.getICLayer());
232  nCDChits++;
233  }
234  }
235 
236  }
237  if (nNotFittedCDChits > 0) {
238  B2DEBUG(100, " No KalmanFitterInfo associated to some TrackPoints with CDC hits, not filling the HitPatternCDC");
239  B2DEBUG(100, nNotFittedCDChits << " out of " << nCDChits << " had no FitterInfo");
240  }
241  hitPatternCDC.setNHits(nCDChits);
242 
243  return hitPatternCDC.getInteger();
244 
245 }
246 
247 
This class is used to transfer CDC information to the track fit.
Definition: CDCRecoHit.h:32
WireID getWireID() const
Getter for WireID object.
Definition: CDCRecoHit.h:49
The ParticleType class for identifying different particle types.
Definition: Const.h:289
int getPDGCode() const
PDG code.
Definition: Const.h:354
static const ParticleSet chargedStableSet
set of charged stable particles
Definition: Const.h:499
Hit pattern of CDC hits within a track.
Definition: HitPatternCDC.h:35
void setNHits(unsigned short nHits)
Sets the 8 MSBs to the total number of hits in the CDC.
void setLayer(const unsigned short layer)
Set bit corresponding to layer to true.
ULong64_t getInteger() const
Getter for underlying integer type.
Hit pattern of the VXD within a track.
Definition: HitPatternVXD.h:37
unsigned int getInteger() const
Getter for the underlying integer.
Definition: HitPatternVXD.h:58
void setSVDLayer(const unsigned short layerId, unsigned short uHits, unsigned short vHits)
Set the number of hits in a specific layer of the SVD.
void setPXDLayer(const unsigned short layerId, unsigned short nHits, const PXDMode &mode=PXDMode::normal)
Set the number of hits in a specific layer of the PXD.
unsigned short getPXDLayer(const unsigned short layerId, const PXDMode &mode=PXDMode::normal) const
Get the number of hits in a specific layer of the PXD.
std::pair< const unsigned short, const unsigned short > getSVDLayer(const unsigned short layerId) const
Get the number of hits in a specific layer of the SVD.
A Class to store the Monte Carlo particle information.
Definition: MCParticle.h:32
PXDRecoHit - an extended form of PXDCluster containing geometry information.
Definition: PXDRecoHit.h:49
VxdID getSensorID() const
Get the compact ID.
Definition: PXDRecoHit.h:101
static genfit::Track & getGenfitTrack(RecoTrack &recoTrack)
Give access to the RecoTrack's genfit::Track.
Definition: RecoTrack.cc:396
This is the Reconstruction Event-Data Model Track.
Definition: RecoTrack.h:76
const genfit::FitStatus * getTrackFitStatus(const genfit::AbsTrackRep *representation=nullptr) const
Return the track fit status for the given representation or for the cardinal one. You are not allowed...
Definition: RecoTrack.h:536
bool wasFitSuccessful(const genfit::AbsTrackRep *representation=nullptr) const
Returns true if the last fit with the given representation was successful.
Definition: RecoTrack.cc:333
const std::vector< genfit::TrackPoint * > & getHitPointsWithMeasurement() const
Return a list of measurements and track points, which can be used e.g. to extrapolate....
Definition: RecoTrack.h:606
const std::vector< genfit::AbsTrackRep * > & getRepresentations() const
Return a list of track representations. You are not allowed to modify or delete them!
Definition: RecoTrack.h:553
float getQualityIndicator() const
Get the quality index attached to this RecoTrack given by one of the reconstruction algorithms....
Definition: RecoTrack.h:729
const genfit::MeasuredStateOnPlane & getMeasuredStateOnPlaneClosestTo(const TVector3 &closestPoint, const genfit::AbsTrackRep *representation=nullptr)
Return genfit's MasuredStateOnPlane, that is closest to the given point useful for extrapolation of m...
Definition: RecoTrack.cc:418
const genfit::MeasuredStateOnPlane & getMeasuredStateOnPlaneFromFirstHit(const genfit::AbsTrackRep *representation=nullptr) const
Return genfit's MeasuredStateOnPlane for the first hit in a fit useful for extrapolation of measureme...
Definition: RecoTrack.cc:586
void addRelationTo(const RelationsInterface< BASE > *object, float weight=1.0, const std::string &namedRelation="") const
Add a relation from this object to another object (with caching).
std::pair< TO *, float > getRelatedToWithWeight(const std::string &name="", const std::string &namedRelation="") const
Get first related object & weight of relation pointing to an array.
SVDRecoHit - an extended form of SVDHit containing geometry information.
Definition: SVDRecoHit2D.h:46
VxdID getSensorID() const
Get the compact ID.
Definition: SVDRecoHit2D.h:100
SVDRecoHit - an extended form of SVDHit containing geometry information.
Definition: SVDRecoHit.h:47
bool isU() const
Is the coordinate u or v?
Definition: SVDRecoHit.h:91
VxdID getSensorID() const
Get the compact ID.
Definition: SVDRecoHit.h:82
Accessor to arrays stored in the data store.
Definition: StoreArray.h:113
T * appendNew()
Construct a new T object at the end of the array.
Definition: StoreArray.h:246
bool storeTrackFromRecoTrack(RecoTrack &recoTrack, const bool useClosestHitToIP=false, const bool useBFieldAtHit=false)
Stores a Belle2 Track from a Reco Track.
Definition: TrackBuilder.cc:35
static uint32_t getHitPatternVXDInitializer(const RecoTrack &recoTrack)
Get the HitPattern in the VXD.
TVector3 m_beamAxis
Extrapolation target, positive z direction.
Definition: TrackBuilder.h:98
std::string m_trackColName
TrackColName (output).
Definition: TrackBuilder.h:90
std::string m_mcParticleColName
MCParticleColName (input, optional).
Definition: TrackBuilder.h:94
std::string m_trackFitResultColName
TrackFitResultColName (output).
Definition: TrackBuilder.h:92
TVector3 m_beamSpot
Extrapolation target, origin.
Definition: TrackBuilder.h:96
static uint64_t getHitPatternCDCInitializer(const RecoTrack &recoTrack)
Get the HitPattern in the CDC.
Class that bundles various TrackFitResults.
Definition: Track.h:25
void setTrackFitResultIndex(const Const::ChargedStable &chargedStable, short index)
Set an index (for positive values) or unavailability-code (with negative values) for a specific mass ...
Definition: Track.h:94
unsigned int getNumberOfFittedHypotheses() const
Returns the number of fitted hypothesis which are stored in this track.
Definition: Track.cc:29
baseType getLayerNumber() const
Get the layer id.
Definition: VxdID.h:96
Class to identify a wire inside the CDC.
Definition: WireID.h:34
unsigned short getICLayer() const
Getter for continuous layer numbering.
Definition: WireID.cc:24
Contains the measurement and covariance in raw detector coordinates.
Exception class for error handling in GENFIT (provides storage for diagnostic information)
Definition: Exception.h:48
virtual const char * what() const noexcept
Standard error message handling for exceptions. use like "std::cerr << e.what();".
Definition: Exception.cc:52
TVector3 getFieldVal(const TVector3 &position)
This does NOT use the cache!
Definition: FieldManager.h:63
static FieldManager * getInstance()
Get singleton instance.
Definition: FieldManager.h:119
virtual double getPVal() const
Get the p value of the fit.
Definition: FitStatus.h:128
double getCharge() const
Get the fitted charge.
Definition: FitStatus.h:118
double getNdf() const
Get the degrees of freedom of the fit.
Definition: FitStatus.h:122
Collects information needed and produced by a AbsKalmanFitter implementations and is specific to one ...
std::vector< double > getWeights() const
Get weights of measurements.
#StateOnPlane with additional covariance matrix.
Abstract base class for different kinds of events.