ATLAS Offline Software
Loading...
Searching...
No Matches
EventAnalysis.h
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2020 CERN for the benefit of the ATLAS collaboration
3*/
4
5
6// Bit of an abstract class ( not in the C++ sense )
7// designed to apply a bunch of cuts & chop up the data
8
9#ifndef IDPERFMON_EVENTANALYSIS_H
10#define IDPERFMON_EVENTANALYSIS_H
11
12
13// Crap that may stay or go
14#include "CLHEP/Vector/LorentzVector.h"
16
17#include <map>
18#include <vector>
19
20class TH1F;
21class TH2F;
22class TProfile;
23class TProfile2D;
24
25namespace EAna
26{
27 const float g_fMuonMass = ParticleConstants::muonMassInMeV/1000.; // Convert MeV to GeV
28 const float g_fElecMass = ParticleConstants::electronMassInMeV/1000.; // Convert MeV to GeV
29 const float CGeV = 1.0e-3;
30}
31
33{
34 public:
36 virtual ~EventAnalysis();
37
38 // Overridden functions.
39 virtual void Init();
40 static constexpr float invalidAnswer{-999.9f};
41
42 // Static Util. function declarations. Defined below class. Can use if no inheritance struct.
43 template<class T> static CLHEP::Hep3Vector calculateMomentum(const T * pP);
44 template<class T> static float EvalInvMass( const T* pxP1, const T* pxP2,
45 float fMass1, float fMass2 = invalidAnswer );
46 template<class T> static float EvalInvMass( const T* pxP1, const T* pxP2, const T* pxp3, const T* pxP4,
47 float fMass1, float fMass2 = -999.9, float fMass3 = -999.9, float fMass4 = invalidAnswer );
48 template<class T> static float EvalDiMuInvMass( const T* pxP1, const T* pxP2 );
49 template<class T> static float EvalFourMuInvMass( const T* pxP1, const T* pxP2, const T* pxP3, const T* pxP4);
50 template<class T> static float EvaluateAngle( const T* pxP1, const T* pxP2 );
51 template<class T> static float EvalPtDiff( const T* pxP1, const T* pxP2 );
52 template<class T> static float EvalPhiDiff( const T* pxP1, const T* pxP2 );
53 template<class T> static float EvalEtaDiff( const T* pxP1, const T* pxP2 );
54
55 template<class T> static float EvalPt( const T* pxP1, const T* pxP2 );
56 template<class T> static float EvalPhi( const T* pxP1, const T* pxP2 );
57 template<class T> static float EvalEta( const T* pxP1, const T* pxP2 );
58 template<class T> static float EvalCharge( const T* pxP1, const T* pxP2 );
59
60 template<class T> static float EvalTransverseMass( const T* pxP1,float fMETx, float fMETy,
61 float fMass1, float fMass2 = invalidAnswer);
62 template<class T> static float EvalTransverseMass( const T* pxP1, float fMETx, float fMETy );
63
64 template<class T> static float EvalTransverseMass( const T* pxP1, const T* pxP2,
65 float fMETx, float fMETy,
66 float fMass1, float fMass2 = invalidAnswer);
67 template<class T> static float EvalTransverseMass( const T* pxP1, const T* pxP2,
68 float fMETx, float fMETy );
69
70
71
72 protected:
73 virtual void BookHistograms();
74
75 unsigned int m_uPassedEvents;
76 std::map<unsigned int, TH1F*> m_x1DHistograms;
77 std::map<unsigned int, TH2F*> m_x2DHistograms;
78 std::map<unsigned int, TProfile*> m_x1DProfHistograms;
79 std::map<unsigned int, TProfile2D*> m_x2DProfHistograms;
80
81 std::string m_xSampleName;
82
83 private:
84 void Register(); // Register the histograms.
85};
86
87
88//=============================================================================
89// Useful static functions defined here
90//=============================================================================
91template<class T> CLHEP::Hep3Vector
93 const auto & p4(pP->p4());
94 return CLHEP::Hep3Vector(p4.Px() * EAna::CGeV , p4.Py() * EAna::CGeV, p4.Pz() * EAna::CGeV);
95}
96
97// 2 Particle Invariant Mass
98template<class T> float EventAnalysis::EvalDiMuInvMass( const T* pxP1, const T* pxP2 )
99{
100 // Check integrity of inputs.
101 if ( !pxP1 || !pxP2 ) return invalidAnswer;
102
103 // Evaluate Di-mu invariant mass.
104 return EvalInvMass( pxP1, pxP2, EAna::g_fMuonMass );
105}
106
107template<class T> float EventAnalysis::EvalInvMass( const T* pxP1, const T* pxP2,
108 float fMass1, float fMass2 /* = -999.9 */ )
109{
110 // Check integrity of inputs.No tachyons.
111 if ( fMass1 < 0.0f ) return invalidAnswer;
112 if ( !pxP1 || !pxP2 ) return invalidAnswer;
113 // Set masses equal if required by user
114 fMass2 = ( fMass2 < 0.0f ) ? fMass1 : fMass2;
115 // Evaluate invariant mass.
116 CLHEP::Hep3Vector xTmp1 = calculateMomentum(pxP1);
117 CLHEP::Hep3Vector xTmp2 = calculateMomentum(pxP2);
118 CLHEP::HepLorentzVector xLVec1; xLVec1.setVectM( xTmp1, fMass1 );
119 CLHEP::HepLorentzVector xLVec2; xLVec2.setVectM( xTmp2, fMass2 );
120 return static_cast<float>( xLVec1.invariantMass( xLVec2 ) );
121}
122
123// 4 Particle Invariant Mass
124template<class T> float EventAnalysis::EvalFourMuInvMass( const T* pxP1, const T* pxP2, const T* pxP3, const T* pxP4 )
125{
126 // Check integrity of inputs.
127 if ( !pxP1 || !pxP2 || !pxP3 || !pxP4) return invalidAnswer;
128
129 // Evaluate invariant mass.
130 return EvalInvMass( pxP1, pxP2, pxP3, pxP4, EAna::g_fMuonMass );
131}
132
133template<class T> float EventAnalysis::EvalInvMass( const T* pxP1, const T* pxP2, const T* pxP3, const T* pxP4,
134 float fMass1, float fMass2, float fMass3, float fMass4 /* = -999.9 */ )
135{
136 // Check integrity of inputs.No tachyons.
137 if ( fMass1 < 0.0f ) return invalidAnswer;
138 if ( !pxP1 || !pxP2 || !pxP3 || !pxP4) return invalidAnswer;
139
140 // Set masses equal if required by user
141 fMass2 = ( fMass2 < 0.0f ) ? fMass1 : fMass2;
142 fMass3 = ( fMass3 < 0.0f ) ? fMass1 : fMass3;
143 fMass4 = ( fMass4 < 0.0f ) ? fMass1 : fMass4;
144
145 // Evaluate invariant mass.
146 CLHEP::Hep3Vector xTmp1 = CLHEP::Hep3Vector( pxP1->p4().Px() * EAna::CGeV, pxP1->p4().Py() * EAna::CGeV, pxP1->p4().Pz() * EAna::CGeV );
147 CLHEP::Hep3Vector xTmp2 = CLHEP::Hep3Vector( pxP2->p4().Px() * EAna::CGeV, pxP2->p4().Py() * EAna::CGeV, pxP2->p4().Pz() * EAna::CGeV );
148 CLHEP::Hep3Vector xTmp3 = CLHEP::Hep3Vector( pxP3->p4().Px() * EAna::CGeV, pxP3->p4().Py() * EAna::CGeV, pxP3->p4().Pz() * EAna::CGeV );
149 CLHEP::Hep3Vector xTmp4 = CLHEP::Hep3Vector( pxP4->p4().Px() * EAna::CGeV, pxP4->p4().Py() * EAna::CGeV, pxP4->p4().Pz() * EAna::CGeV );
150
151 CLHEP::HepLorentzVector xLVec; xLVec.setVectM ( xTmp1, fMass1 );
152 CLHEP::HepLorentzVector xLVec2; xLVec2.setVectM( xTmp2, fMass2 );
153 CLHEP::HepLorentzVector xLVec3; xLVec3.setVectM( xTmp3, fMass3 );
154 CLHEP::HepLorentzVector xLVec4; xLVec4.setVectM( xTmp4, fMass4 );
155
156 xLVec += xLVec2;
157 xLVec += xLVec3;
158 xLVec += xLVec4;
159
160 return static_cast<float>( xLVec.m() );
161}
162
163// Angle Between two particles
164template<class T> float EventAnalysis::EvaluateAngle( const T* pxP1, const T* pxP2 )
165{
166 // Check integrity of inputs.
167 if ( !pxP1 || !pxP2 ) return invalidAnswer;
168 // Evaluate the angle.
169 CLHEP::Hep3Vector xTmp1 = calculateMomentum(pxP1);
170 CLHEP::Hep3Vector xTmp2 = calculateMomentum(pxP2);
171 return static_cast<float>( xTmp1.angle(xTmp2) );
172}
173
174template<class T> float EventAnalysis::EvalPtDiff( const T* pxP1, const T* pxP2 )
175{
176 // Check integrity of inputs.
177 if ( !pxP1 || !pxP2 ) return invalidAnswer;
178 // Evaluate the difference between the momenta. Signed using positive - negative if appropriate.
179 if ( pxP1->charge() > 0.5f )
180 {
181 return static_cast<float>( pxP1->pt() * EAna::CGeV - pxP2->pt() * EAna::CGeV );
182 }
183 else
184 {
185 return static_cast<float>( pxP2->pt() * EAna::CGeV - pxP1->pt() * EAna::CGeV );
186 }
187}
188
189
190
191template<class T> float EventAnalysis::EvalPhiDiff( const T* pxP1, const T* pxP2 )
192{
193 // Check integrity of inputs.
194 if ( !pxP1 || !pxP2 ) return invalidAnswer;
195 // Evaluate the angle.
196 CLHEP::Hep3Vector xTmp1 = calculateMomentum(pxP1);
197 CLHEP::Hep3Vector xTmp2 = calculateMomentum(pxP2);
198 return static_cast<float>( xTmp1.deltaPhi(xTmp2) );
199}
200
201
202template<class T> float EventAnalysis::EvalEtaDiff( const T* pxP1, const T* pxP2 )
203{
204 // Check integrity of inputs.
205 if ( !pxP1 || !pxP2 ) return invalidAnswer;
206 // Evaluate the angle.
207 CLHEP::Hep3Vector xTmp1 = calculateMomentum(pxP1);
208 CLHEP::Hep3Vector xTmp2 = calculateMomentum(pxP2);
209 return static_cast<float>( xTmp1.polarAngle(xTmp2) );
210}
211
212template<class T> float EventAnalysis::EvalPt( const T* pxP1, const T* pxP2 )
213{
214 // Check integrity of inputs.
215 if ( !pxP1 || !pxP2 ) return invalidAnswer;
216 CLHEP::Hep3Vector xTmp1 = calculateMomentum(pxP1);
217 CLHEP::Hep3Vector xTmp2 = calculateMomentum(pxP2);
218 return static_cast<float>( (xTmp1 + xTmp2).perp() );
219}
220
221template<class T> float EventAnalysis::EvalPhi( const T* pxP1, const T* pxP2 )
222{
223 // Check integrity of inputs.
224 if ( !pxP1 || !pxP2 ) return invalidAnswer;
225 CLHEP::Hep3Vector xTmp1 = calculateMomentum(pxP1);
226 CLHEP::Hep3Vector xTmp2 = calculateMomentum(pxP2);
227 return static_cast<float>( (xTmp1 + xTmp2).phi() );
228}
229
230template<class T> float EventAnalysis::EvalEta( const T* pxP1, const T* pxP2 )
231{
232 // Check integrity of inputs.
233 if ( !pxP1 || !pxP2 ) return invalidAnswer;
234 CLHEP::Hep3Vector xTmp1 = calculateMomentum(pxP1);
235 CLHEP::Hep3Vector xTmp2 = calculateMomentum(pxP2);
236 return static_cast<float>( (xTmp1 + xTmp2).pseudoRapidity() );
237}
238
239template<class T> float EventAnalysis::EvalCharge( const T* pxP1, const T* pxP2 )
240{
241 // Check integrity of inputs.
242 if ( !pxP1 || !pxP2 ) return invalidAnswer;
243 return static_cast<float>( pxP1->charge() + pxP2->charge() );
244}
245
246// Transverse Mass - 1 Particle + MET
247template<class T> float EventAnalysis::EvalTransverseMass( const T* pxP1, float fMETx, float fMETy )
248{
249 // Check integrity of inputs.
250 if ( !pxP1 ) return invalidAnswer;
251 // Evaluate Di-mu invariant mass.
252 return EvalInvMass( pxP1, fMETx, fMETy, EAna::g_fMuonMass );
253}
254
255template<class T> float EventAnalysis::EvalTransverseMass( const T* pxP1, float fMETx, float fMETy,
256 float fMass1, float fMass2 /* = -999.9 */ )
257{
258 // Check integrity of inputs.No tachyons.
259 if ( fMass1 < 0.0f ) return invalidAnswer;
260 if ( !pxP1 ) return invalidAnswer;
261 // Set masses equal if required by user.
262 fMass2 = ( fMass2 < 0.0f ) ? fMass1 : fMass2;
263 // Evaluate invariant mass.
264 CLHEP::Hep3Vector xTmp1 = CLHEP::Hep3Vector( pxP1->p4().Px() * EAna::CGeV, pxP1->p4().Py() * EAna::CGeV, 0.0f );
265 CLHEP::Hep3Vector xTmp2 = CLHEP::Hep3Vector( fMETx, fMETy, 0.0f );
266 CLHEP::HepLorentzVector xLVec1; xLVec1.setVectM( xTmp1, fMass1 );
267 CLHEP::HepLorentzVector xLVec2; xLVec2.setVectM( xTmp2, 0.0f );
268 return static_cast<float>( xLVec1.invariantMass( xLVec2 ) );
269}
270
271// Transverse Mass - 2 Particles + MET
272template<class T> float EventAnalysis::EvalTransverseMass( const T* pxP1, const T* pxP2, float fMETx, float fMETy )
273{
274 // Check integrity of inputs.
275 if ( !pxP1 || !pxP2 ) return invalidAnswer;
276 // Evaluate Di-mu invariant mass.
277 return EvalTransverseMass( pxP1, pxP2, fMETx, fMETy, EAna::g_fMuonMass );
278}
279
280template<class T> float EventAnalysis::EvalTransverseMass( const T* pxP1, const T* pxP2, float fMETx, float fMETy,
281 float fMass1, float fMass2 /* = -999.9 */ )
282{
283 // Check integrity of inputs.No tachyons.
284 if ( fMass1 < 0.0f ) return invalidAnswer;
285 if ( !pxP1 || !pxP2 ) return invalidAnswer;
286 // Set masses equal if required by user.
287 fMass2 = ( fMass2 < 0.0f ) ? fMass1 : fMass2;
288 // Evaluate invariant mass.
289 CLHEP::Hep3Vector xTmp1 = CLHEP::Hep3Vector( pxP1->p4().Px() * EAna::CGeV, pxP1->p4().Py() * EAna::CGeV, 0.0f );
290 CLHEP::Hep3Vector xTmp2 = CLHEP::Hep3Vector( pxP2->p4().Px() * EAna::CGeV, pxP2->p4().Py() * EAna::CGeV, 0.0f );
291 CLHEP::Hep3Vector xTmp12 = xTmp1 + xTmp2;
292 CLHEP::Hep3Vector xTmp3 = CLHEP::Hep3Vector( fMETx, fMETy, 0.0f );
293 CLHEP::HepLorentzVector xLVec1; xLVec1.setVectM( xTmp12, fMass1 );
294 CLHEP::HepLorentzVector xLVec2; xLVec2.setVectM( xTmp3, 0.0f );
295 return static_cast<float>( xLVec1.invariantMass( xLVec2 ) );
296}
297
298//=============================================================================
299
300#endif
A number of constexpr particle constants to avoid hardcoding them directly in various places.
static float EvaluateAngle(const T *pxP1, const T *pxP2)
std::map< unsigned int, TProfile2D * > m_x2DProfHistograms
std::map< unsigned int, TH2F * > m_x2DHistograms
static float EvalDiMuInvMass(const T *pxP1, const T *pxP2)
static float EvalCharge(const T *pxP1, const T *pxP2)
virtual ~EventAnalysis()
std::map< unsigned int, TH1F * > m_x1DHistograms
static float EvalPhi(const T *pxP1, const T *pxP2)
virtual void BookHistograms()
static float EvalPtDiff(const T *pxP1, const T *pxP2)
static float EvalTransverseMass(const T *pxP1, float fMETx, float fMETy, float fMass1, float fMass2=invalidAnswer)
virtual void Init()
std::map< unsigned int, TProfile * > m_x1DProfHistograms
static CLHEP::Hep3Vector calculateMomentum(const T *pP)
static constexpr float invalidAnswer
static float EvalPt(const T *pxP1, const T *pxP2)
static float EvalEtaDiff(const T *pxP1, const T *pxP2)
static float EvalFourMuInvMass(const T *pxP1, const T *pxP2, const T *pxP3, const T *pxP4)
unsigned int m_uPassedEvents
static float EvalPhiDiff(const T *pxP1, const T *pxP2)
static float EvalEta(const T *pxP1, const T *pxP2)
std::string m_xSampleName
static float EvalInvMass(const T *pxP1, const T *pxP2, float fMass1, float fMass2=invalidAnswer)
const float g_fMuonMass
const float CGeV
const float g_fElecMass
constexpr double muonMassInMeV
the mass of the muon (in MeV)
constexpr double electronMassInMeV
the mass of the electron (in MeV)
TH1F(name, title, nxbins, bins_par2, bins_par3=None, path='', **kwargs)