ATLAS Offline Software
Loading...
Searching...
No Matches
PFTrackSelector.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2026 CERN for the benefit of the ATLAS collaboration
3*/
5#include "PFTrackSelector.h"
9#include "GaudiKernel/SystemOfUnits.h"
10
11constexpr float invGeV = 1./CLHEP::GeV;
12
13PFTrackSelector::PFTrackSelector(const std::string& name, ISvcLocator* pSvcLocator):
14 AthReentrantAlgorithm(name, pSvcLocator)
15{
16}
17
19
22
23 ATH_CHECK(m_tracksReadHandleKey.initialize());
24 ATH_CHECK(m_vertexKey.initialize());
25
26 // Optional readhandlekeys for electrons and muons
27 if(!m_electronsReadHandleKey.key().empty()) {
29 }
30 if(!m_muonsReadHandleKey.key().empty()) {
31 ATH_CHECK(m_muonsReadHandleKey.initialize());
32 }
33
35
36 if (!m_monTool.empty()) ATH_CHECK(m_monTool.retrieve());
37
38 return StatusCode::SUCCESS;
39
40}
41
42StatusCode PFTrackSelector::execute(const EventContext& ctx) const{
43 // Monitor the time taken to execute the alg
44 auto t_exec = Monitored::Timer<std::chrono::milliseconds>( "TIME_execute" );
45 Monitored::ScopedTimer execution_time(t_exec);
46 auto N_tracks = Monitored::Scalar( "N_tracks", 0 );
47 auto eta_track = Monitored::Scalar( "eta_track", 0. );
48 auto pt_track = Monitored::Scalar( "pt_track", 0. );
49
51 ATH_CHECK(eflowRecTracksWriteHandle.record(std::make_unique<eflowRecTrackContainer>()));
52
53 /* Verify the read handle has a valid pointer, and if not return */
55 if (!tracksReadHandle.isValid()) {
56 ATH_MSG_WARNING("Can not retrieve xAOD::TrackParticleContainer with name: " << tracksReadHandle.key());
57 return StatusCode::FAILURE;
58 }
59
60 const xAOD::ElectronContainer* electrons = nullptr;
61 std::optional<SG::ReadHandle<xAOD::ElectronContainer>> electronsReadHandle;
62 if (!m_electronsReadHandleKey.empty()) {
63 electronsReadHandle.emplace(m_electronsReadHandleKey, ctx);
64 ATH_CHECK(electronsReadHandle->isValid());
65 electrons = electronsReadHandle->cptr();
66 }
67 const xAOD::MuonContainer* muons = nullptr;
68 std::optional<SG::ReadHandle<xAOD::MuonContainer>> muonsReadHandle;
69 if (!m_muonsReadHandleKey.empty()) {
70 muonsReadHandle.emplace(m_muonsReadHandleKey, ctx);
71 ATH_CHECK(muonsReadHandle->isValid());
72 muons = muonsReadHandle->cptr();
73 }
74
75 // the tight track selection efficiency is around 80% (evaluated in mu=200 Run4 MC sample), reserve memory accordingly
76 eflowRecTracksWriteHandle->reserve(static_cast<size_t>(0.8*tracksReadHandle->size()));
77
78 /* Do the track selection for tracks to be used in all of the following steps: */
79 for (const auto *thisTrack : *tracksReadHandle){
80
81 if (!thisTrack){
82 ATH_MSG_WARNING("Have invalid pointer to xAOD::TrackParticle");
83 continue;
84 }
85
86 ATH_MSG_DEBUG("Have track with E, pt, eta and phi of " << thisTrack->e() << ", " << thisTrack->pt() << ", "
87 << thisTrack->eta() << " and " << thisTrack->phi());
88
89 bool rejectTrack(!selectTrack(*thisTrack));
90 ATH_MSG_DEBUG("rejectTrack is " << rejectTrack);
91 if (rejectTrack) continue;
92 bool isElectron = this->isElectron(thisTrack, electrons);
93 ATH_MSG_DEBUG("isElectron is " << isElectron);
94 if (isElectron) continue;
95 bool isMuon = this->isMuon(thisTrack, muons);
96 ATH_MSG_DEBUG("isMuon is " << isMuon);
97 if (isMuon) continue;
98
99 // Monitor the time per selected track
100 auto t_track = Monitored::Timer<std::chrono::microseconds>( "TIME_track" );
101 eta_track = thisTrack->eta();
102 pt_track = thisTrack->pt() * invGeV;
103 const xAOD::TrackParticleContainer* trkcont = static_cast<const xAOD::TrackParticleContainer*>(thisTrack->container());
104
105 /* Create the eflowRecCluster and put it in the container */
106 unsigned int trackIndex = thisTrack->index();
107 std::unique_ptr<eflowRecTrack> thisEFRecTrack = std::make_unique<eflowRecTrack>(ctx, ElementLink<xAOD::TrackParticleContainer>(trkcont, trackIndex), m_theTrackExtrapolatorTool);
108 thisEFRecTrack->setTrackId(trackIndex);
109 eflowRecTracksWriteHandle->push_back(std::move(thisEFRecTrack));
110
111 // Fill histogram
112 auto mon_trk = Monitored::Group(m_monTool, t_track, eta_track, pt_track);
113 }
114
115 std::sort(eflowRecTracksWriteHandle->begin(), eflowRecTracksWriteHandle->end(), eflowRecTrack::SortDescendingPt());
116
117 N_tracks = eflowRecTracksWriteHandle->size();
118 auto mon_exectime = Monitored::Group(m_monTool, t_exec, N_tracks);
119 return StatusCode::SUCCESS;
120}
121
122StatusCode PFTrackSelector::finalize(){return StatusCode::SUCCESS;}
123
124bool
126{
127 // We pass a null xAOD::Vertex pointer to accept here, the vertex is only needed if z0 cuts are applied (which they
128 // are not)
129 if (track.pt() * 0.001 < m_upperTrackPtCut){
130 return static_cast<bool>(m_trackSelectorTool->accept(track, nullptr));
131 }
132 else
133 return false;
134}
135
137
138 if (electronContainer==nullptr)
139 return false;
140
141 for (const auto* thisElectron : *electronContainer) {
142 if (thisElectron) {
143 unsigned int nTrack = thisElectron->nTrackParticles();
144
145 if (0 != nTrack) {
147 if (origTrack) {
148 if (track == origTrack) {
149 return true;
150 }
151 } // if valid track pointer
152 else
153 ATH_MSG_WARNING("Electron object map has NULL pointer to original TrackParticle");
154 } // if has a track
155 else
156 ATH_MSG_WARNING("Electron object has " << nTrack << " tracks");
157 } // if valid pointer
158 else
159 ATH_MSG_WARNING("Electron is a NULL pointer");
160 } // electron loop
161
162 return false;
163}
164
165bool
167{
168 if (muonContainer==nullptr)
169 return false;
170
171 for (const auto* theMuon : *muonContainer) {
172 if (theMuon) {
173 ATH_MSG_DEBUG("Considering muon in isMuon with e,pt, eta and phi of "
174 << theMuon->e() << ", " << theMuon->pt() << ", " << theMuon->eta() << " and " << theMuon->phi());
175 const ElementLink<xAOD::TrackParticleContainer>& theLink = theMuon->inDetTrackParticleLink();
176 if (theLink.isValid()) {
177 const xAOD::TrackParticle* ID_track = *theLink;
178 if (ID_track) {
179 if (track == ID_track){
180 return true;
181 }
182 } else
183 ATH_MSG_WARNING("This muon has a NULL pointer to the track");
184 } else
185 ATH_MSG_WARNING("This muon has an invalid link to the track");
186 } // if muon pointer is valid
187 else
188 ATH_MSG_WARNING("This muon is a NULL pointer");
189 } // muon loop
190
191 return false;
192}
#define ATH_CHECK
Evaluate an expression and check for errors.
#define ATH_MSG_WARNING(x)
#define ATH_MSG_DEBUG(x)
constexpr float invGeV
Handle class for reading from StoreGate.
Handle class for recording to StoreGate.
xAOD::ElectronContainer * electronContainer
xAOD::MuonContainer * muonContainer
An algorithm that can be simultaneously executed in multiple threads.
Group of local monitoring quantities and retain correlation when filling histograms
Declare a monitored scalar variable.
Helper class to create a scoped timer.
A monitored timer.
bool selectTrack(const xAOD::TrackParticle &track) const
This applys a selection criteria to the track using the tracking CP track selection tool.
bool isMuon(const xAOD::TrackParticle *track, const xAOD::MuonContainer *muonContainer) const
check if track belongs to an muon
SG::WriteHandleKey< eflowRecTrackContainer > m_eflowRecTracksWriteHandleKey
WriteHandleKey for the eflowRecTrackContainer to write out.
SG::ReadHandleKey< xAOD::VertexContainer > m_vertexKey
PFTrackSelector(const std::string &name, ISvcLocator *pSvcLocator)
Default constructor.
StatusCode initialize()
Gaudi AthReentrantAlgorithm hooks.
ToolHandle< eflowTrackExtrapolatorBaseAlgTool > m_theTrackExtrapolatorTool
ToolHandle for track extrapolation to calorimeter tool.
SG::ReadHandleKey< xAOD::TrackParticleContainer > m_tracksReadHandleKey
ReadHandleKey for the TrackParticleContainer to be used as input.
StatusCode execute(const EventContext &ctx) const
ToolHandle< InDet::IInDetTrackSelectionTool > m_trackSelectorTool
ToolHandle to track selection tool provided by tracking CP.
SG::ReadHandleKey< xAOD::MuonContainer > m_muonsReadHandleKey
ReadHandleKey for the MuonContainer to be used as input.
ToolHandle< GenericMonitoringTool > m_monTool
Online monitoring tool for recording histograms of the alg in action.
bool isElectron(const xAOD::TrackParticle *track, const xAOD::ElectronContainer *electronContainer) const
check if track belongs to an electron
StatusCode finalize()
SG::ReadHandleKey< xAOD::ElectronContainer > m_electronsReadHandleKey
ReadHandleKey for the ElectronContainer to be used as input.
Gaudi::Property< float > m_upperTrackPtCut
Upper limit on track Pt for input tracks.
virtual bool isValid() override final
Can the handle be successfully dereferenced?
virtual const std::string & key() const override final
Return the StoreGate ID for the referenced object.
StatusCode record(std::unique_ptr< T > data)
Record a const object to the store.
void sort(typename DataModel_detail::iterator< DVL > beg, typename DataModel_detail::iterator< DVL > end)
Specialization of sort for DataVector/List.
const xAOD::TrackParticle * getOriginalTrackParticle(const xAOD::Electron *el)
Helper function for getting the "Original" Track Particle (i.e before GSF) via the electron.
ElectronContainer_v1 ElectronContainer
Definition of the current "electron container version".
TrackParticle_v1 TrackParticle
Reference the current persistent version:
TrackParticleContainer_v1 TrackParticleContainer
Definition of the current "TrackParticle container version".
MuonContainer_v1 MuonContainer
Definition of the current "Muon container version".