ATLAS Offline Software
ClusterTruthTool.cxx
Go to the documentation of this file.
1 
14 #include "ClusterTruthTool.h"
15 
21 #include "TLorentzVector.h"
22 
24  const std::string& n,
25  const IInterface* p)
26  : base_class(t, n, p) {}
27 
29  const HGTD_Cluster* cluster, const xAOD::TruthParticle* tp,
30  const InDetSimDataCollection* sim_data,
31  const HepMC::GenEvent* hard_scatter_evnt) const {
32 
33  if (not sim_data or not tp) {
34  return {HGTD::ClusterTruthOrigin::UNIDENTIFIED, false, false};
35  }
36 
37  ATH_MSG_DEBUG("[ClusterTruthTool] " << sim_data->size() << " SDO elements");
38  ATH_MSG_DEBUG("[ClusterTruthTool] all SimData IDs: ");
39  for (const auto& elem : *sim_data) {
40  ATH_MSG_DEBUG(elem.first);
41  }
42 
43  const std::vector<Identifier>& rdo_id_list = cluster->rdoList();
44  // keep record of the cluster origins and if they are shadowed or not
45  std::vector<std::pair<HGTD::ClusterTruthOrigin, bool>> shadowed_origins;
46 
47  for (const auto& rdo_id : rdo_id_list) {
48 
49  ATH_MSG_DEBUG("[ClusterTruthTool] looking for ID:" << rdo_id);
50 
51  auto pos = sim_data->find(rdo_id);
52  // the InDetSimData contains a std::pair<HepMcParticleLink, float>, where
53  // the second entry in the pair holds the time of the SiChargedDiode
54  if (pos == sim_data->end()) {
56  "[HGTD::ClusterTruthTool::classifyCluster] ID not found in SDO "
57  "map, going to next ID");
58  continue;
59  }
60  // collect deposits, sorted with first deposit at start of map bu default
61  std::map<float, HGTD::ClusterTruthOrigin> sorted_deposits;
62 
64  // the following is taken from 20.20 as is
65  ATH_MSG_DEBUG("[ClusterTruthTool] going through "
66  << pos->second.getdeposits().size() << " deposits");
67  for (const auto& deposit : pos->second.getdeposits()) {
68  const HepMcParticleLink& particle_link = deposit.first;
69  int barcode = HepMC::barcode(particle_link); // FIXME barcode-based
70 
71  ATH_MSG_DEBUG("[ClusterTruthTool] barcode:" << barcode);
72  // barcodes of 0 or secondaries generated by GEANT4
73  // 0 is also used for detector noise, delta rays and random energy
74  // deposits
75  if (barcode == 0 || HepMC::is_simulation_particle(particle_link.cptr())) {
76  sorted_deposits.emplace(deposit.second,
78  continue;
79  }
80  // check for identity with original particle
81  HepMC::ConstGenParticlePtr gen_part = particle_link.cptr();
82  if (gen_part) {
83  TLorentzVector l4(gen_part->momentum().px(), gen_part->momentum().py(),
84  gen_part->momentum().pz(), gen_part->momentum().e());
85  // if the barcode is identical and spacial matching passes, then this
86  // deposit came from the tested truth particle
87  if (barcode == HepMC::barcode(tp) && tp->p4().DeltaR(l4) < 0.05) { // FIXME barcode-based comparing GenParticle and xAOD::TruthParticle unique IDs - using barcodes for now
88  sorted_deposits.emplace(deposit.second,
90  // if given, the parent event can be checked
91  } else if (hard_scatter_evnt and
92  gen_part->parent_event() == hard_scatter_evnt) {
93  sorted_deposits.emplace(deposit.second,
95  // otherwise, a particle that was generated but doesn't come from the
96  // hard scatter is considered to be originating from a pileup
97  // interaction
98  } else {
99  sorted_deposits.emplace(deposit.second,
101  }
102  } else {
103  // if there is no gen particle, we can guess based on the event index
104  if (particle_link.eventIndex() == 0) {
105  sorted_deposits.emplace(deposit.second,
107  } else {
108  // If the gen was not kept, we assume it is cut away from truth record
109  // and is pileup
110  sorted_deposits.emplace(deposit.second,
112  }
113  }
114  } // END lOOP over the deposits
115 
116  ATH_MSG_DEBUG("[ClusterTruthTool] " << sorted_deposits.size()
117  << " sorted_deposits");
118 
119  // check for shadowing, which means that a deposit was left by the truth
120  // particle, but it was not the first deposit and is thus not used for the
121  // time measurement -> I will have an incorrect time
122  bool is_shadowed = false;
124 
126  sorted_deposits.begin();
127 
128  for (; elem != sorted_deposits.end(); ++elem) {
129  if (elem == sorted_deposits.begin()) {
130  current_origin = elem->second;
131  } else {
132  // if one of the later deposits originates from the truth particle, then
133  // the hit I want to find was shadowed by something else, and I will
134  // reconstruct an incorrect time
135  if (current_origin != HGTD::ClusterTruthOrigin::TRUTH_PARTICLE &&
137  is_shadowed = true;
138  }
139  }
140  } // END LOOP over the time sorted deposits
141  shadowed_origins.emplace_back(current_origin, is_shadowed);
142  } // END LOOP over RDO identifiers
143 
145 
146  if (shadowed_origins.empty()) {
147  ATH_MSG_DEBUG("did not manage to understand any RDOs...");
149  result.is_shadowed = false;
150  // A cluster is considered to be merged if more than one particle deposited
151  // energy in a given pad.
152  result.is_merged = false;
153  } else {
154  result.is_merged = false;
155  result.origin = shadowed_origins.at(0).first;
156  result.is_shadowed = shadowed_origins.at(0).second;
157  for (size_t i = 1; i < shadowed_origins.size(); ++i) {
158  if (shadowed_origins.at(i).first != result.origin) {
159  result.is_merged = true;
160  } else {
161  result.is_shadowed |= shadowed_origins.at(i).second;
162  }
163  }
164  }
165  return result;
166 }
xAOD::iterator
JetConstituentVector::iterator iterator
Definition: JetConstituentVector.cxx:68
HGTD::ClusterTruthTool::classifyCluster
virtual HGTD::ClusterTruthInfo classifyCluster(const HGTD_Cluster *cluster, const xAOD::TruthParticle *tp, const InDetSimDataCollection *sim_data, const HepMC::GenEvent *hard_scatter_evnt=nullptr) const override final
The InDetSimDataCollection is a map, connecting Identifiers from the RDOs to InDetSimData objects,...
Definition: ClusterTruthTool.cxx:28
ClusterTruthTool.h
Copyright (C) 2002-2022 CERN for the benefit of the ATLAS collaboration.
get_generator_info.result
result
Definition: get_generator_info.py:21
python.PerfMonSerializer.p
def p
Definition: PerfMonSerializer.py:743
HGTD::ClusterTruthOrigin
ClusterTruthOrigin
Definition: IHGTD_ClusterTruthTool.h:27
HGTD::ClusterTruthInfo
Definition: IHGTD_ClusterTruthTool.h:35
Trk::PrepRawData::rdoList
const std::vector< Identifier > & rdoList() const
return the List of rdo identifiers (pointers)
ParticleTest.tp
tp
Definition: ParticleTest.py:25
InDetSimDataCollection
Definition: InDetSimDataCollection.h:25
read_hist_ntuple.t
t
Definition: read_hist_ntuple.py:5
HGTD_Cluster.h
Copyright (C) 2002-2023 CERN for the benefit of the ATLAS collaboration.
HGTD_Cluster
Definition: HGTD_Cluster.h:35
HepMC::is_simulation_particle
bool is_simulation_particle(const T &p)
Method to establish if a particle (or barcode) was created during the simulation (TODO update to be s...
Definition: MagicNumbers.h:299
McEventCollection.h
lumiFormat.i
int i
Definition: lumiFormat.py:92
beamspotman.n
n
Definition: beamspotman.py:731
ATH_MSG_DEBUG
#define ATH_MSG_DEBUG(x)
Definition: AthMsgStreamMacros.h:29
HepMC::barcode
int barcode(const T *p)
Definition: Barcode.h:16
xAOD::TruthParticle_v1
Class describing a truth particle in the MC record.
Definition: TruthParticle_v1.h:41
HGTD::ClusterTruthOrigin::UNIDENTIFIED
@ UNIDENTIFIED
HGTD::ClusterTruthOrigin::SECONDARY
@ SECONDARY
HGTD::ClusterTruthOrigin::TRUTH_PARTICLE
@ TRUTH_PARTICLE
HepMC::ConstGenParticlePtr
const GenParticle * ConstGenParticlePtr
Definition: GenParticle.h:38
HGTD::ClusterTruthTool::ClusterTruthTool
ClusterTruthTool(const std::string &, const std::string &, const IInterface *)
Definition: ClusterTruthTool.cxx:23
MagicNumbers.h
python.LumiBlobConversion.pos
pos
Definition: LumiBlobConversion.py:18
HGTD::ClusterTruthOrigin::HARD_SCATTER
@ HARD_SCATTER
InDetSimDataCollection.h
HGTD::ClusterTruthOrigin::PILEUP
@ PILEUP
TruthParticle.h