ATLAS Offline Software
MuidTrackIsolation.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2021 CERN for the benefit of the ATLAS collaboration
3 */
4 
6 // MuidTrackIsolation
7 // AlgTool for estimating the number, total charged momentum and most
8 // energetic inner detector tracks in a cone surrounding a muon
9 //
11 
12 #include "MuidTrackIsolation.h"
13 
14 #include <cmath>
15 #include <iomanip>
16 
18 #include "GaudiKernel/SystemOfUnits.h"
23 #include "TrkSurfaces/Surface.h"
24 #include "TrkTrack/Track.h"
26 namespace Rec {
27 
28  MuidTrackIsolation::MuidTrackIsolation(const std::string& type, const std::string& name, const IInterface* parent) :
29  AthAlgTool(type, name, parent), m_etaSafetyFactor(0.1) {
30  declareInterface<IMuidTrackIsolation>(this);
31  }
32 
33  //<<<<<< PUBLIC MEMBER FUNCTION DEFINITIONS >>>>>>
34 
36  ATH_MSG_INFO("MuidTrackIsolation::initialize()");
37 
38  // get the Tools
39  ATH_CHECK(m_intersector.retrieve());
41  // create the calo barrel surfaces (cylinder) and 2 endcap discs)
42  double radius = 2.0 * Gaudi::Units::meter;
43  double halfLength = 4.0 * Gaudi::Units::meter;
45  transform.setIdentity();
46  m_caloCylinder = std::make_unique<Trk::CylinderSurface>(transform, radius, halfLength);
47 
48  // the corresponding max barrel cotTheta
49  m_barrelCotTheta = halfLength / radius;
50 
51  // and the forward/backward endcap disks
52  Amg::Transform3D discRotation;
53  discRotation.setIdentity();
54  Amg::Vector3D forwardDiscPosition(0., 0., halfLength);
55  auto transform1 = std::make_unique<Amg::Transform3D>(discRotation * forwardDiscPosition);
56  m_caloForwardDisc = std::make_unique<Trk::DiscSurface>(*transform1, 0., radius);
57  Amg::Vector3D backwardDiscPosition(0., 0., -halfLength);
58  auto transform2 = std::make_unique<Amg::Transform3D>(discRotation * backwardDiscPosition);
59  m_caloBackwardDisc = std::make_unique<Trk::DiscSurface>(*transform2, 0., radius);
60 
61  ATH_CHECK(m_inDetTracksLocation.initialize());
62 
63  return StatusCode::SUCCESS;
64  }
65  std::pair<int, double> MuidTrackIsolation::trackIsolation(const EventContext& ctx, double eta, double phi) const {
66  // debug input quantities
67  ATH_MSG_DEBUG(" MuidTrackIsolation:: " << std::setiosflags(std::ios::fixed)
68  << (m_trackExtrapolation ? "applied after extrapolation to calo, " : "applied at perigee, ")
69  << " for muon at calo with eta,phi " << std::setw(8) << std::setprecision(3) << eta
70  << std::setw(8) << std::setprecision(3) << phi);
71 
72  // set initial state
73  std::pair<int, double> isolation{0, 0.};
74 
75  // retrieve track collection
77  if (!inDetTracks.isPresent()) {
78  ATH_MSG_DEBUG(" no ID Track container at location " << m_inDetTracksLocation.key());
79  return isolation;
80  }
81 
82  if (!inDetTracks.isValid()) {
83  ATH_MSG_WARNING(" ID Track container " << m_inDetTracksLocation.key() << " not valid!");
84  return isolation;
85  }
86 
87  // evaluate isolation according to configuration
89  isolation = trackExtrapolated(inDetTracks.cptr(), eta, phi);
90  } else {
91  isolation = trackVertex(inDetTracks.cptr(), eta, phi);
92  }
93 
94  // debug result
95  ATH_MSG_DEBUG("Found " << isolation.first << std::setiosflags(std::ios::fixed) << " InDet tracks with total momentum "
96  << std::setw(8) << std::setprecision(1) << isolation.second / Gaudi::Units::GeV << " GeV");
97 
98  return isolation;
99  }
100 
101  std::pair<int, double> MuidTrackIsolation::trackVertex(const TrackCollection* inDetTracks, double eta, double phi) const {
102  // set initial state
103  double sumP = 0.;
104  int numberTracks = 0;
105 
106  // choose tracks in cone
107  for (const Trk::Track* id : *inDetTracks) {
108  const Trk::Perigee& perigee = *id->perigeeParameters();
109  if (id->info().trackProperties(Trk::TrackInfo::StraightTrack) || perigee.pT() < m_minPt) continue;
110 
111  double inDetPhi = perigee.parameters()[Trk::phi];
112  double inDetEta = perigee.eta();
113 
114  double diffEta = std::abs(eta - inDetEta);
115  double diffPhi = xAOD::P4Helpers::deltaPhi(phi, inDetPhi);
116 
117  ATH_MSG_DEBUG(std::endl
118  << std::setiosflags(std::ios::fixed) << " Id track: momentum " << std::setw(8) << std::setprecision(1)
119  << perigee.momentum().mag() / Gaudi::Units::GeV << " with perigee eta and difference " << std::setw(8)
120  << std::setprecision(3) << perigee.eta() << std::setw(8) << std::setprecision(3) << diffEta
121  << " and same for phi " << std::setw(8) << std::setprecision(3) << perigee.parameters()[Trk::phi] << std::setw(8)
122  << std::setprecision(3) << diffPhi);
123 
124  if ((diffPhi * diffPhi + diffEta * diffEta) > m_trackCone2) continue;
125  ++numberTracks;
126  const double p = perigee.momentum().mag();
127  sumP += p;
128 
129  ATH_MSG_VERBOSE("inside cone, track#" << std::setw(3) << numberTracks);
130  }
131 
132  return std::make_pair(numberTracks, sumP);
133  }
134 
135  std::pair<int, double> MuidTrackIsolation::trackExtrapolated(const TrackCollection* inDetTracks, double eta, double phi) const {
136  // set initial state
137  double sumP = 0.;
138  int numberTracks = 0;
139 
140  // extrapolate close in eta tracks to calorimeter surface
141  for (const Trk::Track* id : *inDetTracks) {
142  const Trk::Perigee& perigee = *id->perigeeParameters();
143  if (id->info().trackProperties(Trk::TrackInfo::StraightTrack) || perigee.pT() < m_minPt) continue;
144 
145  double inDetEta = perigee.eta();
146  if (std::abs(eta - inDetEta) > m_trackCone + m_etaSafetyFactor) continue;
147 
148  // track has sufficient momentum and is close in eta:
149  // find intersection at calo surface
150  double qOverP = perigee.parameters()[Trk::qOverP];
152  double cotTheta = std::tan(M_PI_2 - perigee.parameters()[Trk::theta]);
153  Amg::Vector3D direction(std::cos(perigee.parameters()[Trk::phi]), std::sin(perigee.parameters()[Trk::phi]), cotTheta);
154  direction /= direction.mag();
155 
156  const Trk::TrackSurfaceIntersection idIntersection(perigee.position(), direction, 0.);
157  const Trk::Surface* surface = m_caloCylinder.get();
158  if (cotTheta > m_barrelCotTheta) {
159  surface = m_caloForwardDisc.get();
160  } else if (cotTheta < -m_barrelCotTheta) {
161  surface = m_caloBackwardDisc.get();
162  }
163  std::optional<Trk::TrackSurfaceIntersection> caloIntersection(
164  m_intersector->intersectSurface(*surface, idIntersection, qOverP));
165 
166  // no intersection - should never happen !
167  if (!caloIntersection) {
168  ATH_MSG_DEBUG(" track didn't find intersection !!! "
169  << std::setiosflags(std::ios::fixed) << " Id track: momentum " << std::setw(8) << std::setprecision(1)
170  << perigee.momentum().mag() / Gaudi::Units::GeV << " with initial eta " << std::setw(8)
171  << std::setprecision(3) << perigee.eta() << " and phi " << std::setw(8) << std::setprecision(3)
172  << perigee.parameters()[Trk::phi]);
173 
174  continue;
175  }
176 
177  double diffEta = eta - caloIntersection->position().eta();
178  double diffPhi = xAOD::P4Helpers::deltaPhi(phi, caloIntersection->position().phi());
179  ATH_MSG_VERBOSE(std::endl
180  << std::setiosflags(std::ios::fixed) << " Id track: momentum " << std::setw(8) << std::setprecision(1)
181  << perigee.momentum().mag() / Gaudi::Units::GeV << " with initial,extrapolated and calo difference for eta "
182  << std::setw(8) << std::setprecision(3) << perigee.eta() << std::setw(8) << std::setprecision(3)
183  << caloIntersection->position().eta() << std::setw(8) << std::setprecision(3) << diffEta << " and phi "
184  << std::setw(8) << std::setprecision(3) << perigee.parameters()[Trk::phi] << std::setw(8)
185  << std::setprecision(3) << caloIntersection->position().phi() << std::setw(8) << std::setprecision(3)
186  << diffPhi);
187 
188  // check if inside cone
189  if ((diffPhi * diffPhi + diffEta * diffEta) < m_trackCone2) {
190  ++numberTracks;
191  const double p = perigee.momentum().mag();
192  sumP += p;
193 
194  ATH_MSG_VERBOSE(" inside cone, track#" << std::setw(3) << numberTracks);
195  }
196  }
197 
198  return std::make_pair(numberTracks, sumP);
199  }
200 
201 } // namespace Rec
GeV
#define GeV
Definition: PhysicsAnalysis/TauID/TauAnalysisTools/Root/HelperFunctions.cxx:17
TrackParameters.h
Rec::MuidTrackIsolation::m_minPt
Gaudi::Property< double > m_minPt
Definition: MuidTrackIsolation.h:57
ATH_MSG_INFO
#define ATH_MSG_INFO(x)
Definition: AthMsgStreamMacros.h:31
SG::ReadHandle::cptr
const_pointer_type cptr()
Dereference the pointer.
Surface.h
Trk::Track
The ATLAS Track class.
Definition: Tracking/TrkEvent/TrkTrack/TrkTrack/Track.h:73
SG::ReadHandle
Definition: StoreGate/StoreGate/ReadHandle.h:70
xAODP4Helpers.h
Trk::ParametersT
Dummy class used to allow special convertors to be called for surfaces owned by a detector element.
Definition: EMErrorDetail.h:25
Rec::MuidTrackIsolation::m_caloForwardDisc
std::unique_ptr< const Trk::Surface > m_caloForwardDisc
Definition: MuidTrackIsolation.h:52
xAOD::P4Helpers::deltaPhi
double deltaPhi(double phiA, double phiB)
delta Phi in range [-pi,pi[
Definition: xAODP4Helpers.h:69
Rec::MuidTrackIsolation::m_etaSafetyFactor
double m_etaSafetyFactor
Definition: MuidTrackIsolation.h:53
Trk::TrackSurfaceIntersection
Definition: TrackSurfaceIntersection.h:32
Rec::MuidTrackIsolation::trackExtrapolated
std::pair< int, double > trackExtrapolated(const TrackCollection *indetTracks, double eta, double phi) const
Definition: MuidTrackIsolation.cxx:135
drawFromPickle.cos
cos
Definition: drawFromPickle.py:36
ATH_MSG_VERBOSE
#define ATH_MSG_VERBOSE(x)
Definition: AthMsgStreamMacros.h:28
InDetAccessor::qOverP
@ qOverP
perigee
Definition: InDetAccessor.h:35
Rec::MuidTrackIsolation::m_trackExtrapolation
Gaudi::Property< bool > m_trackExtrapolation
Definition: MuidTrackIsolation.h:60
Track.h
Trk::TrackInfo::StraightTrack
@ StraightTrack
A straight track.
Definition: Tracking/TrkEvent/TrkTrack/TrkTrack/TrackInfo.h:84
MuidTrackIsolation.h
Rec::MuidTrackIsolation::trackIsolation
std::pair< int, double > trackIsolation(const EventContext &ctx, double eta, double phi) const override
IMuidTrackIsolation interface: get the number of tracks and summed momentum in a cone at the producti...
Definition: MuidTrackIsolation.cxx:65
python.utils.AtlRunQueryDQUtils.p
p
Definition: AtlRunQueryDQUtils.py:210
python.SystemOfUnits.meter
int meter
Definition: SystemOfUnits.py:61
Rec::MuidTrackIsolation::trackVertex
std::pair< int, double > trackVertex(const TrackCollection *indetTracks, double eta, double phi) const
Definition: MuidTrackIsolation.cxx:101
Rec::MuidTrackIsolation::initialize
StatusCode initialize() override
Definition: MuidTrackIsolation.cxx:35
Rec
Name: MuonSpContainer.h Package : offline/Reconstruction/MuonIdentification/muonEvent.
Definition: FakeTrackBuilder.h:10
Trk::theta
@ theta
Definition: ParamDefs.h:66
Rec::MuidTrackIsolation::m_trackCone2
double m_trackCone2
Definition: MuidTrackIsolation.h:59
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
Amg::Transform3D
Eigen::Affine3d Transform3D
Definition: GeoPrimitives.h:46
TrackCollection.h
Amg::transform
Amg::Vector3D transform(Amg::Vector3D &v, Amg::Transform3D &tr)
Transform a point from a Trasformation3D.
Definition: GeoPrimitivesHelpers.h:156
CylinderSurface.h
test_pyathena.parent
parent
Definition: test_pyathena.py:15
Rec::MuidTrackIsolation::m_trackCone
Gaudi::Property< double > m_trackCone
Definition: MuidTrackIsolation.h:58
ATH_CHECK
#define ATH_CHECK
Definition: AthCheckMacros.h:40
Rec::MuidTrackIsolation::MuidTrackIsolation
MuidTrackIsolation(const std::string &type, const std::string &name, const IInterface *parent)
Definition: MuidTrackIsolation.cxx:28
drawFromPickle.tan
tan
Definition: drawFromPickle.py:36
DataVector< Trk::Track >
SG::ReadHandle::isValid
virtual bool isValid() override final
Can the handle be successfully dereferenced?
Rec::MuidTrackIsolation::m_intersector
ToolHandle< Trk::IIntersector > m_intersector
Definition: MuidTrackIsolation.h:56
generateBunchGroupSetFromOldKey.transform2
def transform2(oldbgs, bgsname, bgnames)
Definition: generateBunchGroupSetFromOldKey.py:37
id
SG::auxid_t id
Definition: Control/AthContainers/Root/debug.cxx:227
name
std::string name
Definition: Control/AthContainers/Root/debug.cxx:228
Rec::MuidTrackIsolation::m_caloCylinder
std::unique_ptr< const Trk::Surface > m_caloCylinder
Definition: MuidTrackIsolation.h:51
Amg::Vector3D
Eigen::Matrix< double, 3, 1 > Vector3D
Definition: GeoPrimitives.h:47
ParticleGun_SamplingFraction.radius
radius
Definition: ParticleGun_SamplingFraction.py:96
ATH_MSG_WARNING
#define ATH_MSG_WARNING(x)
Definition: AthMsgStreamMacros.h:32
python.CaloScaleNoiseConfig.type
type
Definition: CaloScaleNoiseConfig.py:78
Rec::MuidTrackIsolation::m_caloBackwardDisc
std::unique_ptr< const Trk::Surface > m_caloBackwardDisc
Definition: MuidTrackIsolation.h:50
Trk::qOverP
@ qOverP
perigee
Definition: ParamDefs.h:67
DiscSurface.h
TRT::Track::cotTheta
@ cotTheta
Definition: InnerDetector/InDetCalibEvent/TRT_CalibData/TRT_CalibData/TrackInfo.h:65
Trk::phi
@ phi
Definition: ParamDefs.h:75
SG::VarHandleBase::isPresent
bool isPresent() const
Is the referenced object present in SG?
Definition: StoreGate/src/VarHandleBase.cxx:394
drawFromPickle.sin
sin
Definition: drawFromPickle.py:36
AthAlgTool
Definition: AthAlgTool.h:26
TrackSurfaceIntersection.h
Trk::Surface
Definition: Tracking/TrkDetDescr/TrkSurfaces/TrkSurfaces/Surface.h:75
Rec::MuidTrackIsolation::m_inDetTracksLocation
SG::ReadHandleKey< TrackCollection > m_inDetTracksLocation
Definition: MuidTrackIsolation.h:54
Rec::MuidTrackIsolation::m_barrelCotTheta
double m_barrelCotTheta
Definition: MuidTrackIsolation.h:49