ATLAS Offline Software
MuonHoughTransformTester.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3 */
4 
6 #include "GaudiKernel/SystemOfUnits.h"
15 #include "Acts/Utilities/Enumerate.hpp"
16 #include "GaudiKernel/PhysicalConstants.h"
17 
19 
20 
21 namespace {
22  constexpr double c_inv = 1. /Gaudi::Units::c_light;
23 }
24 
25 
26 namespace MuonValR4 {
27  using namespace MuonR4;
28  using namespace MuonVal;
30  using simHitSet = std::unordered_set<const xAOD::MuonSimHit*>;
31  unsigned int countMatched(const simHitSet& truthHits,
32  const simHitSet& recoHits) {
33  unsigned int matched{0};
34  for (const xAOD::MuonSimHit* reco : recoHits) {
35  matched += truthHits.count(reco);
36  }
37  return matched;
38  }
39  unsigned int countMatched(const xAOD::MuonSegment* truthSeg,
40  const MuonR4::SegmentSeed* seed) {
41  return truthSeg ? countMatched(getMatchingSimHits(*truthSeg), getMatchingSimHits(*seed)) : 0;
42  }
43  unsigned int countMatched(const xAOD::MuonSegment* truthSeg,
44  const MuonR4::Segment* segment) {
45  return truthSeg ? countMatched(getMatchingSimHits(*truthSeg), getMatchingSimHits(*segment)) : 0;
46  }
48  template <class SpType>
49  bool isPrecHit(const SpType& sp) {
50  return sp.type() == xAOD::UncalibMeasType::MdtDriftCircleType ||
52  (sp.type() == xAOD::UncalibMeasType::sTgcStripType && sp.measuresEta());
53  }
54 
56  ATH_CHECK(m_geoCtxKey.initialize());
57 
58  {
59  int infoOpts = 0;
60  if (m_isMC) infoOpts = EventInfoBranch::isMC;
61  m_tree.addBranch(std::make_unique<EventInfoBranch>(m_tree, infoOpts));
62  }
63  ATH_CHECK(m_truthSegmentKey.initialize(!m_truthSegmentKey.empty()));
65  ATH_CHECK(m_inSegmentKeys.initialize());
66  ATH_CHECK(m_inHoughSegmentSeedKeys.initialize());
67  ATH_CHECK(m_spKey.initialize(m_writeSpacePoints));
68  if (m_writeSpacePoints) {
69  m_spTester = std::make_unique<SpacePointTesterModule>(m_tree, m_spKey.key(), msgLevel());
70  m_tree.addBranch(m_spTester);
71  } else {
72  m_tree.disableBranch(m_spMatchedToPattern.name());
73  m_tree.disableBranch(m_spMatchedToSegment.name());
74  }
75  ATH_CHECK(m_tree.init(this));
76  ATH_CHECK(m_idHelperSvc.retrieve());
77  ATH_CHECK(detStore()->retrieve(m_detMgr));
78 
79  ATH_CHECK(m_visionTool.retrieve(EnableTool{!m_visionTool.empty()}));
80  ATH_MSG_DEBUG("Succesfully initialised");
81  return StatusCode::SUCCESS;
82  }
83 
84 
86  const xAOD::MuonSegment& truthSeg,
87  const MuonR4::Segment& recoSeg) const{
88  unsigned int same{0};
89  const auto [truPos, truDir] = SegmentFit::makeLine(SegmentFit::localSegmentPars(truthSeg));
90  const auto [recoPos, recoDir] = SegmentFit::makeLine(SegmentFit::localSegmentPars(gctx, recoSeg));
91  const std::vector<int> truthSigns = SegmentFitHelpers::driftSigns(truPos, truDir, recoSeg.measurements(), msgStream());
92  const std::vector<int> recoSigns = SegmentFitHelpers::driftSigns(recoPos, recoDir, recoSeg.measurements(), msgStream());
93  for (unsigned int s = 0 ; s < truthSigns.size(); ++s) {
94  same += (truthSigns[s] != 0) && truthSigns[s] == recoSigns[s];
95  }
96  return same;
97  }
98  std::vector<ObjectMatching>
100  const xAOD::MuonSegmentContainer* truthSegments,
101  const SegmentSeedContainer* seedContainer,
102  const SegmentContainer* segmentContainer) const {
103  std::vector<ObjectMatching> allAssociations{};
104  std::unordered_set<const SegmentSeed*> usedSeeds{};
105  std::unordered_set<const Segment*> usedSegs{};
106 
109  if (m_isMC) {
110  // collect the sim hits that contributed to our segments and seeds.
111  std::vector<simHitSet> truthHitsVec{}, seedSimHitVec{}, segmentSimHitVec{};
112  for (const SegmentSeed* seed: *seedContainer) {
113  seedSimHitVec.emplace_back(getMatchingSimHits(*seed));
114  }
115  for (const Segment* segment: *segmentContainer){
116  segmentSimHitVec.emplace_back(getMatchingSimHits(*segment));
117  }
118 
119  // Now look at the truth segments, collecting their sim hits.
120  // Compare these to the sim hits on our reco objects
121  for (const xAOD::MuonSegment* truth: *truthSegments) {
122  const simHitSet& truthHits{truthHitsVec.emplace_back(getMatchingSimHits(*truth))};
123  ObjectMatching & matchedWithTruth = allAssociations.emplace_back();
124  matchedWithTruth.truthSegment = truth;
125  matchedWithTruth.chamber = m_detMgr->getSectorEnvelope((*truthHits.begin())->identify());
126 
127  std::vector<std::pair<const SegmentSeed*, unsigned>> matchedSeeds{};
128 
129  // Find seeds sharing at least one simHit with our truth segment
130  // can't wait for views::enumerate
131  int seedIdx{-1};
132  for (const SegmentSeed* seed : *seedContainer) {
133  ++seedIdx;
134  if (seed->msSector() != matchedWithTruth.chamber) {
135  continue;
136  }
137  const simHitSet& seedHits{seedSimHitVec[seedIdx]};
138  unsigned int matchedHits = countMatched(truthHits, seedHits);
139  if (!matchedHits) {
140  continue;
141  }
142  matchedSeeds.emplace_back(std::make_pair(seed, matchedHits));
143  }
144  // Find segments sharing at least one simHit with our truth segment
145  std::vector<std::pair<const Segment*, unsigned>> matchedSegs{};
146  int segmentIdx{-1};
147  for (const Segment* segment : *segmentContainer) {
148  ++segmentIdx;
149  if (segment->msSector() != matchedWithTruth.chamber) {
150  continue;
151  }
152  const simHitSet& segmentHits{segmentSimHitVec[segmentIdx]};
153  unsigned int matchedHits = countMatched(truthHits, segmentHits);
154  if (!matchedHits) {
155  continue;
156  }
157  matchedSegs.emplace_back(std::make_pair(segment,matchedHits));
158  }
159 
160  // sort by quality of match
161 
162  // for segments (by hit count and same-side hits)
163  std::ranges::sort(matchedSegs,
164  [this, &truth, &gctx](const std::pair<const Segment*, unsigned>& segA,
165  const std::pair<const Segment*, unsigned>& segB){
166  if (segA.second != segB.second) return segA.second > segB.second;
167  return countOnSameSide(gctx, *truth, *segA.first) > countOnSameSide(gctx, *truth, *segB.first);
168  });
169  // and for seeds (by raw hit count)
170  std::ranges::sort(matchedSeeds, [](const std::pair<const SegmentSeed*, unsigned>& seedA,
171  const std::pair<const SegmentSeed*, unsigned>& seedB) {
172  return seedA.second > seedB.second;
173  });
174 
175 
176  // now we can populate our association object
177 
178  // first, we handle the segments and any seeds connected with them
179  for (const auto& [matched, nMatchedHits] : matchedSegs) {
180  // add segment to the list of all segments
181  matchedWithTruth.matchedSegments.push_back(matched);
182  // and update our book-keeping to record that this segment and its seed have already been written
183  usedSeeds.insert(matched->parent());
184  usedSegs.insert(matched);
185  }
186 
187  // now, we add the seeds
188  for (const auto& [seed , nHits] : matchedSeeds) {
189  // add seed to the list of all seeds
190  ATH_MSG_VERBOSE("Seed with "<<nHits);
191  matchedWithTruth.matchedSeeds.push_back(seed);
192  matchedWithTruth.matchedSeedFoundSegment.push_back(usedSeeds.count(seed));
193  usedSeeds.insert(seed);
194  }
195  } // end of loop over truth segments
196  }
197 
201 
202  // start with segments, and also collect "their" seeds in a common entry
203  for (const Segment* seg: *segmentContainer) {
204  // skip segments that were previously seen and written in the truth loop
205  if (usedSegs.count(seg)) {
206  continue;
207  }
208  ObjectMatching & match = allAssociations.emplace_back();
209  match.chamber = seg->msSector();
210  match.matchedSegments = {seg};
211  match.matchedSeeds = {seg->parent()};
212  // this seed has been written as well - do not write it in the following loop
213  usedSeeds.insert(seg->parent());
214  }
215  for (const SegmentSeed* seed: *seedContainer) {
216  // skip seeds that are on segments or seen in the truth loop
217  if (usedSeeds.count(seed)) {
218  continue;
219  }
220  ObjectMatching & match = allAssociations.emplace_back();
221  match.chamber = seed->msSector();
222  match.matchedSeeds = {seed};
223  }
224  return allAssociations;
225  }
226 
228  ATH_CHECK(m_tree.write());
229  return StatusCode::SUCCESS;
230  }
232 
233  const EventContext & ctx = Gaudi::Hive::currentContext();
234  const ActsGeometryContext* gctxPtr{nullptr};
235  ATH_CHECK(SG::get(gctxPtr, m_geoCtxKey, ctx));
236  const ActsGeometryContext& gctx{*gctxPtr};
237 
238 
241 
242  for (const SG::ReadHandleKey<SegmentSeedContainer>& key : m_inHoughSegmentSeedKeys) {
243  const SegmentSeedContainer* readSegmentSeeds{nullptr};
244  ATH_CHECK(SG::get(readSegmentSeeds, key, ctx));
245  segmentSeeds.insert(segmentSeeds.end(),readSegmentSeeds->begin(), readSegmentSeeds->end());
246  }
247  for (const SG::ReadHandleKey<SegmentContainer>& key : m_inSegmentKeys) {
248  const SegmentContainer* readSegments{nullptr};
249  ATH_CHECK(SG::get(readSegments, key, ctx));
250  segments.insert(segments.end(),readSegments->begin(), readSegments->end());
251  }
252  const xAOD::MuonSegmentContainer* readTruthSegments{nullptr};
253  ATH_CHECK(SG::get(readTruthSegments , m_truthSegmentKey, ctx));
254 
255  ATH_MSG_DEBUG("Succesfully retrieved input collections. Seeds: "<<segmentSeeds.size()
256  <<", segments: "<<segments.size() <<", truth segments: "<<(readTruthSegments? readTruthSegments->size() : -1)<<".");
257  std::vector<ObjectMatching> objects = matchWithTruth(gctx, readTruthSegments, segmentSeeds.asDataVector(),
258  segments.asDataVector());
259  for (const ObjectMatching& obj : objects) {
260  fillChamberInfo(obj.chamber);
261  fillTruthInfo(gctx, obj.truthSegment);
262  fillSeedInfo(obj);
263  fillSegmentInfo(gctx, obj);
264  ATH_CHECK(m_tree.fill(ctx));
265  }
266  return StatusCode::SUCCESS;
267  }
269  m_out_chamberIndex = toInt(msSector->chamberIndex());
270  m_out_stationSide = msSector->side();
271  m_out_stationPhi = msSector->stationPhi();
272  }
274  const xAOD::MuonSegment* segment) {
275  if (!segment) return;
276  m_out_hasTruth = true;
277 
278  const Amg::Vector3D segDir{segment->direction()};
279  static const SG::Accessor<float> acc_pt{"pt"};
280  static const SG::Accessor<float> acc_charge{"charge"};
281  // eta is interpreted as the eta-location
282  m_out_gen_Eta = segDir.eta();
283  m_out_gen_Phi = segDir.phi();
284  m_out_gen_Pt = acc_pt(*segment);
285  m_out_gen_Q = acc_charge(*segment);
286 
287  const auto [chamberPos, chamberDir] = SegmentFit::makeLine(SegmentFit::localSegmentPars(*segment));
288  m_out_gen_nHits = segment->nPrecisionHits()+segment->nPhiLayers() + segment->nTrigEtaLayers();
289  using namespace Muon::MuonStationIndex;
290  m_out_gen_nMDTHits = segment->nPrecisionHits() * (segment->technology() == TechnologyIndex::MDT);
291  m_out_gen_nNswHits = segment->nPrecisionHits() * (segment->technology() != TechnologyIndex::MDT);
292  m_out_gen_nTGCHits = (segment->nPhiLayers() + segment->nTrigEtaLayers()) * !isBarrel(segment->chamberIndex());
293  m_out_gen_nRPCHits = (segment->nPhiLayers() + segment->nTrigEtaLayers()) * isBarrel(segment->chamberIndex());
294 
295  m_out_gen_tantheta = houghTanTheta(chamberDir);
296  m_out_gen_tanphi = houghTanPhi(chamberDir);
297  m_out_gen_y0 = chamberPos.y();
298  m_out_gen_x0 = chamberPos.x();
299  m_out_gen_time = segment->t0();
300 
301  double minYhit = std::numeric_limits<double>::max();
302  double maxYhit = -1 * std::numeric_limits<double>::max();
303  for (const xAOD::MuonSimHit* hit : getMatchingSimHits(*segment)){
304  const Identifier hitId = hit->identify();
305  const MuonGMR4::MuonReadoutElement* RE = m_detMgr->getReadoutElement(hitId);
306  const IdentifierHash hash{m_idHelperSvc->isMdt(hitId) ? RE->measurementHash(hitId)
307  : RE->layerHash(hitId) };
308  const Amg::Transform3D localToChamber = RE->msSector()->globalToLocalTrans(gctx) * RE->localToGlobalTrans(gctx, hash);
309  const Amg::Vector3D chamberPos = localToChamber * xAOD::toEigen(hit->localPosition());
310  minYhit = std::min(chamberPos.y(), minYhit);
311  maxYhit = std::max(chamberPos.y(), maxYhit);
312  }
313  m_out_gen_minYhit = minYhit;
314  m_out_gen_maxYhit = maxYhit;
315 
316  ATH_MSG_DEBUG("A true max on chamber index "<<m_out_chamberIndex.getVariable()<<" side "<<m_out_stationSide.getVariable()<<" phi "<<m_out_stationPhi.getVariable()<<" with "
317  <<m_out_gen_nMDTHits.getVariable()<<" MDT and "<<m_out_gen_nRPCHits.getVariable()+m_out_gen_nTGCHits.getVariable()<< " trigger hits is at "
318  <<m_out_gen_tantheta.getVariable()<<" and "<<m_out_gen_y0.getVariable());
319  }
321  m_out_bucketEnd = bucket.coveredMax();
322  m_out_bucketStart = bucket.coveredMin();
323  m_out_nSpacePoints = bucket.size();
324  m_out_nPrecSpacePoints = std::ranges::count_if(bucket, [](const SpacePointBucket::value_type& sp){
325  return isPrecHit(*sp);
326  });
327  m_out_nPhiSpacePoints = std::ranges::count_if(bucket, [](const SpacePointBucket::value_type& sp){
328  return sp->measuresPhi();
329  });
330  if (!m_visionTool.isEnabled()){
331  return;
332  }
333  m_out_nTrueSpacePoints = std::ranges::count_if(bucket,[this](const SpacePointBucket::value_type& sp){
334  return m_visionTool->isLabeled(*sp);
335  });
336  m_out_nTruePrecSpacePoints = std::ranges::count_if(bucket,[this](const SpacePointBucket::value_type& sp){
337  return isPrecHit(*sp) && m_visionTool->isLabeled(*sp);
338  });
339  m_out_nTruePhiSpacePoints = std::ranges::count_if(bucket,[this](const SpacePointBucket::value_type& sp){
340  return sp->measuresPhi() && m_visionTool->isLabeled(*sp);
341  });
342  }
344 
345  m_out_seed_n = obj.matchedSeeds.size();
346  for (const auto [iseed, seed] : Acts::enumerate(obj.matchedSeeds)){
347  if (iseed ==0) {
348  fillBucketInfo(*seed->parentBucket());
349  }
350  double minYhit = m_out_bucketEnd.getVariable();
351  double maxYhit = m_out_bucketStart.getVariable();
352  for (const SpacePoint* hit : seed->getHitsInMax()){
353  minYhit = std::min(hit->positionInChamber().y(),minYhit);
354  maxYhit = std::max(hit->positionInChamber().y(),maxYhit);
355  }
356  m_out_seed_minYhit.push_back(minYhit);
357  m_out_seed_maxYhit.push_back(maxYhit);
358 
359  m_out_seed_hasPhiExtension.push_back(seed->hasPhiExtension());
360  m_out_seed_nMatchedHits.push_back(countMatched(obj.truthSegment, seed));
361  m_out_seed_y0.push_back(seed->interceptY());
362  m_out_seed_tantheta.push_back(seed->tanTheta());
363  if (seed->hasPhiExtension()){
364  m_out_seed_x0.push_back(seed->interceptX());
365  m_out_seed_tanphi.push_back(seed->tanPhi());
366  } else{
367  m_out_seed_x0.push_back(-999);
368  m_out_seed_tanphi.push_back(-999);
369  }
370 
371  m_out_seed_nHits.push_back(seed->getHitsInMax().size());
372  unsigned nMdtSeed{0}, nRpcSeed{0}, nTgcSeed{0}, nMmSeed{0}, nsTgcSeed{0};
373  unsigned nPrecHits{0}, nEtaHits{0}, nPhiHits{0}, nTrueHits{0}, nTruePrecHits{0}, nTrueEtaHits{0}, nTruePhiHits{0};
374  std::vector<unsigned char> matched{};
375  for (const HoughHitType & houghSP: seed->getHitsInMax()){
376  if (m_writeSpacePoints){
377  unsigned treeIdx = m_spTester->push_back(*houghSP);
378  if (treeIdx >= matched.size()){
379  matched.resize(treeIdx +1);
380  }
381  matched[treeIdx] = true;
382  }
383  nPrecHits += isPrecHit(*houghSP);
384  nPhiHits += houghSP->measuresPhi();
385  nEtaHits += houghSP->measuresEta();
386 
387  if (m_visionTool.isEnabled()) {
388  nTrueHits += m_visionTool->isLabeled(*houghSP);
389  nTruePrecHits += m_visionTool->isLabeled(*houghSP) && isPrecHit(*houghSP);
390  nTruePhiHits += m_visionTool->isLabeled(*houghSP) && houghSP->measuresPhi();
391  nTrueEtaHits += m_visionTool->isLabeled(*houghSP) && houghSP->measuresEta();
392  }
393  switch (houghSP->type()) {
395  ++nMdtSeed;
396  break;
398  nRpcSeed+=houghSP->measuresEta();
399  nRpcSeed+=houghSP->measuresPhi();
400  break;
402  nTgcSeed+=houghSP->measuresEta();
403  nTgcSeed+=houghSP->measuresPhi();
404  break;
406  nsTgcSeed += houghSP->measuresEta();
407  nsTgcSeed += houghSP->measuresPhi();
408  break;
410  ++nMmSeed;
411  break;
412  default:
413  ATH_MSG_WARNING("Technology "<<houghSP->identify() <<" not yet implemented");
414  }
415  }
416  m_out_seed_nMdt.push_back(nMdtSeed);
417  m_out_seed_nRpc.push_back(nRpcSeed);
418  m_out_seed_nTgc.push_back(nTgcSeed);
419  m_out_seed_nsTgc.push_back(nsTgcSeed);
420  m_out_seed_nMm.push_back(nMmSeed);
421 
422  m_out_seed_nPrecHits.push_back(nPrecHits);
423  m_out_seed_nEtaHits.push_back(nEtaHits);
424  m_out_seed_nPhiHits.push_back(nPhiHits);
425 
426  m_out_seed_nTrueHits.push_back(nTrueHits);
427  m_out_seed_nTruePrecHits.push_back(nTruePrecHits);
428  m_out_seed_nTrueEtaHits.push_back(nTrueEtaHits);
429  m_out_seed_nTruePhiHits.push_back(nTruePhiHits);
430 
431  m_out_seed_ledToSegment.push_back(obj.matchedSeedFoundSegment.at(iseed));
432  if (m_writeSpacePoints) {
433  m_spMatchedToPattern[iseed] = std::move(matched);
434  }
435  }
436  }
437 
439  const ObjectMatching& obj){
440  using namespace SegmentFit;
441 
442  m_out_segment_n = obj.matchedSegments.size();
443  for (auto & segment : obj.matchedSegments){
444  m_out_segment_hasPhi.push_back(std::ranges::find_if(segment->measurements(), [](const auto& meas){ return meas->measuresPhi();})
445  !=segment->measurements().end());
446  m_out_segment_fitIter.push_back(segment->nFitIterations());
447  m_out_segment_truthMatchedHits.push_back(countMatched(obj.truthSegment, segment));
448  m_out_segment_chi2.push_back(segment->chi2());
449  m_out_segment_nDoF.push_back(segment->nDoF());
450  m_out_segment_hasTimeFit.push_back(segment->hasTimeFit());
451 
452  m_out_segment_err_x0.push_back(segment->covariance()(toInt(ParamDefs::x0), toInt(ParamDefs::x0)));
453  m_out_segment_err_y0.push_back(segment->covariance()(toInt(ParamDefs::y0), toInt(ParamDefs::y0)));
454  m_out_segment_err_tantheta.push_back(segment->covariance()(toInt(ParamDefs::theta), toInt(ParamDefs::theta)));
455  m_out_segment_err_tanphi.push_back(segment->covariance()(toInt(ParamDefs::phi), toInt(ParamDefs::phi)));
456  m_out_segment_err_time.push_back(segment->covariance()(toInt(ParamDefs::time), toInt(ParamDefs::time)));
457  const auto [locPos, locDir] = makeLine(localSegmentPars(gctx, *segment));
458  m_out_segment_tanphi.push_back(houghTanPhi(locDir));
459  m_out_segment_tantheta.push_back(houghTanTheta(locDir));
460  m_out_segment_y0.push_back(locPos.y());
461  m_out_segment_x0.push_back(locPos.x());
462  m_out_segment_time.push_back(segment->segementT0() + segment->position().mag() * c_inv);
463 
464  unsigned nMdtHits{0}, nRpcEtaHits{0}, nRpcPhiHits{0}, nTgcEtaHits{0}, nTgcPhiHits{0},
465  nMmEtaHits{0}, nMmStereoHits{0}, nStgcStripHits{0},nStgcWireHits{0}, nStgcPadHits{0};
466  unsigned nTrueHits{0}, nTruePrecHits{0}, nTrueEtaHits{0}, nTruePhiHits{0};
467 
468  double minYhit = std::numeric_limits<double>::max();
469  double maxYhit = -1 * std::numeric_limits<double>::max();
470 
471  std::vector<unsigned char> matched;
472  for (const auto & meas : segment->measurements()){
473  // skip dummy measurement from beam spot constraint
474  if (meas->type() == xAOD::UncalibMeasType::Other) continue;
475  minYhit = std::min(meas->positionInChamber().y(),minYhit);
476  maxYhit = std::max(meas->positionInChamber().y(),maxYhit);
477  if (m_writeSpacePoints) {
478  unsigned treeIdx = m_spTester->push_back(*meas->spacePoint());
479  if (treeIdx >= matched.size()){
480  matched.resize(treeIdx +1);
481  }
482  matched[treeIdx] = true;
483  }
484  if (m_visionTool.isEnabled()) {
485  nTrueHits += m_visionTool->isLabeled(*meas->spacePoint());
486  nTruePrecHits += isPrecHit(*meas) && m_visionTool->isLabeled(*meas->spacePoint());
487  nTrueEtaHits += meas->measuresEta() && m_visionTool->isLabeled(*meas->spacePoint());
488  nTruePhiHits += meas->measuresPhi() && m_visionTool->isLabeled(*meas->spacePoint());
489  }
490  switch (meas->type()) {
492  ++nMdtHits;
493  break;
495  nRpcEtaHits += meas->measuresEta();
496  nRpcPhiHits += meas->measuresPhi();
497  break;
499  nTgcEtaHits += meas->measuresEta();
500  nTgcPhiHits += meas->measuresPhi();
501  break;
503  const MmIdHelper& idHelper{m_idHelperSvc->mmIdHelper()};
504  nMmEtaHits += !idHelper.isStereo(meas->spacePoint()->identify());
505  nMmStereoHits += !idHelper.isStereo(meas->spacePoint()->identify());
506  break;
508  const auto* prd = static_cast<const xAOD::sTgcMeasurement*>(meas->spacePoint()->primaryMeasurement());
509  nStgcStripHits += prd->channelType() == sTgcIdHelper::sTgcChannelTypes::Strip;
510  nStgcWireHits += prd->channelType() == sTgcIdHelper::sTgcChannelTypes::Wire;
511  nStgcPadHits += prd->channelType() == sTgcIdHelper::sTgcChannelTypes::Pad;
512  prd = dynamic_cast<const xAOD::sTgcMeasurement*>(meas->spacePoint()->secondaryMeasurement());
513  if (prd) {
514  nStgcWireHits += prd->channelType() == sTgcIdHelper::sTgcChannelTypes::Wire;
515  nStgcPadHits += prd->channelType() == sTgcIdHelper::sTgcChannelTypes::Pad;
516  }
517  break;
518  } default:
519  break;
520  }
521  }
522  m_out_segment_nMdtHits.push_back(nMdtHits);
523  m_out_segment_nRpcEtaHits.push_back(nRpcEtaHits);
524  m_out_segment_nRpcPhiHits.push_back(nRpcPhiHits);
525  m_out_segment_nTgcEtaHits.push_back(nTgcEtaHits);
526  m_out_segment_nTgcPhiHits.push_back(nTgcPhiHits);
527 
528  m_out_segment_nMmEtaHits.push_back(nMmEtaHits);
529  m_out_segment_nMmStereoHits.push_back(nMmStereoHits);
530  m_out_segment_nsTgcStripHits.push_back(nStgcStripHits);
531  m_out_segment_nsTgcWireHits.push_back(nStgcWireHits);
532  m_out_segment_nsTgcPadpHits.push_back(nStgcPadHits);
533 
534 
535  m_out_segment_nTrueHits.push_back(nTrueHits);
536  m_out_segment_nTruePrecHits.push_back(nTruePrecHits);
537  m_out_segment_nTruePhiHits.push_back(nTruePhiHits);
538  m_out_segment_nTrueEtaHits.push_back(nTrueEtaHits);
539 
540  m_out_segment_minYhit.push_back(minYhit);
541  m_out_segment_maxYhit.push_back(maxYhit);
542  if (m_writeSpacePoints) {
543  m_spMatchedToSegment.push_back(std::move(matched));
544  }
545  }
546  }
547 } // namespace MuonValR4
python.PyKernel.retrieve
def retrieve(aClass, aKey=None)
Definition: PyKernel.py:110
MuonR4::SegmentFitHelpers::driftSigns
std::vector< int > driftSigns(const Amg::Vector3D &posInChamber, const Amg::Vector3D &dirInChamber, const std::vector< const SpacePoint * > &uncalibHits, MsgStream &msg)
Calculates whether a segment line travereses the tube measurements on the left (-1) or right (1) side...
Definition: SegmentFitHelperFunctions.cxx:217
MuonSimHitHelpers.h
xAOD::MuonSimHit_v1
Definition: MuonSimHit_v1.h:18
UtilFunctions.h
MuonGMR4::SpectrometerSector::side
int8_t side() const
Returns the side of the MS-sector 1 -> A side ; -1 -> C side.
Definition: SpectrometerSector.cxx:57
MuonValR4::MuonHoughTransformTester::finalize
virtual StatusCode finalize() override
Definition: MuonHoughTransformTester.cxx:227
MuonGMR4::MuonReadoutElement::msSector
const SpectrometerSector * msSector() const
Returns the pointer to the envelope volume enclosing all chambers in the sector.
MuonValR4::countMatched
unsigned int countMatched(const simHitSet &truthHits, const simHitSet &recoHits)
Definition: MuonHoughTransformTester.cxx:31
MuonGMR4::SpectrometerSector
A spectrometer sector forms the envelope of all chambers that are placed in the same MS sector & laye...
Definition: SpectrometerSector.h:40
LArConditions2Ntuple.objects
objects
Definition: LArConditions2Ntuple.py:64
MuonR4::SpacePointBucket
: The muon space point bucket represents a collection of points that will bre processed together in t...
Definition: MuonSpectrometer/MuonPhaseII/Event/MuonSpacePoint/MuonSpacePoint/SpacePointContainer.h:21
MuonGMR4::SpectrometerSector::stationPhi
int stationPhi() const
: Returns the station phi of the sector
Definition: SpectrometerSector.cxx:63
SG::Accessor< float >
Muon::MuonStationIndex
Definition: MuonStationIndex.h:13
MuonR4::SpacePointBucket::coveredMin
double coveredMin() const
lower interval value covered by the bucket
Definition: MuonSpectrometer/MuonPhaseII/Event/MuonSpacePoint/MuonSpacePoint/SpacePointContainer.h:29
SG::VIEW_ELEMENTS
@ VIEW_ELEMENTS
this data object is a view, it does not own its elmts
Definition: OwnershipPolicy.h:18
ConstDataVector.h
DataVector adapter that acts like it holds const pointers.
MuonVal::EventInfoBranch::isMC
@ isMC
Flag determining whether the branch is simulation.
Definition: EventInfoBranch.h:20
max
constexpr double max()
Definition: ap_fixedTest.cxx:33
min
constexpr double min()
Definition: ap_fixedTest.cxx:26
MuonR4::Segment
Placeholder for what will later be the muon segment EDM representation.
Definition: MuonSpectrometer/MuonPhaseII/Event/MuonPatternEvent/MuonPatternEvent/Segment.h:19
xAOD::UncalibMeasType::MMClusterType
@ MMClusterType
MuonR4::Segment::measurements
const MeasVec & measurements() const
Returns the associated measurements.
Definition: MuonSpectrometer/MuonPhaseII/Event/MuonPatternEvent/MuonPatternEvent/Segment.h:49
MuonValR4::MuonHoughTransformTester::ObjectMatching
Definition: MuonHoughTransformTester.h:48
MuonGMR4::MuonReadoutElement
The MuonReadoutElement is an abstract class representing the geometry representing the muon detector.
Definition: MuonPhaseII/MuonDetDescr/MuonReadoutGeometryR4/MuonReadoutGeometryR4/MuonReadoutElement.h:38
HoughHelperFunctions.h
xAOD::MuonSegment_v1
Class describing a MuonSegment.
Definition: MuonSegment_v1.h:33
EventInfoBranch.h
MuonGMR4::MuonReadoutElement::layerHash
virtual IdentifierHash layerHash(const Identifier &measId) const =0
ATH_MSG_VERBOSE
#define ATH_MSG_VERBOSE(x)
Definition: AthMsgStreamMacros.h:28
SG::ReadHandleKey
Property holding a SG store/key/clid from which a ReadHandle is made.
Definition: StoreGate/StoreGate/ReadHandleKey.h:39
xAOD::UncalibMeasType::sTgcStripType
@ sTgcStripType
SpectrometerSector.h
MuonR4::SegmentFit::makeLine
std::pair< Amg::Vector3D, Amg::Vector3D > makeLine(const Parameters &pars)
Returns the parsed parameters into an Eigen line parametrization.
Definition: SegmentFitterEventData.cxx:26
python.TrigEgammaFastCaloHypoTool.same
def same(val, tool)
Definition: TrigEgammaFastCaloHypoTool.py:10
MuonValR4::simHitSet
std::unordered_set< const xAOD::MuonSimHit * > simHitSet
Definition: MuonHoughTransformTester.cxx:30
MuonValR4::MuonHoughTransformTester::ObjectMatching::matchedSeedFoundSegment
std::vector< char > matchedSeedFoundSegment
Definition: MuonHoughTransformTester.h:57
MuonR4::SegmentFit::ParamDefs::phi
@ phi
xAOD::UncalibMeasType::TgcStripType
@ TgcStripType
MuonValR4::MuonHoughTransformTester::ObjectMatching::matchedSeeds
std::vector< const MuonR4::SegmentSeed * > matchedSeeds
All seeds matched to this object.
Definition: MuonHoughTransformTester.h:56
MuonR4::houghTanPhi
double houghTanPhi(const Amg::Vector3D &v)
: Returns the hough tanPhi [x] / [z]
Definition: SegmentFitterEventData.cxx:18
MuonR4::SpacePointBucket::coveredMax
double coveredMax() const
upper interval value covered by the bucket
Definition: MuonSpectrometer/MuonPhaseII/Event/MuonSpacePoint/MuonSpacePoint/SpacePointContainer.h:31
MuonGMR4::SpectrometerSector::chamberIndex
Muon::MuonStationIndex::ChIndex chamberIndex() const
Returns the chamber index scheme.
Definition: SpectrometerSector.cxx:62
MuonValR4::MuonHoughTransformTester::countOnSameSide
unsigned int countOnSameSide(const ActsGeometryContext &gctx, const xAOD::MuonSegment &truthSeg, const MuonR4::Segment &recoSeg) const
Calculates how many measurements from the segment fit have the same drift sign as when evaluated with...
Definition: MuonHoughTransformTester.cxx:85
MuonValR4::MuonHoughTransformTester::matchWithTruth
std::vector< ObjectMatching > matchWithTruth(const ActsGeometryContext &gctx, const xAOD::MuonSegmentContainer *truthSegments, const MuonR4::SegmentSeedContainer *seedContainer, const MuonR4::SegmentContainer *segmentContainer) const
Definition: MuonHoughTransformTester.cxx:99
xAOD::sTgcMeasurement_v1::channelType
virtual sTgcChannelTypes channelType() const =0
Returns the channel type of the measurement (Pad/Wire/Strip)
SG::get
const T * get(const ReadCondHandleKey< T > &key, const EventContext &ctx)
Convenience function to retrieve an object given a ReadCondHandleKey.
Definition: ReadCondHandle.h:287
EL::StatusCode
::StatusCode StatusCode
StatusCode definition for legacy code.
Definition: PhysicsAnalysis/D3PDTools/EventLoop/EventLoop/StatusCode.h:22
ATH_MSG_DEBUG
#define ATH_MSG_DEBUG(x)
Definition: AthMsgStreamMacros.h:29
SegmentFitHelperFunctions.h
MuonGMR4::SpectrometerSector::globalToLocalTrans
Amg::Transform3D globalToLocalTrans(const ActsGeometryContext &gctx) const
Returns the global -> local transformation from the ATLAS global.
Definition: SpectrometerSector.cxx:78
Amg::Transform3D
Eigen::Affine3d Transform3D
Definition: GeoPrimitives.h:46
MuonValR4::MuonHoughTransformTester::fillTruthInfo
void fillTruthInfo(const ActsGeometryContext &gctx, const xAOD::MuonSegment *truthSegment)
Fill the associated truth information into the tree.
Definition: MuonHoughTransformTester.cxx:273
xAOD::Other
@ Other
ATH_CHECK
#define ATH_CHECK
Definition: AthCheckMacros.h:40
MuonValR4::isPrecHit
bool isPrecHit(const SpType &sp)
Define a spacepoint as precision hit if it's a Mdt or NSW eta hit.
Definition: MuonHoughTransformTester.cxx:49
MuonValR4::MuonHoughTransformTester::fillSegmentInfo
void fillSegmentInfo(const ActsGeometryContext &gctx, const ObjectMatching &obj)
Fill the info assciated to the segment.
Definition: MuonHoughTransformTester.cxx:438
MuonR4::SegmentFit::ParamDefs::x0
@ x0
MuonValR4::MuonHoughTransformTester::fillBucketInfo
void fillBucketInfo(const MuonR4::SpacePointBucket &bucket)
Fill the hit summary info of the associated bucket.
Definition: MuonHoughTransformTester.cxx:320
DataVector
Derived DataVector<T>.
Definition: DataVector.h:794
ActsGeometryContext
Include the GeoPrimitives which need to be put first.
Definition: ActsGeometryContext.h:27
MuonR4::SegmentFit::ParamDefs::time
@ time
MuonR4::SpacePoint
The muon space point is the combination of two uncalibrated measurements one of them measures the eta...
Definition: MuonSpectrometer/MuonPhaseII/Event/MuonSpacePoint/MuonSpacePoint/SpacePoint.h:19
MuonValR4
Lightweight algorithm to read xAOD MDT sim hits and (fast-digitised) drift circles from SG and fill a...
Definition: IPatternVisualizationTool.h:23
MuonValR4::MuonHoughTransformTester::ObjectMatching::truthSegment
const xAOD::MuonSegment * truthSegment
Truth segment for reference.
Definition: MuonHoughTransformTester.h:52
python.PyKernel.detStore
detStore
Definition: PyKernel.py:41
MuonR4::SegmentFit::ParamDefs::y0
@ y0
MuonVal
Class to store array like branches into the n-tuples.
Definition: HitValAlg.cxx:19
MuonHoughDefs.h
sTgcMeasurement.h
MuonR4::SegmentFit::toInt
constexpr int toInt(const ParamDefs p)
Definition: MuonHoughDefs.h:42
MuonValR4::MuonHoughTransformTester::ObjectMatching::chamber
const MuonGMR4::SpectrometerSector * chamber
Associated chamber.
Definition: MuonHoughTransformTester.h:50
python.ElectronD3PDObject.matched
matched
Definition: ElectronD3PDObject.py:138
python.PhysicalConstants.c_light
float c_light
Definition: PhysicalConstants.py:73
Amg::Vector3D
Eigen::Matrix< double, 3, 1 > Vector3D
Definition: GeoPrimitives.h:47
MuonValR4::MuonHoughTransformTester::initialize
virtual StatusCode initialize() override
Definition: MuonHoughTransformTester.cxx:55
python.copyTCTOutput.locDir
locDir
Definition: copyTCTOutput.py:112
MuonR4
This header ties the generic definitions in this package.
Definition: HoughEventData.h:16
MuonValR4::MuonHoughTransformTester::execute
virtual StatusCode execute() override
Definition: MuonHoughTransformTester.cxx:231
MuonValR4::MuonHoughTransformTester::ObjectMatching::matchedSegments
std::vector< const MuonR4::Segment * > matchedSegments
All segments matched to this object.
Definition: MuonHoughTransformTester.h:54
MuonValR4::MuonHoughTransformTester::fillSeedInfo
void fillSeedInfo(const ObjectMatching &obj)
Fill the info associated to the seed.
Definition: MuonHoughTransformTester.cxx:343
MmIdHelper
Definition: MmIdHelper.h:54
CaloCondBlobAlgs_fillNoiseFromASCII.hash
dictionary hash
Definition: CaloCondBlobAlgs_fillNoiseFromASCII.py:108
ATH_MSG_WARNING
#define ATH_MSG_WARNING(x)
Definition: AthMsgStreamMacros.h:32
ConstDataVector
DataVector adapter that acts like it holds const pointers.
Definition: ConstDataVector.h:76
MuonR4::SegmentSeed
Representation of a segment seed (a fully processed hough maximum) produced by the hough transform.
Definition: SegmentSeed.h:14
MuonGMR4::MuonReadoutElement::measurementHash
virtual IdentifierHash measurementHash(const Identifier &measId) const =0
Constructs the identifier hash from the full measurement Identifier.
python.LArCondContChannels.isBarrel
isBarrel
Definition: LArCondContChannels.py:659
python.SystemOfUnits.s
float s
Definition: SystemOfUnits.py:147
MuonGMR4::MuonReadoutElement::localToGlobalTrans
const Amg::Transform3D & localToGlobalTrans(const ActsGeometryContext &ctx) const
Returns the local to global transformation into the ATLAS coordinate system.
Definition: MuonPhaseII/MuonDetDescr/MuonReadoutGeometryR4/src/MuonReadoutElement.cxx:81
MuonHoughTransformTester.h
MuonR4::SegmentFit::localSegmentPars
Parameters localSegmentPars(const xAOD::MuonSegment &seg)
Returns the localSegPars decoration from a xAODMuon::Segment.
Definition: SegmentFitterEventData.cxx:32
MuonValR4::MuonHoughTransformTester::fillChamberInfo
void fillChamberInfo(const MuonGMR4::SpectrometerSector *chamber)
Fill the current chamber info into the output.
Definition: MuonHoughTransformTester.cxx:268
python.PyAthena.obj
obj
Definition: PyAthena.py:132
MmIdHelper::isStereo
bool isStereo(const Identifier &id) const
Definition: MmIdHelper.cxx:817
xAOD::UncalibMeasType::RpcStripType
@ RpcStripType
xAOD::UncalibMeasType::MdtDriftCircleType
@ MdtDriftCircleType
MuonR4::houghTanTheta
double houghTanTheta(const Amg::Vector3D &v)
Returns the hough tanTheta [y] / [z].
Definition: SegmentFitterEventData.cxx:14
MuonR4::getMatchingSimHits
std::unordered_set< const xAOD::MuonSimHit * > getMatchingSimHits(const xAOD::MuonSegment &segment)
: Returns all sim hits matched to a xAOD::MuonSegment
Definition: MuonSimHitHelpers.cxx:27
MuonSegmentReaderConfig.reco
reco
Definition: MuonSegmentReaderConfig.py:133
MuonR4::SegmentFit::ParamDefs::theta
@ theta
MDT
@ MDT
Definition: RegSelEnums.h:31
match
bool match(std::string s1, std::string s2)
match the individual directories of two strings
Definition: hcg.cxx:356
MuonValR4::ObjectMatching
MuonHoughTransformTester::ObjectMatching ObjectMatching
Definition: MuonHoughTransformTester.cxx:29
xAOD::sTgcMeasurement_v1
Definition: sTgcMeasurement_v1.h:21
NSWL1::PadTriggerAdapter::segment
Muon::NSW_PadTriggerSegment segment(const NSWL1::PadTrigger &data)
Definition: PadTriggerAdapter.cxx:5
mapkey::key
key
Definition: TElectronEfficiencyCorrectionTool.cxx:37
Identifier
Definition: IdentifierFieldParser.cxx:14