Belle II Software  release-08-01-10
CDCMCMap.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/trackFindingCDC/mclookup/CDCMCMap.h>
9 
10 #include <framework/datastore/StoreArray.h>
11 
12 #include <cdc/dataobjects/CDCHit.h>
13 #include <cdc/dataobjects/CDCSimHit.h>
14 #include <mdst/dataobjects/MCParticle.h>
15 
16 #include <iostream>
17 
18 using namespace Belle2;
19 using namespace TrackFindingCDC;
20 
21 namespace {
22  template <class MapType>
23  void print_map(const MapType& m)
24  {
25  using const_iterator = typename MapType::const_iterator;
26  for (const_iterator iter = m.begin(), iend = m.end(); iter != iend; ++iter) {
27  std::cout << iter->first << "-->" << iter->second << std::endl;
28  }
29  }
30 }
31 
33 {
34  B2DEBUG(25, "In CDCMCMap::clear()");
35  m_simHitsByHit.clear();
36 
37  m_hitsByMCParticle.clear();
38  m_simHitsByMCParticle.clear();
39 
42 }
43 
45 {
46  B2DEBUG(25, "In CDCMCMap::fill()");
47  clear();
48 
52 
55 
56  B2DEBUG(25, "m_simHitsByHit.size(): " << m_simHitsByHit.size());
57 
58  B2DEBUG(25, "m_hitsByMCParticle.size(): " << m_hitsByMCParticle.size());
59  B2DEBUG(25, "m_simHitsByMCParticle.size(): " << m_simHitsByMCParticle.size());
60 
61  B2DEBUG(25, "m_reassignedSecondaryHits.size(): " << m_reassignedSecondaryHits.size());
62  B2DEBUG(25, "m_reassignedSecondarySimHits.size(): " << m_reassignedSecondarySimHits.size());
63 }
64 
66 {
67  StoreArray<CDCSimHit> simHits;
68  StoreArray<CDCHit> hits;
69 
70  // Pickup an iterator for hinted insertion
71  auto itInsertHint = m_simHitsByHit.end();
72 
73  for (const CDCSimHit& simHit : simHits) {
74  const CDCSimHit* ptrSimHit = &simHit;
75  RelationVector<CDCHit> relatedHits = simHit.getRelationsTo<CDCHit>();
76 
77  int nRelatedHits = relatedHits.size();
78  if (nRelatedHits > 1) {
79  B2WARNING("CDCSimHit as more than one related CDCHit - reorganize the mapping");
80  }
81 
82  for (const CDCHit& hit : relatedHits) {
83  const CDCHit* ptrHit = &hit;
84 
85  if (m_simHitsByHit.count(ptrHit) != 0) {
86  B2WARNING("CDCHit as more than one related CDCSimHit - reorganize the mapping");
87  }
88 
89  itInsertHint = m_simHitsByHit.insert(itInsertHint, {ptrHit, ptrSimHit});
90  }
91  }
92 
93  // Check if every hit has a corresponding simulated hit
94  for (const CDCHit& hit : hits) {
95  const CDCHit* ptrHit = &hit;
96 
97  if (m_simHitsByHit.count(ptrHit) == 0) {
98  B2WARNING("CDCHit has no related CDCSimHit in CDCMCMap::fill()");
99  }
100  }
101 }
102 
104 {
105  StoreArray<CDCHit> hits;
106 
107  std::map<const MCParticle*, std::vector<const CDCSimHit*>> primarySimHitsByMCParticle;
108 
109  for (const CDCHit& hit : hits) {
110  const CDCHit* ptrHit = &hit;
111  RelationVector<MCParticle> relatedMCParticles = hit.getRelationsFrom<MCParticle>();
112 
113  const int nRelatedMCParticles = relatedMCParticles.size();
114 
115  if (nRelatedMCParticles == 0 and not isBackground(ptrHit)) {
116  B2WARNING("CDCHit has no related MCParticle but CDCHit indicates that it is no "
117  "background in CDCMCMap::fill()");
118  }
119 
120  if (nRelatedMCParticles > 1) {
121  B2WARNING("CDCHit as more than one related MCParticle - reorganize the mapping");
122  }
123 
124  // Pickup an iterator for hinted insertion
125  auto itInsertHint = m_hitsByMCParticle.end();
126  for (int iRelatedMCParticle = 0; iRelatedMCParticle < nRelatedMCParticles; ++iRelatedMCParticle) {
127  const MCParticle* ptrMCParticle = relatedMCParticles[iRelatedMCParticle];
128  double weight = relatedMCParticles.weight(iRelatedMCParticle);
129 
130  if (indicatesReassignedSecondary(weight)) {
131  m_reassignedSecondaryHits.insert(ptrHit);
132  } else {
133  const CDCSimHit* ptrSimHit = ptrHit->getRelatedFrom<CDCSimHit>();
134  if (ptrMCParticle->isPrimaryParticle() and ptrSimHit) {
135  primarySimHitsByMCParticle[ptrMCParticle].push_back(ptrSimHit);
136  }
137  }
138 
139  itInsertHint = m_hitsByMCParticle.insert(itInsertHint, {ptrMCParticle, ptrHit});
140  }
141  }
142 
143  // Check time ordering of primary hits
144  int nSortedIncorretly = 0;
145  auto lessFlightTime = [](const CDCSimHit * lhs, const CDCSimHit * rhs) {
146  return lhs->getFlightTime() < rhs->getFlightTime();
147  };
148 
149  auto lessArrayIndex = [](const CDCSimHit * lhs, const CDCSimHit * rhs) -> bool {
150  return lhs->getArrayIndex() < rhs->getArrayIndex();
151  };
152 
153  for (std::pair<const MCParticle* const, std::vector<const CDCSimHit*>>&
154  primarySimHitsForMCParticle : primarySimHitsByMCParticle) {
155 
156  const MCParticle* ptrMCParticle = primarySimHitsForMCParticle.first;
157  std::vector<const CDCSimHit*>& simHits = primarySimHitsForMCParticle.second;
158  std::sort(simHits.begin(), simHits.end(), lessArrayIndex);
159  auto itSorted = std::is_sorted_until(simHits.begin(), simHits.end(), lessFlightTime);
160  if (itSorted != simHits.end()) {
161  ++nSortedIncorretly;
162  B2DEBUG(25,
163  "CDCSimHits for MCParticle " << ptrMCParticle->getArrayIndex()
164  << " only sorted correctly up to hit number "
165  << std::distance(simHits.begin(), itSorted));
166  --itSorted;
167  B2DEBUG(25,
168  "Between wire " << (*itSorted)->getWireID() << " " << (*itSorted)->getFlightTime()
169  << "ns "
170  << (*itSorted)->getArrayIndex());
171  ++itSorted;
172  B2DEBUG(25,
173  "and wire " << (*itSorted)->getWireID() << " " << (*itSorted)->getFlightTime()
174  << "ns "
175  << (*itSorted)->getArrayIndex());
176  }
177  }
178  if (nSortedIncorretly) {
179  B2WARNING("(BII-2136) CDCSimHits for "
180  << nSortedIncorretly
181  << " primary mc particles are not sorted correctly by their time of flight");
182  }
183 }
184 
186 {
187  StoreArray<CDCSimHit> simHits;
188 
189  for (const CDCSimHit& simHit : simHits) {
190  const CDCSimHit* ptrSimHit = &simHit;
191  RelationVector<MCParticle> relatedMCParticles = simHit.getRelationsFrom<MCParticle>();
192 
193  const int nRelatedMCParticles = relatedMCParticles.size();
194 
195  if (nRelatedMCParticles == 0 and not isBackground(ptrSimHit)) {
196  B2WARNING("CDCSimHit has no related MCParticle but CDCSimHit indicates that it is no "
197  "background in CDCMCMap::fill()");
198  }
199 
200  if (nRelatedMCParticles > 1) {
201  B2WARNING("CDCSimHit as more than one related MCParticle - reorganize the mapping");
202  }
203 
204  // Pickup an iterator for hinted insertion
205  auto itInsertHint = m_simHitsByMCParticle.end();
206  for (int iRelatedMCParticle = 0; iRelatedMCParticle < nRelatedMCParticles; ++iRelatedMCParticle) {
207  const MCParticle* ptrMCParticle = relatedMCParticles[iRelatedMCParticle];
208  double weight = relatedMCParticles.weight(iRelatedMCParticle);
209 
210  if (indicatesReassignedSecondary(weight)) {
211  m_reassignedSecondarySimHits.insert(ptrSimHit);
212  }
213 
214  itInsertHint = m_simHitsByMCParticle.insert(itInsertHint, {ptrMCParticle, ptrSimHit});
215  }
216  }
217 }
218 
220 {
221  StoreArray<CDCHit> hits;
222 
223  for (const CDCHit& hit : hits) {
224  const CDCHit* ptrHit = &hit;
225 
226  const CDCSimHit* ptrSimHit = getSimHit(ptrHit);
227  const MCParticle* ptrMCParticle = getMCParticle(ptrHit);
228 
229  const MCParticle* ptrMCParticleFromSimHit = getMCParticle(ptrSimHit);
230 
231  if (ptrMCParticle != ptrMCParticleFromSimHit) {
232  B2WARNING("MCParticle from CDCHit and MCParticle from related CDCSimHit mismatch in "
233  "CDCMCMap::validateRelations()");
234  }
235  }
236 }
237 
239 {
240  for (const CDCHit* ptrHit : m_reassignedSecondaryHits) {
241 
242  const CDCSimHit* ptrSimHit = getSimHit(ptrHit);
243  if (not isReassignedSecondary(ptrSimHit)) {
244  B2WARNING("CDCHit is reassigned secondary but related CDCSimHit is not.");
245  }
246  }
247 }
248 
249 MayBePtr<const CDCSimHit> CDCMCMap::getSimHit(const CDCHit* hit) const
250 {
251  return hit ? hit->getRelated<CDCSimHit>() : nullptr;
252 }
253 
254 MayBePtr<const CDCHit> CDCMCMap::getHit(const CDCSimHit* simHit) const
255 {
256  return simHit ? simHit->getRelated<CDCHit>() : nullptr;
257 }
258 
259 bool CDCMCMap::isBackground(const CDCSimHit* simHit) const
260 {
261  return simHit ? simHit->getBackgroundTag() != BackgroundMetaData::bg_none : false;
262 }
263 
264 bool CDCMCMap::isBackground(const CDCHit* hit) const
265 {
266  return isBackground(getSimHit(hit));
267 }
268 
269 MayBePtr<const MCParticle> CDCMCMap::getMCParticle(const CDCHit* hit) const
270 {
271  return hit ? hit->getRelated<MCParticle>() : nullptr;
272 }
273 
274 MayBePtr<const MCParticle> CDCMCMap::getMCParticle(const CDCSimHit* simHit) const
275 {
276  return simHit ? simHit->getRelated<MCParticle>() : nullptr;
277 }
Class containing the result of the unpacker in raw data and the result of the digitizer in simulation...
Definition: CDCHit.h:40
Example Detector.
Definition: CDCSimHit.h:21
double getFlightTime() const
The method to get flight time.
Definition: CDCSimHit.h:184
A Class to store the Monte Carlo particle information.
Definition: MCParticle.h:32
int getArrayIndex() const
Get 0-based index of the particle in the corresponding MCParticle list.
Definition: MCParticle.h:244
Class for type safe access to objects that are referred to in relations.
size_t size() const
Get number of relations.
float weight(int index) const
Get weight with index.
int getArrayIndex() const
Returns this object's array index (in StoreArray), or -1 if not found.
FROM * getRelatedFrom(const std::string &name="", const std::string &namedRelation="") const
Get the object from which this object has a relation.
T * getRelated(const std::string &name="", const std::string &namedRelation="") const
Get the object to or from which this object has a relation.
virtual unsigned short getBackgroundTag() const
Get background tag.
Definition: SimHitBase.h:46
Accessor to arrays stored in the data store.
Definition: StoreArray.h:113
MayBePtr< const CDCSimHit > getSimHit(const CDCHit *hit) const
Seeks the CDCSimHit related to the CDCHit.
Definition: CDCMCMap.cc:249
std::set< const CDCHit * > m_reassignedSecondaryHits
The set of reassigned secondary CDCHits.
Definition: CDCMCMap.h:162
void fillSimHitByHitMap()
Retrieve the relations array from CDCSimHits to CDCHits and fill it in to the local map which does th...
Definition: CDCMCMap.cc:65
std::set< const CDCSimHit * > m_reassignedSecondarySimHits
The set of reassigned secondary CDCSimHits.
Definition: CDCMCMap.h:165
std::multimap< const CDCHit *, const CDCSimHit * > m_simHitsByHit
Memory for a one to one relation from CDCHit to CDCSimHits.
Definition: CDCMCMap.h:153
void validateRelations() const
Checks if the relations CDCHit -> MCParticle and CDCHit -> CDCSimHit -> MCParticle commute.
Definition: CDCMCMap.cc:219
void fillMCParticleByHitMap()
Retrieve the relations array from MCParticle to CDCHits and fill it in to the local map which does th...
Definition: CDCMCMap.cc:103
bool isBackground(const CDCSimHit *simHit) const
Indicates if the CDCSimHit is considered background.
Definition: CDCMCMap.cc:259
static bool indicatesReassignedSecondary(double weight)
Indicate if the given weight suggests that the corresponding hit to MCParticle relation has been redi...
Definition: CDCMCMap.h:52
MayBePtr< const CDCHit > getHit(const CDCSimHit *simHit) const
Seeks the CDCHit related to the CDCSimHit - nullptr if no CDCHit is related.
Definition: CDCMCMap.cc:254
void fillMCParticleBySimHitMap()
Retrieve the relations array from MCParticle to CDCSimHits and fill it in to the local map which does...
Definition: CDCMCMap.cc:185
MayBePtr< const MCParticle > getMCParticle(const CDCHit *hit) const
Seeks the MCParticle related to the CDCHit.
Definition: CDCMCMap.cc:269
std::multimap< const MCParticle *, const CDCHit * > m_hitsByMCParticle
Memory for a one to n relation from MCParticles to CDCHit.
Definition: CDCMCMap.h:156
bool isReassignedSecondary(const CDCSimHit *ptrSimHit) const
Indicates if the CDCSimHit has been reassigned to a primary MCParticle.
Definition: CDCMCMap.h:110
std::multimap< const MCParticle *, const CDCSimHit * > m_simHitsByMCParticle
Memory for a one to n relation from MCParticles to CDCSimHit.
Definition: CDCMCMap.h:159
void clear()
Clear all information from the former event.
Definition: CDCMCMap.cc:32
void validateReassignedSecondaries() const
Checks if each CDCHit is marked as reassigned secondary is related to a reassigned secondary CDCSimHi...
Definition: CDCMCMap.cc:238
void fill()
Fill the Monte Carlo information retrieved from the DataStore into the local multimaps.
Definition: CDCMCMap.cc:44
bool isPrimaryParticle() const
Check if particle is a primary particle which was created by the generator (and not,...
Definition: MCParticle.h:595
Abstract base class for different kinds of events.