ATLAS Offline Software
Loading...
Searching...
No Matches
DecoratePromptLeptonImproved.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2025 CERN for the benefit of the ATLAS collaboration
3*/
4
5// Local
8
9// ROOT
10#include "TMVA/Config.h"
11#include "TH1.h"
12
13// C/C++
14#include <cmath>
15#include <iostream>
16#include <sstream>
17#include <sys/stat.h>
18
19
20namespace {
21
22
23// Accessor constants.
24static const SG::ConstAccessor<float> accessCalIsolation30 ("topoetcone30");
25static const SG::ConstAccessor<float> accessTrackIsolation30 ("ptvarcone30");
26static const SG::ConstAccessor<float> accessTrackIsolation30TTVA ("ptvarcone30_Nonprompt_All_MaxWeightTTVA_pt500");
27static const SG::ConstAccessor<float> accessMuonCalE ("calE");
28static const SG::ConstAccessor<float> accessMuonParamEnergyLoss ("ParamEnergyLoss");
29
30
31} // anonymous namespace
32
33
34//======================================================================================================
35Prompt::DecoratePromptLeptonImproved::DecoratePromptLeptonImproved(const std::string& name, ISvcLocator* pSvcLocator):
36 AthAlgorithm(name, pSvcLocator),
37 m_BDTVarKey(Def::NONE)
38{}
39
40//=============================================================================
42{
43 ATH_MSG_DEBUG("Initializing DecoratePromptLeptonImproved...");
44 ATH_MSG_DEBUG("m_leptonsName = " << m_leptonsName);
45 if (m_printTime)
46 {
47 //
48 // Reset timers
49 //
50 m_timerAll .Reset();
51 m_timerExec.Reset();
52 m_timerMuon.Reset();
53 m_timerElec.Reset();
54
55 //
56 // Start full timer
57 //
58 m_timerAll.Start();
59 }
60
61 ATH_CHECK(m_trackJetsKey.initialize());
62 ATH_CHECK(m_primaryVertexKey.initialize());
63 ATH_CHECK(m_clusterContainerKey.initialize());
64
65 ATH_MSG_DEBUG("Initializing " << m_electronsKey);
66
67 ATH_CHECK(m_electronsKey.initialize(m_leptonsName == "Electrons"));
68 ATH_CHECK(m_muonsKey.initialize(m_leptonsName == "Muons"));
69
70 ATH_MSG_DEBUG("Number of int vars to read: " << m_stringIntVars.size());
71 ATH_MSG_DEBUG("Number of float vars to read: " << m_stringFloatVars.size());
72
73 // Setup variable holder
74 m_vars = std::make_unique<Prompt::VarHolder>();
75
76 //
77 // Read vector<string> vars into vector<Var> and append
78 //
79 m_intVars = m_vars->readVectorVars(m_stringIntVars);
80 m_floatVars = m_vars->readVectorVars(m_stringFloatVars);
81
82 m_allVars.insert(m_allVars.end(), m_intVars .begin(), m_intVars .end());
83 m_allVars.insert(m_allVars.end(), m_floatVars.begin(), m_floatVars.end());
84
85 m_varTMVA.resize(m_allVars.size());
86
87
88 //
89 // Get key for recording BDT output
90 //
91 m_BDTVarKey = m_vars->registerDynamicVar(m_BDTName);
92
93 if(m_BDTVarKey == Def::NONE) {
94 ATH_MSG_ERROR("Failed to create key for BDT name=" << m_BDTName);
95 return StatusCode::FAILURE;
96 }
97
98 //
99 // Fill decorator maps
100 //
102
103 //
104 // Initialize const accessors
105 //
107
108 ATH_MSG_DEBUG("Initialized DecoratePromptLeptonImproved.");
109
110 //
111 // Initialize TMVA Reader
112 //
114
115 ATH_MSG_DEBUG("Initialized TMVA Reader.");
116
117 return StatusCode::SUCCESS;
118}
119
120//=============================================================================
122{
123 if(m_printTime) {
124 //
125 // Print full time stopwatch
126 //
127 m_timerAll.Stop();
128
129 ATH_MSG_INFO("Real time: " << m_timerAll.RealTime() << "\t CPU time: " << m_timerAll.CpuTime());
130
131 ATH_MSG_INFO("Execute time: " << PrintResetStopWatch(m_timerExec));
134 }
135
136 return StatusCode::SUCCESS;
137}
138
139
140//=============================================================================
141StatusCode Prompt::DecoratePromptLeptonImproved::execute(const EventContext& ctx)
142{
143 //
144 // Start execute timer
145 //
147
148
149 //
150 // Retrieve containers from evtStore
151 //
155
156 ATH_MSG_DEBUG("======================================="
157 << "\n\t\t\t Size of vertex container: " << vertices ->size()
158 << "\n\t\t\t Size of track jet container: " << trackJets->size()
159 << "\n-----------------------------------------------------------------");
160
161 //
162 // Find default Primary Vertex
163 //
164 const xAOD::Vertex *primaryVertex = nullptr;
165
166 for(const xAOD::Vertex *vertex: *vertices) {
167 if(vertex->vertexType() == xAOD::VxType::PriVtx) {
168 primaryVertex = vertex;
169 break;
170 }
171 }
172
173 std::vector<decoratorFloatH_t> floatDecors;
174 floatDecors.reserve (m_floatDecorHandleKeys.size());
176 floatDecors.emplace_back (k, ctx);
177 }
178
179 std::vector<decoratorShortH_t> shortDecors;
180 shortDecors.reserve (m_shortDecorHandleKeys.size());
182 shortDecors.emplace_back (k, ctx);
183 }
184
185 if(m_leptonsName == "Electrons") {
186 //
187 // Process electrons
188 //
189 ATH_MSG_DEBUG("Reading " << m_electronsKey);
191
192 for(const xAOD::Electron *elec: *electrons) {
193 decorateElec(*elec, *trackJets, *clusters, primaryVertex, floatDecors, shortDecors);
194 }
195 } else if(m_leptonsName == "Muons") {
196 //
197 // Process muons
198 //
199 ATH_MSG_DEBUG("Reading " << m_muonsKey);
201
202 for(const xAOD::Muon *muon: *muons) {
203 decorateMuon(*muon, *trackJets, primaryVertex, floatDecors, shortDecors);
204 ATH_MSG_DEBUG("Muon decorated");
205 }
206 } else {
207 ATH_MSG_ERROR("Must specify Electrons or Muons");
208 return StatusCode::FAILURE;
209 }
210
211 return StatusCode::SUCCESS;
212}
213
214
215//=============================================================================
217{
218 //
219 // Make new instance of TMVA Reader and add variables
220 //
221 m_TMVAReader = std::make_unique<TMVA::Reader>();
222
223 for(unsigned i = 0; i < m_allVars.size(); ++i) {
224 m_TMVAReader->AddVariable(m_vars->asStr(m_allVars.at(i)), &m_varTMVA[i]);
225 }
226
227 //
228 // Get path to xml training file
229 //
230 std::string fullPathToFile = PathResolverFindCalibFile("JetTagNonPromptLepton/"
232 + "/TMVAClassification_" + m_methodTitleMVA + ".weights.xml");
233
234 if(!m_configPathOverride.empty()) {
235 ATH_MSG_INFO("Override path resolver result");
236 fullPathToFile = m_configPathOverride;
237 }
238
239 ATH_MSG_INFO("TMVA configuration file: " + fullPathToFile);
240 ATH_MSG_INFO("TMVA method name: " + m_methodTitleMVA);
241
242 //
243 // Book an instance of BDT reader if path is available
244 //
245 if(fullPathToFile == "") {
246 ATH_MSG_ERROR("Could not find path to xml training file");
247 return false;
248 }
249 else {
250 m_TMVAReader->BookMVA(m_methodTitleMVA.toString(), fullPathToFile);
251 }
252
253 return true;
254}
255
256
257//=============================================================================
259{
260 std::string inputContName;
261 if (m_leptonsName == "Electrons") {
262 inputContName = m_electronsKey.key();
263 }
264 else if (m_leptonsName == "Muons") {
265 inputContName = m_muonsKey.key();
266 }
267 else {
268 ATH_MSG_ERROR ("LeptonContainerName was " << m_leptonsName <<
269 "; must be either Electrons or Muons");
270 return StatusCode::FAILURE;
271 }
272
273 DecorMap_t vetoedVars;
274 for(const std::string &vvar: m_vetoDecoratorFloatVars) {
275 const Def::Var vkey = m_vars->registerDynamicVar(vvar);
276
277 if(vkey == Def::NONE) {
278 ATH_MSG_ERROR("Failed to create key for variable name=" << vvar);
279 return StatusCode::FAILURE;
280 }
281
282 vetoedVars.try_emplace (vkey, 0);
283 }
284 for(const std::string &vvar: m_vetoDecoratorShortVars) {
285 const Def::Var vkey = m_vars->registerDynamicVar(vvar);
286
287 if(vkey == Def::NONE) {
288 ATH_MSG_ERROR("Failed to create key for variable name=" << vvar);
289 return StatusCode::FAILURE;
290 }
291
292 vetoedVars.try_emplace (vkey, 0);
293 }
294
295 //
296 // Fill short variable map
297 //
298 for(Prompt::Def::Var &var: m_intVars) {
299 if (!vetoedVars.contains (var)) {
300 m_shortDecorMap.try_emplace (var, m_shortDecorHandleKeys.size());
301 m_shortDecorHandleKeys.push_back (SG::makeContDecorKey (inputContName, m_inputVarDecoratePrefix + m_vars->asStr(var)));
302 }
303 }
304
305 //
306 // Fill float variable map
307 //
309 for(Prompt::Def::Var &var: m_floatVars) {
310 if (!vetoedVars.contains (var)) {
311 m_floatDecorMap.try_emplace (var, m_floatDecorHandleKeys.size());
312 m_floatDecorHandleKeys.push_back (SG::makeContDecorKey (inputContName, m_inputVarDecoratePrefix + m_vars->asStr(var)));
313 }
314 }
315
316 //
317 // Fill additional variables
318 //
319 if (!vetoedVars.contains (m_BDTVarKey)) {
321 m_floatDecorHandleKeys.push_back (SG::makeContDecorKey (inputContName, m_BDTName));
322 }
323
324 for(const std::string &evar: m_extraDecoratorFloatVars) {
325 const Def::Var ekey = m_vars->registerDynamicVar(evar);
326
327 if(ekey == Def::NONE) {
328 ATH_MSG_ERROR("Failed to create key for variable name=" << evar);
329 return StatusCode::FAILURE;
330 }
331
332 if (!vetoedVars.contains (ekey)) {
333 m_floatDecorMap.try_emplace (ekey, m_floatDecorHandleKeys.size());
334 m_floatDecorHandleKeys.push_back (SG::makeContDecorKey (inputContName, m_inputVarDecoratePrefix + evar));
335 }
336 }
337
338 for(const std::string &evar: m_extraDecoratorShortVars) {
339 const Def::Var ekey = m_vars->registerDynamicVar(evar);
340
341 if(ekey == Def::NONE) {
342 ATH_MSG_ERROR("Failed to create key for variable name=" << evar);
343 return StatusCode::FAILURE;
344 }
345
346 if (!vetoedVars.contains (ekey)) {
347 m_shortDecorMap.try_emplace (ekey, m_shortDecorHandleKeys.size());
348 m_shortDecorHandleKeys.push_back (SG::makeContDecorKey (inputContName, m_inputVarDecoratePrefix + evar));
349 }
350 }
351
352 ATH_CHECK(m_shortDecorHandleKeys.initialize());
353 ATH_CHECK(m_floatDecorHandleKeys.initialize());
354
355 // Print decorator counts
356 ATH_MSG_DEBUG("Added " << m_shortDecorHandleKeys.size() << " short decorators");
357 ATH_MSG_DEBUG("Added " << m_floatDecorHandleKeys.size() << " float decorators");
358
359 // Instantiate MVA X bin
360 if(m_leptonPtBinsVector.size() < 2) {
361 ATH_MSG_ERROR("Invalid PtBins size=" << m_leptonPtBinsVector.size());
362 return StatusCode::FAILURE;
363 }
364
365 std::unique_ptr<double []> PtBins = std::make_unique<double []>(m_leptonPtBinsVector.size());
366
367 for(unsigned i = 0; i < m_leptonPtBinsVector.size(); i++) {
368 PtBins[i] = m_leptonPtBinsVector[i];
369 }
370
371 m_leptonPtBinHist = std::make_unique<TH1D>("PtBin", "PtBin", m_leptonPtBinsVector.size() - 1, PtBins.get());
372
373 return StatusCode::SUCCESS;
374}
375
376//=============================================================================
378{
379 //
380 // Instantiate isolation accessors
381 //
383
384 //
385 // Instantiate accessors for RNN variables
386 //
387 for(const std::string &name: m_accessorRNNVars) {
388 const Def::Var akey = m_vars->registerDynamicVar(name);
389
390 if(m_accessRNNMap.insert(floatAccessorMap::value_type(akey, AccessFloat(name))).second) {
391 ATH_MSG_DEBUG("Add float RNN accessor: " << name);
392 }
393 else {
394 ATH_MSG_WARNING("Skip duplicate float accessor: " << name);
395 }
396 }
397}
398
399//=============================================================================
401 const xAOD::Electron &electron,
402 const xAOD::JetContainer &trackJets,
403 const xAOD::CaloClusterContainer &clusters,
404 const xAOD::Vertex *primaryVertex,
405 std::vector<decoratorFloatH_t>& floatDecors,
406 std::vector<decoratorShortH_t>& shortDecors
407)
408{
409 //
410 // Find nearest track jet to electron
411 //
413
415
416 std::pair<double, const xAOD::Jet*> match = findTrackJet(electron, trackJets);
417
418 if(match.second) {
419 //
420 // Get muon calorimeter energy variable, RNN and secondary vertex variables
421 //
422 getElectronAnpVariables(electron, clusters, vars, primaryVertex);
423
424 //
425 // Get mutual variables, passing track as argument
426 //
427 getMutualVariables(electron, *match.second, electron.trackParticle(), vars);
428
429 //
430 // Pass variables to TMVA
431 //
432 addVarsToTMVA(vars);
433 }
434 else {
435 //
436 // Decorate electron with default values
437 //
438 fillVarDefault(vars);
439
440 ATH_MSG_DEBUG("No track jet found near to electron");
441 }
442
443 //
444 // Decorate electron with input vars and BDT weight
445 //
446 decorateAuxLepton(electron, vars, floatDecors, shortDecors);
447}
448
449
450//=============================================================================
452 const xAOD::Muon &muon,
453 const xAOD::JetContainer &trackJets,
454 const xAOD::Vertex *primaryVertex,
455 std::vector<decoratorFloatH_t>& floatDecors,
456 std::vector<decoratorShortH_t>& shortDecors
457)
458{
459 //
460 // Find nearest track jet to muon
461 //
463
465
466 std::pair<double, const xAOD::Jet*> match = findTrackJet(muon, trackJets);
467
468 if(match.second) {
469 //
470 // Get muon calorimeter energy variable, RNN and secondary vertex variables
471 //
472 getMuonAnpVariables(muon, vars, primaryVertex);
473
474 //
475 // Get mutual variables, passing track as argument
476 //
477 getMutualVariables(muon, *match.second, muon.trackParticle(xAOD::Muon::TrackParticleType::Primary), vars);
478
479 //
480 // Add variables to TMVA Reader
481 //
482 addVarsToTMVA(vars);
483 }
484 else {
485 //
486 // Decorate muon with default values
487 //
488 fillVarDefault(vars);
489
490 ATH_MSG_DEBUG("No track jet found near to muon");
491 }
492
493 //
494 // Decorate muon with input vars and BDT weight
495 //
496 decorateAuxLepton(muon, vars, floatDecors, shortDecors);
497}
498
499//=============================================================================
501 const xAOD::Electron &elec,
502 const xAOD::CaloClusterContainer &clusters,
503 Prompt::VarHolder &vars,
504 const xAOD::Vertex *primaryVertex
505)
506{
507 //
508 // Get Muon variables - calorimeter
509 //
510 double sumCoreEt_large = 0.0, CaloClusterSumEtRel = 0.0;
511
512 if(elec.caloCluster()) {
513 const double elec_calEta = elec.caloCluster()->eta();
514 const double elec_calPhi = elec.caloCluster()->phi();
515
516 for(const xAOD::CaloCluster *cluster: clusters) {
517 const double deta = elec_calEta - cluster->eta();
518 const double dphi = TVector2::Phi_mpi_pi(elec_calPhi - cluster->phi());
519 const double dr = std::sqrt(deta*deta + dphi*dphi);
520
521 if(dr < m_elecMinCalErelConeSize) {
522 sumCoreEt_large += cluster->pt();
523 }
524 }
525 }
526
527 if(elec.pt() > 0.0) CaloClusterSumEtRel = sumCoreEt_large/elec.pt();
528
529 vars.addVar(Prompt::Def::CaloClusterSumEtRel, CaloClusterSumEtRel);
530
531 //
532 // Get lepton isolation variables
533 //
534 const double Topoetcone30rel = accessIsolation(accessCalIsolation30, elec);
535 const double Ptvarcone30rel = accessIsolation(accessTrackIsolation30, elec);
536
537 vars.addVar(Prompt::Def::Topoetcone30rel, Topoetcone30rel);
538 vars.addVar(Prompt::Def::Ptvarcone30rel, Ptvarcone30rel);
539
540 //
541 // Get secondary vertex variable
542 //
543 std::vector<double> goodVertexNdistLong;
544
545 if(m_accessDeepSecondaryVertex->isAvailable(elec)) {
546 std::vector<ElementLink<xAOD::VertexContainer> > vtxLinks = (*m_accessDeepSecondaryVertex)(elec);
547
548 for(ElementLink<xAOD::VertexContainer> &vtxLink: vtxLinks) {
549 if(!vtxLink.isValid()) {
550 ATH_MSG_WARNING("VertexContainer : invalid link");
551 continue;
552 }
553
554 const xAOD::Vertex *vtx = *vtxLink;
555
556 const double fitProb = Prompt::getVertexFitProb(vtx);
557
558 if(fitProb < m_vertexMinChiSquaredProb) {
559 continue;
560 }
561
562 const double theta = std::acos(getVertexCosThetaWithLepDir(elec, vtx, primaryVertex));
563
564 if (theta < m_vertexMinThetaBarrElec && std::fabs(elec.eta()) <= m_vertexBarrEcapAbsEtaAt) continue;
565 else if (theta < m_vertexMinThetaEcapElec && std::fabs(elec.eta()) > m_vertexBarrEcapAbsEtaAt) continue;
566
567 const double vertex_ndist_long = getVertexLongitudinalNormDist(elec, vtx, primaryVertex);
568
569 goodVertexNdistLong.push_back(vertex_ndist_long);
570 }
571 }
572 else {
573 ATH_MSG_WARNING("VertexContainer : " << m_vertexLinkName << " not found for the electron");
574 }
575
576 double best_vertex_ndist_long = 0.0;
577
578 if(goodVertexNdistLong.size() > 0) {
579 std::sort(goodVertexNdistLong.begin(), goodVertexNdistLong.end());
580 best_vertex_ndist_long = goodVertexNdistLong.back();
581 }
582
584 vars.addVar(Prompt::Def::CandVertex_NPassVtx, goodVertexNdistLong.size());
585}
586
587//=============================================================================
589 const xAOD::Muon &muon,
590 Prompt::VarHolder &vars,
591 const xAOD::Vertex *primaryVertex
592) const
593{
594 //
595 // Get Muon variables - calorimeter
596 //
597 double calE = -99.0, peloss = -99.0, caloClusterERel = -99.0;
598
599 if(const xAOD::CaloCluster* cluster = muon.cluster()) {
600 if(accessMuonCalE.isAvailable(*cluster) && accessMuonParamEnergyLoss.isAvailable(muon)) {
601 calE = accessMuonCalE(*cluster);
602 peloss = accessMuonParamEnergyLoss(muon);
603
604 caloClusterERel = calE/peloss;
605 }
606 else {
607 ATH_MSG_WARNING("Muon calE or ParamEnergyLoss not found in auxiliary store");
608 }
609 }
610
611 vars.addVar(Prompt::Def::CaloClusterERel, caloClusterERel);
612
613 //
614 // Get lepton isolation variables
615 //
616 const double Topoetcone30rel = accessIsolation(accessCalIsolation30, muon);
617 const double ptvarcone30TightTTVAPt500rel = accessIsolation(accessTrackIsolation30TTVA, muon);
618
619 vars.addVar(Prompt::Def::Topoetcone30rel, Topoetcone30rel);
620 vars.addVar(Prompt::Def::Ptvarcone30_TightTTVA_pt500rel, ptvarcone30TightTTVAPt500rel);
621
622 //
623 // Get Muon Secondary Vertex variable
624 //
625 std::vector<double> goodVertexNdistLong;
626
627 if(m_accessDeepSecondaryVertex->isAvailable(muon)) {
628 std::vector<ElementLink<xAOD::VertexContainer> > vtxLinks = (*m_accessDeepSecondaryVertex)(muon);
629 goodVertexNdistLong.reserve(vtxLinks.size());
630
631 for(ElementLink<xAOD::VertexContainer> &vtxLink: vtxLinks) {
632 if(!vtxLink.isValid()) {
633 ATH_MSG_WARNING("VertexContainer : invalid link");
634 continue;
635 }
636
637 const xAOD::Vertex *vtx = *vtxLink;
638
639 const double fitProb = Prompt::getVertexFitProb(vtx);
640
641 if(fitProb > m_vertexMinChiSquaredProb) {
642 const double vertex_ndist_long = getVertexLongitudinalNormDist(muon, vtx, primaryVertex);
643
644 goodVertexNdistLong.push_back(vertex_ndist_long);
645 }
646 }
647 }
648 else {
649 ATH_MSG_WARNING("VertexContainer : " << m_vertexLinkName << " not found for the muon");
650 }
651
652 double best_vertex_ndist_long = 0.0;
653
654 if(goodVertexNdistLong.size() > 0) {
655 std::sort(goodVertexNdistLong.begin(), goodVertexNdistLong.end());
656 best_vertex_ndist_long = goodVertexNdistLong.back();
657 }
658
660 vars.addVar(Prompt::Def::CandVertex_NPassVtx, goodVertexNdistLong.size());
661}
662
663//=============================================================================
665 const xAOD::IParticle &particle,
666 const xAOD::Jet &track_jet,
667 const xAOD::TrackParticle *track,
669) const
670{
671 //
672 // Add lepton - jet variables to VarHolder
673 //
674 double PtFrac = -99.;
675 double PtRel = -99.;
676
677 if(particle.pt() > 0.0 && track_jet.pt() > 0.0) {
678
679 if(track) {
680 PtFrac = track->pt()/track_jet.pt();
681 }
682
683 const double angle = particle.p4().Vect().Angle(track_jet.p4().Vect());
684
685 PtRel = particle.pt() * std::sin(angle);
686 }
687
688 //
689 // Add vars to VarHolder
690 //
691 vars.addVar(Prompt::Def::PtFrac, PtFrac);
692 vars.addVar(Prompt::Def::PtRel, PtRel);
693 vars.addVar(Prompt::Def::DRlj, track_jet.p4().DeltaR(particle.p4()));
695
696 //
697 // Get RNN variables
698 //
699 for(const floatAccessorMap::value_type &acc: m_accessRNNMap) {
700 if(acc.second.isAvailable(particle)) {
701 vars.addVar(acc.first, acc.second(particle));
702 }
703 else {
704 ATH_MSG_WARNING("LeptonTagger RNN not found in auxiliary store for variable=" << vars.asStr(acc.first));
705 }
706 }
707
708 //
709 // Get lepton variables - pT X bin
710 //
711 const double lepPt = particle.pt();
712
713 const double xmax = m_leptonPtBinHist->GetXaxis()->GetXmax();
714 const double xmin = m_leptonPtBinHist->GetXaxis()->GetXmin();
715
716 int curr_bin = 0;
717
718 if(xmin < lepPt && lepPt < xmax) {
719 curr_bin = m_leptonPtBinHist->FindBin(lepPt);
720 }
721 else if (!(lepPt < xmax)) {
722 curr_bin = m_leptonPtBinHist->GetNbinsX();
723 }
724 else if (!(lepPt > xmin)) {
725 curr_bin = 1;
726 }
727
728 vars.addVar(Prompt::Def::MVAXBin, curr_bin);
729 vars.addVar(Prompt::Def::RawPt, lepPt);
730
731 ATH_MSG_DEBUG("getMutualVariables - lepPt = " << lepPt << ", MVAXBin = " << curr_bin);
732}
733
734//=============================================================================
736 const AccessFloat &isoAccessor,
737 const xAOD::IParticle &particle
738) const {
739 double isolation = -99., isolationrel = -99.;
740
741 if(isoAccessor.isAvailable(particle)) {
742 isolation = isoAccessor(particle);
743 }
744 else {
745 ATH_MSG_WARNING("Lepton isolation not found in auxiliary store");
746 }
747
748 if(particle.pt() > 0.0) {
749 isolationrel = isolation / particle.pt();
750 }
751
752 return isolationrel;
753}
754
755//=============================================================================
757{
758 //
759 // Add variables to TMVA reader
760 //
761 for(unsigned i = 0; i < m_allVars.size(); ++i) {
762 m_varTMVA[i] = 0.0;
763
764 if(!vars.getVar(m_allVars.at(i), m_varTMVA[i])) {
765 ATH_MSG_WARNING("Missing input variable: " << m_vars->asStr(m_allVars.at(i)));
766 }
767 }
768
769 //
770 // Decorate lepton with classifier response, if goodJet
771 //
772 float bdt_weight = m_TMVAReader->EvaluateMVA(m_methodTitleMVA.toString());
773
774 if(m_BDTVarKey != Def::NONE) {
775 vars.addVar(m_BDTVarKey, bdt_weight);
776 }
777 else {
778 ATH_MSG_WARNING("addVarsToTMVA - invalid Def::Var key for " << m_BDTName);
779 }
780}
781
782//=============================================================================
784{
785 //
786 // Add default values to VarHolder
787 //
788 for(const DecorMap_t::value_type &dec: m_floatDecorMap) {
789 vars.addVar(dec.first, -99.0);
790 }
791
792 for(const DecorMap_t::value_type &dec: m_shortDecorMap) {
793 vars.addVar(dec.first, -99.0);
794 }
795}
796
797//=============================================================================
799 const xAOD::IParticle &particle,
800 Prompt::VarHolder &vars,
801 std::vector<decoratorFloatH_t>& floatDecors,
802 std::vector<decoratorShortH_t>& shortDecors
803) const
804{
805 //
806 // Decorate lepton with input short variables
807 //
808 for(const DecorMap_t::value_type &dec: m_shortDecorMap) {
809 double val = 0.0;
810
811 if(vars.getVar(dec.first, val)) {
812 shortDecors.at(dec.second)(particle) = static_cast<short>(val);
813
814 ATH_MSG_DEBUG("Short variable: " << vars.asStr(dec.first) << " = " << val);
815 }
816 else {
817 ATH_MSG_WARNING("Short variable " << vars.asStr(dec.first) << " not decorated to lepton");
818 }
819 }
820
821 //
822 // Decorate lepton with input float variables
823 //
824 for(const DecorMap_t::value_type &dec: m_floatDecorMap) {
825 double val = 0.0;
826
827 if(vars.getVar(dec.first, val)) {
828 floatDecors.at(dec.second)(particle) = val;
829
830 ATH_MSG_DEBUG("Float variable: " << vars.asStr(dec.first) << " = " << val);
831 }
832 else {
833 ATH_MSG_WARNING("Float variable " << vars.asStr(dec.first) << " not decorated to lepton");
834 }
835 }
836}
837
838//=============================================================================
839template<class T> std::pair<double, const xAOD::Jet*> Prompt::DecoratePromptLeptonImproved::findTrackJet(const T &part,
840 const xAOD::JetContainer &jets)
841{
842 //
843 // Find nearest track jet and a return a pair of dR and xAOD::Jet*
844 //
845 const xAOD::Jet *minjet = 0;
846 double mindr = 10.0;
847 std::pair<double, const xAOD::Jet*> match(mindr, minjet);
848
849 for(const xAOD::Jet* jet: jets) {
850 const double dr = part.p4().DeltaR(jet->p4());
851
852 if(!minjet || dr < mindr) {
853 mindr = dr;
854 minjet = jet;
855 match = std::make_pair(mindr, minjet);
856 }
857 }
858
859
860 if(minjet && mindr < m_maxLepTrackJetDR) {
861 return match;
862 }
863
864 minjet = 0;
865 return std::make_pair(10., minjet);
866}
867
868//=============================================================================
870 const xAOD::IParticle &lepton,
871 const xAOD::Vertex *secondaryVertex,
872 const xAOD::Vertex *primaryVertex
873) const
874{
875 //
876 // get the Longitudinal normalized distance between the secondary vertex and primary vertex
877 //
878 if(!secondaryVertex || !primaryVertex) {
879 ATH_MSG_WARNING("getVertexLongitudinalNormDist - invalid pointer of lepton/secondaryVertex/primaryVertex");
880 return 0.0;
881 }
882
883
884 float normDist_SVPV = 0.0;
885
886 if(!Prompt::GetAuxVar(*secondaryVertex, normDist_SVPV, "normDistToPriVtx")) {
887 ATH_MSG_WARNING("getVertexLongitudinalNormDist - missing \"normDistToPriVtx\"");
888 }
889
890 double cos_theta = getVertexCosThetaWithLepDir(lepton, secondaryVertex, primaryVertex);
891
892 return normDist_SVPV*cos_theta;
893}
894
895//=============================================================================
897 const xAOD::Vertex *secondaryVertex,
898 const xAOD::Vertex *primaryVertex) const
899{
900 //
901 // get the Longitudinal nomalized distance between the secondary vertex and primary vertex
902 //
903 if(!secondaryVertex || !primaryVertex) {
904 ATH_MSG_WARNING("GetVertexThetaWithLepDir - invalid pointer of lepton/secondaryVertex/primaryVertex");
905 return 0.0;
906 }
907
908 const Amg::Vector3D sv_to_pv_v3 = secondaryVertex->position() - primaryVertex->position();
909
910 const TVector3 sv_to_pv_t3 = TVector3(sv_to_pv_v3.x(), sv_to_pv_v3.y(), sv_to_pv_v3.z());
911 const TVector3 lepton_dirt = lepton.p4().Vect();
912
913 const double cos_theta = sv_to_pv_t3.Unit()*lepton_dirt.Unit();
914
915 return cos_theta;
916}
917
Scalar theta() const
theta method
#define ATH_CHECK
Evaluate an expression and check for errors.
#define ATH_MSG_ERROR(x)
#define ATH_MSG_INFO(x)
#define ATH_MSG_WARNING(x)
#define ATH_MSG_DEBUG(x)
std::string PathResolverFindCalibFile(const std::string &logical_file_name)
size_t size() const
Number of registered mappings.
double angle(const GeoTrf::Vector2D &a, const GeoTrf::Vector2D &b)
AthAlgorithm(const std::string &name, ISvcLocator *pSvcLocator)
Constructor.
std::pair< double, const xAOD::Jet * > findTrackJet(const T &part, const xAOD::JetContainer &jets)
Gaudi::Property< std::string > m_configFileVersion
Gaudi::Property< std::vector< double > > m_leptonPtBinsVector
Gaudi::Property< std::vector< std::string > > m_vetoDecoratorShortVars
void getMutualVariables(const xAOD::IParticle &particle, const xAOD::Jet &track_jet, const xAOD::TrackParticle *track, Prompt::VarHolder &vars) const
SG::ReadHandleKey< xAOD::VertexContainer > m_primaryVertexKey
SG::WriteDecorHandleKeyArray< xAOD::IParticleContainer > m_shortDecorHandleKeys
Gaudi::Property< std::vector< std::string > > m_stringFloatVars
std::unordered_map< Def::Var, size_t > DecorMap_t
Gaudi::Property< std::vector< std::string > > m_extraDecoratorShortVars
SG::WriteDecorHandleKeyArray< xAOD::IParticleContainer > m_floatDecorHandleKeys
SG::ReadHandleKey< xAOD::CaloClusterContainer > m_clusterContainerKey
double getVertexCosThetaWithLepDir(const xAOD::IParticle &lepton, const xAOD::Vertex *secondaryVertex, const xAOD::Vertex *primaryVertex) const
void fillVarDefault(Prompt::VarHolder &vars) const
Gaudi::Property< std::string > m_inputVarDecoratePrefix
SG::ReadHandleKey< xAOD::ElectronContainer > m_electronsKey
void decorateElec(const xAOD::Electron &electron, const xAOD::JetContainer &trackJets, const xAOD::CaloClusterContainer &clusters, const xAOD::Vertex *primaryVertex, std::vector< decoratorFloatH_t > &floatDecors, std::vector< decoratorShortH_t > &shortDecors)
DecoratePromptLeptonImproved(const std::string &name, ISvcLocator *pSvcLocator)
void getMuonAnpVariables(const xAOD::Muon &muon, Prompt::VarHolder &vars, const xAOD::Vertex *primaryVertex) const
Gaudi::Property< std::vector< std::string > > m_extraDecoratorFloatVars
void getElectronAnpVariables(const xAOD::Electron &elec, const xAOD::CaloClusterContainer &clusters, Prompt::VarHolder &vars, const xAOD::Vertex *primaryVertex)
Gaudi::Property< std::vector< std::string > > m_accessorRNNVars
double getVertexLongitudinalNormDist(const xAOD::IParticle &lepton, const xAOD::Vertex *secondaryVertex, const xAOD::Vertex *primaryVertex) const
SG::ReadHandleKey< xAOD::MuonContainer > m_muonsKey
void decorateAuxLepton(const xAOD::IParticle &particle, Prompt::VarHolder &vars, std::vector< decoratorFloatH_t > &floatDecors, std::vector< decoratorShortH_t > &shortDecors) const
std::unique_ptr< Prompt::VarHolder > m_vars
Gaudi::Property< std::vector< std::string > > m_vetoDecoratorFloatVars
std::optional< AccessVertex > m_accessDeepSecondaryVertex
virtual StatusCode execute(const EventContext &ctx) override
Execute method.
Gaudi::Property< std::string > m_configPathOverride
Gaudi::Property< std::vector< std::string > > m_stringIntVars
float accessIsolation(const SG::ConstAccessor< float > &isoAccessor, const xAOD::IParticle &particle) const
SG::ReadHandleKey< xAOD::JetContainer > m_trackJetsKey
void decorateMuon(const xAOD::Muon &muon, const xAOD::JetContainer &trackJets, const xAOD::Vertex *primaryVertex, std::vector< decoratorFloatH_t > &floatDecors, std::vector< decoratorShortH_t > &shortDecors)
double getVar(const unsigned key) const
Definition VarHolder.h:265
std::string asStr(const uint32_t key, const double val)
bool addVar(unsigned key, double value)
Adds a variable to the VarHolder.
Definition VarHolder.h:200
Helper class to provide constant type-safe access to aux data.
bool isAvailable(const ELT &e) const
Test to see if this variable exists in the store.
Property holding a SG store/key/clid/attr name from which a WriteDecorHandle is made.
virtual double eta() const
The pseudorapidity ( ) of the particle.
virtual double phi() const
The azimuthal angle ( ) of the particle.
virtual double pt() const override final
The transverse momentum ( ) of the particle.
Definition Egamma_v1.cxx:66
virtual double eta() const override final
The pseudorapidity ( ) of the particle.
Definition Egamma_v1.cxx:71
const xAOD::CaloCluster * caloCluster(size_t index=0) const
Pointer to the xAOD::CaloCluster/s that define the electron candidate.
Class providing the definition of the 4-vector interface.
virtual FourMom_t p4() const =0
The full 4-momentum of the particle.
size_t size() const
number of constituents
virtual FourMom_t p4() const
The full 4-momentum of the particle.
Definition Jet_v1.cxx:71
JetConstituentVector getConstituents() const
Return a vector of consituents. The object behaves like vector<const IParticle*>. See JetConstituentV...
Definition Jet_v1.cxx:149
virtual double pt() const
The transverse momentum ( ) of the particle.
Definition Jet_v1.cxx:44
const Amg::Vector3D & position() const
Returns the 3-pos.
bool match(std::string s1, std::string s2)
match the individual directories of two strings
Definition hcg.cxx:359
double xmax
Definition listroot.cxx:61
double xmin
Definition listroot.cxx:60
Eigen::Matrix< double, 3, 1 > Vector3D
@ Topoetcone30rel
Definition VarHolder.h:60
@ CandVertex_normDistToPriVtxLongitudinalBest_ThetaCutVtx
Definition VarHolder.h:69
@ CandVertex_NPassVtx
Definition VarHolder.h:70
@ Ptvarcone30_TightTTVA_pt500rel
Definition VarHolder.h:62
@ CaloClusterSumEtRel
Definition VarHolder.h:66
@ CaloClusterERel
Definition VarHolder.h:65
@ CandVertex_normDistToPriVtxLongitudinalBest
Definition VarHolder.h:68
bool GetAuxVar(const T1 &obj, T2 &value, const std::string &var_name)
Definition PromptUtils.h:83
std::string PrintResetStopWatch(TStopwatch &watch)
double getVertexFitProb(const xAOD::Vertex *vtx)
std::string makeContDecorKey(const std::string &cont, const std::string &decor)
Make a StoreGate key from container and decoration name.
void sort(typename DataModel_detail::iterator< DVL > beg, typename DataModel_detail::iterator< DVL > end)
Specialization of sort for DataVector/List.
@ PriVtx
Primary vertex.
Jet_v1 Jet
Definition of the current "jet version".
CaloCluster_v1 CaloCluster
Define the latest version of the calorimeter cluster class.
TrackParticle_v1 TrackParticle
Reference the current persistent version:
Vertex_v1 Vertex
Define the latest version of the vertex class.
Muon_v1 Muon
Reference the current persistent version:
CaloClusterContainer_v1 CaloClusterContainer
Define the latest version of the calorimeter cluster container.
JetContainer_v1 JetContainer
Definition of the current "jet container version".
Electron_v1 Electron
Definition of the current "egamma version".