ATLAS Offline Software
Loading...
Searching...
No Matches
TrigGlobEffCorr::Calculator Class Reference

#include <Calculator.h>

Inheritance diagram for TrigGlobEffCorr::Calculator:
Collaboration diagram for TrigGlobEffCorr::Calculator:

Classes

class  Helper
struct  Period

Public Member Functions

 Calculator (TrigGlobalEfficiencyCorrectionTool &parent, unsigned nPeriodsToReserve)
bool addPeriod (ImportData &data, const std::pair< unsigned, unsigned > &boundaries, const std::string &combination, bool useToys, std::size_t &uniqueElectronLeg, std::size_t &uniquePhotonLeg)
bool compute (TrigGlobalEfficiencyCorrectionTool &parent, const LeptonList &leptons, unsigned runNumber, Efficiencies &efficiencies)
bool checkTriggerMatching (TrigGlobalEfficiencyCorrectionTool &parent, bool &matched, const LeptonList &leptons, unsigned runNumber)
bool checkTriggerMatching (TrigGlobalEfficiencyCorrectionTool &parent, bool &matched, std::unordered_map< std::string, bool > *matched_per_trigger, const LeptonList &leptons, unsigned runNumber)
bool getRelevantTriggersForUser (TrigGlobalEfficiencyCorrectionTool &parent, std::vector< std::string > &triggers, unsigned runNumber)
void setLevel (MSG::Level lvl)
 Change the current logging level.
Functions providing the same interface as AthMessaging
bool msgLvl (const MSG::Level lvl) const
 Test the output level of the object.
MsgStream & msg () const
 The standard message stream.
MsgStream & msg (const MSG::Level lvl) const
 The standard message stream.

Private Types

using LeptonList = TrigGlobalEfficiencyCorrectionTool::LeptonList
using TrigDef = TrigGlobEffCorr::ImportData::TrigDef
using GlobEffFunc

Private Member Functions

bool aboveThreshold (const Lepton &p, std::size_t leg) const
template<typename Trig1L>
auto getLoosestLegAboveThreshold (const Lepton &lepton, const flat_set< Trig1L > &trigs, bool &success) -> std::enable_if_t< Trig1L::is1L(), std::size_t >
Efficiencies getCachedTriggerLegEfficiencies (const Lepton &lepton, unsigned runNumber, std::size_t leg, bool &success)
bool fillListOfLegsFor (const Lepton &lepton, const std::vector< TrigDef > &triggers, flat_set< std::size_t > &validLegs) const
bool canTriggerBeFired (const TrigDef &trig, const std::vector< flat_set< std::size_t > > &firedLegs) const
const PeriodgetPeriod (unsigned runNumber) const
bool findUniqueLeg (xAOD::Type::ObjectType obj, std::size_t &uniqueLeg, const std::vector< TrigDef > &defs)
template<typename Trig1L>
auto globalEfficiency (const LeptonList &, unsigned, const Trig1L, Efficiencies &) -> std::enable_if_t< Trig1L::is1L(), bool >
 One single-lepton trigger.
template<typename Trig1L_obj1, typename Trig1L_obj2>
auto globalEfficiency (const LeptonList &, unsigned, const Trig1L_obj1 trig1, const Trig1L_obj2 trig2, Efficiencies &) -> std::enable_if_t< Trig1L_obj1::is1L() &&Trig1L_obj2::is1L() &&Trig1L_obj1::object() !=Trig1L_obj2::object(), bool >
 Two single-lepton triggers, two object types.
template<typename Trig1L>
auto globalEfficiency (const LeptonList &, unsigned, const flat_set< Trig1L > &, Efficiencies &) -> std::enable_if_t< Trig1L::is1L(), bool >
 Several single-lepton triggers, one object type.
template<typename Trig1L_obj1, typename Trig1L_obj2>
auto globalEfficiency (const LeptonList &, unsigned, const flat_set< Trig1L_obj1 > &trigs1, const flat_set< Trig1L_obj2 > &trigs2, Efficiencies &) -> std::enable_if_t< Trig1L_obj1::is1L() &&Trig1L_obj2::is1L() &&Trig1L_obj1::object() !=Trig1L_obj2::object(), bool >
 Several single-lepton triggers, two object types.
template<typename Trig2Lmix>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2Lmix, Efficiencies &) -> std::enable_if_t< Trig2Lmix::is2Lmix(), bool >
 One mixed-flavour dilepton trigger.
template<typename Trig2Lsym>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2Lsym, Efficiencies &) -> std::enable_if_t< Trig2Lsym::is2Lsym(), bool >
 One symmetric dilepton trigger.
template<typename Trig2Lasym>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2Lasym, Efficiencies &) -> std::enable_if_t< Trig2Lasym::is2Lasym(), bool >
 One asymmetric dilepton trigger.
template<typename Trig2Lmix, typename Trig1L_obj1, typename Trig1L_obj2>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2Lmix, const flat_set< Trig1L_obj1 > &, const flat_set< Trig1L_obj2 > &, Efficiencies &) -> std::enable_if_t< Trig2Lmix::is2Lmix() &&Trig1L_obj1::is1L() &&Trig2Lmix::object1()==Trig1L_obj1::object() &&Trig1L_obj2::is1L() &&Trig2Lmix::object2()==Trig1L_obj2::object(), bool >
 One mixed-flavour dilepton trigger + single-lepton triggers.
template<typename Trig2L, typename Trig1L>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2L, const Trig1L, Efficiencies &) -> std::enable_if_t< Trig2L::is2Lnomix() &&Trig1L::is1L() &&Trig2L::object()==Trig1L::object(), bool >
 One dilepton trigger + one single-lepton trigger.
template<typename Trig2Lsym, typename Trig1L>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2Lsym, const flat_set< Trig1L > &, Efficiencies &) -> std::enable_if_t< Trig2Lsym::is2Lsym() &&Trig1L::is1L() &&Trig1L::object()==Trig2Lsym::object(), bool >
 One symmetric dilepton trigger + several single-lepton triggers.
template<typename Trig2Lasym, typename Trig1L>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2Lasym, const flat_set< Trig1L > &, Efficiencies &) -> std::enable_if_t< Trig2Lasym::is2Lasym() &&Trig1L::is1L() &&Trig1L::object()==Trig2Lasym::object(), bool >
 One asymmetric dilepton trigger + several single-lepton triggers.
template<typename Trig2Lsym, typename Trig1L>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2Lsym, const Trig2Lsym, const flat_set< Trig1L > &, Efficiencies &) -> std::enable_if_t< Trig2Lsym::is2Lsym() &&Trig1L::is1L() &&Trig1L::object()==Trig2Lsym::object(), bool >
 Two symmetric dilepton triggers + several single-lepton triggers.
template<typename Trig2Lasym, typename Trig2Lsym, typename Trig1L>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2Lasym, const Trig2Lsym, const flat_set< Trig1L > &, Efficiencies &) -> std::enable_if_t< Trig2Lasym::is2Lasym() &&Trig2Lsym::is2Lsym() &&Trig2Lsym::object()==Trig2Lasym::object() &&Trig1L::is1L() &&Trig1L::object()==Trig2Lasym::object(), bool >
 Two dilepton triggers (one asym., one sym.) + several single-lepton triggers.
template<typename Trig3Lsym>
auto globalEfficiency (const LeptonList &, unsigned, const Trig3Lsym, Efficiencies &) -> std::enable_if_t< Trig3Lsym::is3Lsym(), bool >
 One symmetric trilepton trigger.
template<typename Trig3Lhalfsym>
auto globalEfficiency (const LeptonList &, unsigned, const Trig3Lhalfsym, Efficiencies &) -> std::enable_if_t< Trig3Lhalfsym::is3Lhalfsym(), bool >
 One half-symmetric trilepton trigger.
template<typename Trig2L, typename Trig2Lmix>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2L, const Trig2Lmix, Efficiencies &) -> std::enable_if_t< Trig2L::is2Lnomix() &&Trig2Lmix::is2Lmix() &&(Trig2Lmix::object1()==Trig2L::object()||Trig2Lmix::object2()==Trig2L::object()), bool >
 One dilepton trigger + one mixed-flavour dilepton trigger.
template<typename Trig2L_obj1, typename Trig2L_obj2, typename Trig2Lmix>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2L_obj1, const Trig2L_obj2, const Trig2Lmix, Efficiencies &) -> std::enable_if_t< Trig2Lmix::is2Lmix() &&Trig2L_obj1::is2Lnomix() &&Trig2L_obj1::object()==Trig2Lmix::object1() &&Trig2L_obj2::is2Lnomix() &&Trig2L_obj2::object()==Trig2Lmix::object2(), bool >
 Combinaisons with 3 dilepton triggers including one mixed-flavour, and one sym.
template<typename Trig2L_obj1, typename Trig2L_obj2, typename Trig2Lmix, typename Trig1L_obj1, typename Trig1L_obj2>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2L_obj1, const Trig2L_obj2, const Trig2Lmix, const flat_set< Trig1L_obj1 > &, const flat_set< Trig1L_obj2 > &, Efficiencies &) -> std::enable_if_t< Trig2Lmix::is2Lmix() &&Trig2L_obj1::is2Lnomix() &&Trig2L_obj1::object()==Trig2Lmix::object1() &&Trig2L_obj2::is2Lnomix() &&Trig2L_obj2::object()==Trig2Lmix::object2() &&Trig1L_obj1::is1L() &&Trig1L_obj1::object()==Trig2Lmix::object1() &&Trig1L_obj2::is1L() &&Trig1L_obj2::object()==Trig2Lmix::object2(), bool >
 Same combinaisons with 3 dilepton triggers, + single-lepton triggers.
template<typename Trig2L_obj1, typename Trig2Lsym_obj1, typename Trig2L_obj2, typename Trig2Lsym_obj2, typename Trig2Lmix, typename Trig1L_obj1, typename Trig1L_obj2>
auto globalEfficiency (const LeptonList &, unsigned, const Trig2L_obj1, const Trig2Lsym_obj1, const Trig2L_obj2, const Trig2Lsym_obj2, const Trig2Lmix, const Trig2Lmix, const flat_set< Trig1L_obj1 > &, const flat_set< Trig1L_obj2 > &, Efficiencies &) -> std::enable_if_t< Trig2Lmix::is2Lmix() &&Trig2L_obj1::is2Lnomix() &&Trig2L_obj1::object()==Trig2Lmix::object1() &&Trig2L_obj2::is2Lnomix() &&Trig2L_obj2::object()==Trig2Lmix::object2() &&Trig2Lsym_obj1::is2Lsym() &&Trig2Lsym_obj1::object()==Trig2Lmix::object1() &&Trig2Lsym_obj2::is2Lsym() &&Trig2Lsym_obj2::object()==Trig2Lmix::object2() &&Trig1L_obj1::is1L() &&Trig1L_obj1::object()==Trig2Lmix::object1() &&Trig1L_obj2::is1L() &&Trig1L_obj2::object()==Trig2Lmix::object2(), bool >
 Six dilepton triggers (two mixed-flavour, two sym., two asym.
template<typename Trig3Lmix>
auto globalEfficiency (const LeptonList &, unsigned, const Trig3Lmix, Efficiencies &) -> std::enable_if_t< Trig3Lmix::is3Lmix(), bool >
 One mixed-flavour trilepton trigger.
template<typename Trig3Lmix1, typename Trig3Lmix2>
auto globalEfficiency (const LeptonList &, unsigned, const Trig3Lmix1, const Trig3Lmix2, Efficiencies &) -> std::enable_if_t< Trig3Lmix1::is3Lmix() &&Trig3Lmix2::is3Lmix() &&Trig3Lmix1::object1()==Trig3Lmix2::object2() &&Trig3Lmix1::object2()==Trig3Lmix2::object1(), bool >
 Two complementary mixed-flavour trilepton triggers.
template<typename Trig4Lsym>
auto globalEfficiency (const LeptonList &, unsigned, const Trig4Lsym, Efficiencies &) -> std::enable_if_t< Trig4Lsym::is4Lsym(), bool >
 One symmetric tetralepton trigger.
bool globalEfficiency_Factorized2 (const LeptonList &leptons, unsigned runNumber, GlobEffFunc func1, GlobEffFunc func2, Efficiencies &globalEfficiencies)
bool globalEfficiency_Factorized3 (const LeptonList &leptons, unsigned runNumber, GlobEffFunc func1, GlobEffFunc func2, GlobEffFunc func3, Efficiencies &globalEfficiencies)
bool globalEfficiency_Toys (const LeptonList &, unsigned, const std::vector< TrigDef > &triggers, Efficiencies &)
void initMessaging () const
 Initialize our message level and MessageSvc.

Private Attributes

TrigGlobalEfficiencyCorrectionToolm_parent
std::vector< Periodm_periods
 pointer updated at each call to compute() because the parent tool might have been moved in-between
std::map< std::pair< const Lepton *, std::size_t >, Efficienciesm_cachedEfficiencies
bool m_forceUnitSF
std::string m_nm
 Message source name.
boost::thread_specific_ptr< MsgStream > m_msg_tls
 MsgStream instance (a std::cout like with print-out levels)
std::atomic< IMessageSvc * > m_imsg { nullptr }
 MessageSvc pointer.
std::atomic< MSG::Level > m_lvl { MSG::NIL }
 Current logging level.
std::atomic_flag m_initialized ATLAS_THREAD_SAFE = ATOMIC_FLAG_INIT
 Messaging initialized (initMessaging)

Friends

class CheckConfig

Detailed Description

Definition at line 26 of file Calculator.h.

Member Typedef Documentation

◆ GlobEffFunc

Initial value:
std::function<bool(Calculator*, const LeptonList&,
unsigned, Efficiencies&)>
TrigGlobalEfficiencyCorrectionTool::LeptonList LeptonList
Definition Calculator.h:27
Calculator(TrigGlobalEfficiencyCorrectionTool &parent, unsigned nPeriodsToReserve)

Definition at line 29 of file Calculator.h.

◆ LeptonList

◆ TrigDef

Constructor & Destructor Documentation

◆ Calculator()

Calculator::Calculator ( TrigGlobalEfficiencyCorrectionTool & parent,
unsigned nPeriodsToReserve )

Definition at line 22 of file Calculator.cxx.

24 : asg::AsgMessaging(&parent), m_parent(&parent) {
25 msg().setLevel(parent.msg().level());
26 m_periods.reserve(nPeriodsToReserve);
27}
TrigGlobalEfficiencyCorrectionTool * m_parent
Definition Calculator.h:66
std::vector< Period > m_periods
pointer updated at each call to compute() because the parent tool might have been moved in-between
Definition Calculator.h:69
MsgStream & msg() const
The standard message stream.
AsgMessaging(const std::string &name)
Constructor with a name.

Member Function Documentation

◆ aboveThreshold()

bool TrigGlobEffCorr::Calculator::aboveThreshold ( const Lepton & p,
std::size_t leg ) const
inlineprivate

Definition at line 74 of file Calculator.h.

74 {
75 return m_parent->aboveThreshold(p, leg);
76 }

◆ addPeriod()

bool Calculator::addPeriod ( ImportData & data,
const std::pair< unsigned, unsigned > & boundaries,
const std::string & combination,
bool useToys,
std::size_t & uniqueElectronLeg,
std::size_t & uniquePhotonLeg )

Choose the appropriate function to compute efficiencies for this particular trigger combination

Definition at line 29 of file Calculator.cxx.

33 {
34 bool success = true;
35 m_parent = data.getParent();
36
37 auto triggers = data.parseTriggerString(combination, success);
38 if (!success)
39 return false;
40 if (!triggers.size()) {
41 ATH_MSG_ERROR("The trigger combination is empty!");
42 return false;
43 }
44
45 if (!findUniqueLeg(xAOD::Type::Electron, uniqueElectronLeg, triggers))
46 return false;
47 if (!findUniqueLeg(xAOD::Type::Photon, uniquePhotonLeg, triggers))
48 return false;
49
52 Helper helper(triggers);
53 if (helper.duplicates()) {
54 ATH_MSG_ERROR("The following combination of triggers contains duplicates: "
55 << combination);
56 return false;
57 }
58 if (!useToys) {
59 success = helper.findAndBindFunction();
60 if (!helper.m_formula) {
62 "This trigger combination is currently not supported with an "
63 "explicit formula (you may use toys instead, slower): "
64 << combination);
65 return false;
66 }
67 } else {
68 helper.m_formula = std::bind(&Calculator::globalEfficiency_Toys, ::_1, ::_2,
69 ::_3, triggers, ::_4);
70 }
71 if (success) {
72 if (data.adaptTriggerListForTriggerMatching(triggers)) {
73 m_periods.emplace_back(boundaries, std::move(helper.m_formula),
74 std::move(triggers));
75 } else {
76 if (m_parent->m_validTrigMatchTool)
77 return false;
78 m_periods.emplace_back(boundaries, std::move(helper.m_formula));
79 }
80 } else {
82 "Unspecified error occurred while trying to find the formula for the "
83 "trigger combination "
84 << combination);
85 }
86 return success;
87}
#define ATH_MSG_ERROR(x)
char data[hepevt_bytes_allocation_ATLAS]
Definition HepEvt.cxx:11
bool findUniqueLeg(xAOD::Type::ObjectType obj, std::size_t &uniqueLeg, const std::vector< TrigDef > &defs)
bool globalEfficiency_Toys(const LeptonList &, unsigned, const std::vector< TrigDef > &triggers, Efficiencies &)
@ Photon
The object is a photon.
Definition ObjectType.h:47
@ Electron
The object is an electron.
Definition ObjectType.h:46

◆ canTriggerBeFired()

bool Calculator::canTriggerBeFired ( const TrigDef & trig,
const std::vector< flat_set< std::size_t > > & firedLegs ) const
private

Definition at line 1476 of file Calculator.cxx.

1478 {
1479 const int nLegs = static_cast<int>(std::count_if(
1480 trig.leg.begin(), trig.leg.end(), [](auto x) { return x != 0ul; }));
1481 const int sameLegs = static_cast<int>(
1482 std::count(trig.leg.begin(), trig.leg.end(), trig.leg[0]));
1483 if (sameLegs == nLegs) {
1484 // single-lepton and symmetric multilepton triggers
1485 return std::count_if(firedLegs.cbegin(), firedLegs.cend(), [&](auto& legs) {
1486 return legs.count(trig.leg[0]);
1487 }) >= nLegs;
1488 } else if (nLegs == 2) {
1489 // asymmetric or mixed-flavour dilepton triggers
1490 bool n0 = false, n1 = false;
1491 for (auto& legs : firedLegs) {
1492 if (n0 && legs.count(trig.leg[1]))
1493 return true;
1494 if (n1 && legs.count(trig.leg[0]))
1495 return true;
1496 n0 = n0 || legs.count(trig.leg[0]);
1497 n1 = n1 || legs.count(trig.leg[1]);
1498 }
1499 } else if (nLegs == 3) {
1500 // other trilepton triggers
1501 auto end = firedLegs.end();
1502 for (auto legs0 = firedLegs.begin(); legs0 != end; ++legs0) {
1503 for (int i = 0; i < 3; ++i) {
1504 if (!legs0->count(trig.leg[i]))
1505 continue;
1506 for (auto legs1 = legs0 + 1; legs1 != end; ++legs1) {
1507 for (int j = 1; j < 3; ++j) {
1508 if (!legs1->count(trig.leg[(i + j) % 3]))
1509 continue;
1510 for (auto legs2 = legs1 + 1; legs2 != end; ++legs2) {
1511 if (legs2->count(trig.leg[(i + 3 - j) % 3]))
1512 return true;
1513 }
1514 }
1515 }
1516 }
1517 }
1518 } else {
1519 ATH_MSG_ERROR("incomplete support of 4-lepton triggers.");
1520 }
1521 return false;
1522}
#define x

◆ checkTriggerMatching() [1/2]

bool TrigGlobEffCorr::Calculator::checkTriggerMatching ( TrigGlobalEfficiencyCorrectionTool & parent,
bool & matched,
const LeptonList & leptons,
unsigned runNumber )

◆ checkTriggerMatching() [2/2]

bool Calculator::checkTriggerMatching ( TrigGlobalEfficiencyCorrectionTool & parent,
bool & matched,
std::unordered_map< std::string, bool > * matched_per_trigger,
const LeptonList & leptons,
unsigned runNumber )

First, for each lepton, list the trigger leg(s) it is allowed to fire (depends on pT and selection tags)

Then for each trigger, call trigger matching tool for all possible (valid) lepton combinations

Get trigger chain name with a "HLT_" prefix

borrow the set of legs that can be fired by that lepton

return the set of legs back to the main container

Definition at line 144 of file Calculator.cxx.

147 {
148 matched = false;
149 if(matched_per_trigger) {
150 for(auto& [key, flag] : *matched_per_trigger) flag = false;
151 }
152
153 m_parent = &parent;
154 auto period = getPeriod(runNumber);
155 if (!period)
156 return false;
157 if (!period->m_triggers.size()) {
158 ATH_MSG_ERROR("Empty list of triggers for run number " << runNumber);
159 return false;
160 }
161 auto& trigMatchTool = m_parent->m_trigMatchTool;
162
165 const unsigned nLep = leptons.size();
166 std::vector<flat_set<std::size_t>> validLegs(leptons.size());
167 for (unsigned i = 0; i < nLep; ++i) {
168 if (!fillListOfLegsFor(leptons[i], period->m_triggers, validLegs[i]))
169 return false;
170 }
171
174 std::vector<flat_set<std::size_t>> firedLegs;
175 std::vector<const xAOD::IParticle*> trigLeptons;
176 const std::size_t magicWordHLT = 0xf7b8b87ef2917d66;
177
178 for (auto& trig : period->m_triggers) {
180 auto itr = m_parent->m_dictionary.find(trig.name ^ magicWordHLT);
181 if (itr == m_parent->m_dictionary.end()) {
182 itr = m_parent->m_dictionary
183 .emplace(trig.name ^ magicWordHLT,
184 "HLT_" + m_parent->m_dictionary.at(trig.name))
185 .first;
186 }
187 const std::string& chain = itr->second;
188
189 unsigned nLegs = 0;
190 if (trig.type & TT_SINGLELEPTON_FLAG)
191 nLegs = 1;
192 else if (trig.type & TT_DILEPTON_FLAG)
193 nLegs = 2;
194 else if (trig.type & TT_TRILEPTON_FLAG)
195 nLegs = 3;
196 else {
197 ATH_MSG_ERROR("Unsupported trigger (type = "
198 << std::hex << trig.type << std::dec << ") " << chain);
199 return false;
200 }
201 firedLegs.resize(nLegs);
202 trigLeptons.resize(nLegs);
203 for (unsigned i0 = 0; i0 < nLep; ++i0) {
204 firedLegs[0].swap(validLegs[i0]);
206 trigLeptons[0] = leptons[i0].particle();
207 if (nLegs == 1) {
208 // Check we have enough lepton(s) on trigger plateau and test the trigger matching
209 if(canTriggerBeFired(trig, firedLegs) && trigMatchTool->match(trigLeptons, chain)) {
210 matched = true;
211 if(!matched_per_trigger) return true;
212 if(matched_per_trigger->count(chain)) matched_per_trigger->at(chain) = true;
213 }
214 } else
215 for (unsigned i1 = i0 + 1; i1 < nLep; ++i1) {
216 firedLegs[1].swap(validLegs[i1]);
217 trigLeptons[1] = leptons[i1].particle();
218 if (nLegs == 2) {
219 if(canTriggerBeFired(trig, firedLegs) && trigMatchTool->match(trigLeptons, chain)) {
220 matched = true;
221 if(!matched_per_trigger) return true;
222 if(matched_per_trigger->count(chain)) matched_per_trigger->at(chain) = true;
223 }
224 } else
225 for (unsigned i2 = i1 + 1; i2 < nLep; ++i2) {
226 firedLegs[2].swap(validLegs[i2]);
227 trigLeptons[2] = leptons[i2].particle();
228 if(canTriggerBeFired(trig, firedLegs) && trigMatchTool->match(trigLeptons, chain)) {
229 matched = true;
230 if(!matched_per_trigger) return true;
231 if(matched_per_trigger->count(chain)) matched_per_trigger->at(chain) = true;
232 }
233 firedLegs[2].swap(validLegs[i2]);
234 }
235 firedLegs[1].swap(validLegs[i1]);
236 }
237 firedLegs[0].swap(
238 validLegs[i0]);
239 }
240 }
241 return true;
242}
bool canTriggerBeFired(const TrigDef &trig, const std::vector< flat_set< std::size_t > > &firedLegs) const
bool fillListOfLegsFor(const Lepton &lepton, const std::vector< TrigDef > &triggers, flat_set< std::size_t > &validLegs) const
const Period * getPeriod(unsigned runNumber) const
bool flag
Definition master.py:29

◆ compute()

bool Calculator::compute ( TrigGlobalEfficiencyCorrectionTool & parent,
const LeptonList & leptons,
unsigned runNumber,
Efficiencies & efficiencies )

Definition at line 125 of file Calculator.cxx.

127 {
128 m_parent = &parent;
129 m_forceUnitSF = false;
130 auto period = getPeriod(runNumber);
131 if (!period)
132 return false;
133 m_cachedEfficiencies.clear();
134 bool success = period->m_formula &&
135 period->m_formula(this, leptons, runNumber, efficiencies);
136 if (m_forceUnitSF) {
137 efficiencies.data() = 1.;
138 efficiencies.mc() = 1.;
139 success = true;
140 }
141 return success;
142}
std::map< std::pair< const Lepton *, std::size_t >, Efficiencies > m_cachedEfficiencies
Definition Calculator.h:71
list efficiencies
translate the station name indices into the string staiton name

◆ fillListOfLegsFor()

bool Calculator::fillListOfLegsFor ( const Lepton & lepton,
const std::vector< TrigDef > & triggers,
flat_set< std::size_t > & validLegs ) const
private

Definition at line 1458 of file Calculator.cxx.

1460 {
1461 validLegs.clear();
1462 for (auto& trig : triggers) {
1463 TriggerProperties tp(trig);
1464 if (!tp.valid()) {
1465 ATH_MSG_ERROR("Unrecognized trigger type " << trig.type);
1466 return false;
1467 }
1468 auto end = tp.cend(lepton.type());
1469 for (auto itr = tp.cbegin(lepton.type()); itr != end; ++itr)
1470 if (aboveThreshold(lepton, *itr))
1471 validLegs.emplace(*itr);
1472 }
1473 return true;
1474}
bool aboveThreshold(const Lepton &p, std::size_t leg) const
Definition Calculator.h:74
xAOD::Type::ObjectType type() const
Definition Lepton.h:29

◆ findUniqueLeg()

bool Calculator::findUniqueLeg ( xAOD::Type::ObjectType obj,
std::size_t & uniqueLeg,
const std::vector< TrigDef > & defs )
private

initial non-zero value means that ListOfLegsPerTool is filled

Definition at line 89 of file Calculator.cxx.

91 {
92 if (uniqueLeg)
93 return true;
95 for (auto& def : defs) {
96 TriggerProperties tp(def);
97 for (auto itr = tp.cbegin(obj); itr != tp.cend(obj); ++itr) {
98 if (uniqueLeg && uniqueLeg != *itr) {
100 "The property 'ListOfLegsPerTool' needs to be filled as the "
101 "specified trigger combination involves several electron (or "
102 "photon) trigger legs");
103 return false;
104 }
105 uniqueLeg = *itr;
106 }
107 }
108 return true;
109}

◆ getCachedTriggerLegEfficiencies()

Efficiencies Calculator::getCachedTriggerLegEfficiencies ( const Lepton & lepton,
unsigned runNumber,
std::size_t leg,
bool & success )
private

Definition at line 276 of file Calculator.cxx.

279 {
280 auto insertion = m_cachedEfficiencies.emplace(std::make_pair(&lepton, leg),
281 Efficiencies());
282 Efficiencies& efficiencies = insertion.first->second;
283 if (insertion.second) {
285 switch (lepton.type()) {
287 res = m_parent->getTriggerLegEfficiencies(
288 lepton.electron(), runNumber, leg, lepton.tag(), efficiencies);
289 break;
290 case xAOD::Type::Muon:
291 res = m_parent->getTriggerLegEfficiencies(lepton.muon(), runNumber, leg,
292 lepton.tag(), efficiencies);
293 break;
295 res = m_parent->getTriggerLegEfficiencies(
296 lepton.photon(), runNumber, leg, lepton.tag(), efficiencies);
297 break;
298 default:
299 ATH_MSG_ERROR("Unsupported particle type");
300 }
301 switch (res) {
303 break;
305 m_forceUnitSF = true;
306 break;
308 [[fallthrough]];
309 default:
310 success = false;
311 efficiencies.data() = -777.;
312 efficiencies.mc() = -777.;
313 }
314 }
315 if (efficiencies.mc() == -777. && !m_forceUnitSF)
316 success = false;
317 return efficiencies;
318}
std::pair< std::vector< unsigned int >, bool > res
TrigGlobEffCorr::Efficiencies Efficiencies
const xAOD::Muon * muon() const
Definition Lepton.h:34
std::size_t tag() const
Definition Lepton.h:30
const xAOD::Electron * electron() const
Definition Lepton.h:31
const xAOD::Photon * photon() const
Definition Lepton.h:37
@ Muon
The object is a muon.
Definition ObjectType.h:48

◆ getLoosestLegAboveThreshold()

template<typename Trig1L>
auto TrigGlobEffCorr::Calculator::getLoosestLegAboveThreshold ( const Lepton & lepton,
const flat_set< Trig1L > & trigs,
bool & success ) -> std::enable_if_t<Trig1L::is1L(), std::size_t>
inlineprivate

Definition at line 78 of file Calculator.h.

80 {
81 return m_parent->getLoosestLegAboveThreshold(
82 lepton, Trig1L::anonymize(trigs), success);
83 }

◆ getPeriod()

const Calculator::Period * Calculator::getPeriod ( unsigned runNumber) const
private

Definition at line 111 of file Calculator.cxx.

111 {
112 auto period =
113 std::find_if(m_periods.cbegin(), m_periods.cend(), [=](const Period& p) {
114 return runNumber >= p.m_boundaries.first &&
115 runNumber <= p.m_boundaries.second;
116 });
117 if (period == m_periods.end()) {
118 ATH_MSG_ERROR("No trigger combination has been specified for run "
119 << runNumber);
120 return nullptr;
121 }
122 return &*period;
123}

◆ getRelevantTriggersForUser()

bool Calculator::getRelevantTriggersForUser ( TrigGlobalEfficiencyCorrectionTool & parent,
std::vector< std::string > & triggers,
unsigned runNumber )

Definition at line 244 of file Calculator.cxx.

246 {
247 triggers.clear();
248 m_parent = &parent;
249 auto period = getPeriod(runNumber);
250 if (!period)
251 return false;
252 if (!period->m_triggers.size()) {
253 ATH_MSG_ERROR("Empty list of triggers for run number "
254 << runNumber
255 << " (was there a configuration issue? please check for "
256 "warnings during initialization)");
257 return false;
258 }
259 bool success = true;
260 auto notfound = parent.m_dictionary.end();
261 for (auto& trig : period->m_triggers) {
262 auto itr = parent.m_dictionary.find(trig.name);
263 if (itr == notfound) {
264 ATH_MSG_ERROR("can't retrieve name of trigger with hash "
265 << trig.name
266 << " (shouldn't happen; contact tool developers!)");
267 success = false;
268 } else
269 triggers.push_back(itr->second);
270 }
271 if (!success)
272 triggers.clear();
273 return success;
274}

◆ globalEfficiency() [1/22]

template<typename Trig1L>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const flat_set< Trig1L > & trigs,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig1L::is1L(), bool>
private

Several single-lepton triggers, one object type.

Definition at line 388 of file Calculator.cxx.

391 {
392 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Several1L() at line "
393 << __LINE__);
394 if (trigs.size() == 1)
395 return globalEfficiency(leptons, runNumber, *trigs.cbegin(),
396 globalEfficiencies);
397 if (!trigs.size()) {
398 globalEfficiencies = {0.};
399 return true;
400 }
401 globalEfficiencies = {1.};
402 bool success = true;
403 for (auto& lepton : leptons) {
404 if (Trig1L::irrelevantFor(lepton))
405 continue;
406 std::size_t loosestLeg =
407 getLoosestLegAboveThreshold(lepton, trigs, success);
408 if (loosestLeg && success) {
409 auto efficiencies = getCachedTriggerLegEfficiencies(lepton, runNumber,
410 loosestLeg, success);
411 globalEfficiencies *= ~efficiencies;
412 }
413 }
414 globalEfficiencies = ~globalEfficiencies;
415 return success;
416}
#define ATH_MSG_DEBUG(x)
auto globalEfficiency(const LeptonList &, unsigned, const Trig1L, Efficiencies &) -> std::enable_if_t< Trig1L::is1L(), bool >
One single-lepton trigger.
auto getLoosestLegAboveThreshold(const Lepton &lepton, const flat_set< Trig1L > &trigs, bool &success) -> std::enable_if_t< Trig1L::is1L(), std::size_t >
Definition Calculator.h:78
Efficiencies getCachedTriggerLegEfficiencies(const Lepton &lepton, unsigned runNumber, std::size_t leg, bool &success)

◆ globalEfficiency() [2/22]

template<typename Trig1L_obj1, typename Trig1L_obj2>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const flat_set< Trig1L_obj1 > & trigs1,
const flat_set< Trig1L_obj2 > & trigs2,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig1L_obj1::is1L() && Trig1L_obj2::is1L() && Trig1L_obj1::object() != Trig1L_obj2::object(), bool>
private

Several single-lepton triggers, two object types.

Definition at line 422 of file Calculator.cxx.

428 {
429 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Several1L() at line "
430 << __LINE__);
431 if (trigs1.size() == 1 && trigs2.size() == 1) {
432 return globalEfficiency(leptons, runNumber, *trigs1.cbegin(),
433 *trigs2.cbegin(), globalEfficiencies);
434 }
435 if (!trigs1.size())
436 return globalEfficiency(leptons, runNumber, trigs2, globalEfficiencies);
437 if (!trigs2.size())
438 return globalEfficiency(leptons, runNumber, trigs1, globalEfficiencies);
439 globalEfficiencies = {1.};
440 bool success = true;
441 for (auto& lepton : leptons) {
442 std::size_t loosestLeg;
443 if (Trig1L_obj1::relevantFor(lepton))
444 loosestLeg = getLoosestLegAboveThreshold(lepton, trigs1, success);
445 else if (Trig1L_obj2::relevantFor(lepton))
446 loosestLeg = getLoosestLegAboveThreshold(lepton, trigs2, success);
447 else
448 continue;
449 if (loosestLeg && success) {
450 auto efficiencies = getCachedTriggerLegEfficiencies(lepton, runNumber,
451 loosestLeg, success);
452 globalEfficiencies *= ~efficiencies;
453 }
454 }
455 globalEfficiencies = ~globalEfficiencies;
456 return success;
457}

◆ globalEfficiency() [3/22]

template<typename Trig1L>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig1L trig,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig1L::is1L(), bool>
private

One single-lepton trigger.

Definition at line 324 of file Calculator.cxx.

327 {
328 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One1L() at line "
329 << __LINE__);
330 if (!trig) {
331 globalEfficiencies = {0.};
332 return true;
333 }
334 globalEfficiencies = {1.};
335 bool success = true;
336 for (auto& lepton : leptons) {
337 if (trig.irrelevantFor(lepton) || !aboveThreshold(lepton, trig()))
338 continue;
339 auto efficiencies =
340 getCachedTriggerLegEfficiencies(lepton, runNumber, trig(), success);
341 globalEfficiencies *= ~efficiencies;
342 }
343 globalEfficiencies = ~globalEfficiencies;
344 return success;
345}

◆ globalEfficiency() [4/22]

template<typename Trig1L_obj1, typename Trig1L_obj2>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig1L_obj1 trig1,
const Trig1L_obj2 trig2,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig1L_obj1::is1L() && Trig1L_obj2::is1L() && Trig1L_obj1::object() != Trig1L_obj2::object(), bool>
private

Two single-lepton triggers, two object types.

Definition at line 351 of file Calculator.cxx.

357 {
358 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Two1L() at line "
359 << __LINE__);
360 if (!trig1)
361 return globalEfficiency(leptons, runNumber, trig2, globalEfficiencies);
362 if (!trig2)
363 return globalEfficiency(leptons, runNumber, trig1, globalEfficiencies);
364 globalEfficiencies = {1.};
365 bool success = true;
366 for (auto& lepton : leptons) {
367 std::size_t leg;
368 if (trig1.relevantFor(lepton))
369 leg = trig1();
370 else if (trig2.relevantFor(lepton))
371 leg = trig2();
372 else
373 continue;
374 if (!aboveThreshold(lepton, leg))
375 continue;
376 auto efficiencies =
377 getCachedTriggerLegEfficiencies(lepton, runNumber, leg, success);
378 globalEfficiencies *= ~efficiencies;
379 }
380 globalEfficiencies = ~globalEfficiencies;
381 return success;
382}

◆ globalEfficiency() [5/22]

template<typename Trig2L, typename Trig1L>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2L trig2L,
const Trig1L trig1L,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2L::is2Lnomix() && Trig1L::is1L() && Trig2L::object() == Trig1L::object(), bool>
inlineprivate

One dilepton trigger + one single-lepton trigger.

Definition at line 601 of file Calculator.cxx.

608 {
609 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One2LSeveral1L() at line "
610 << __LINE__);
611 return globalEfficiency(leptons, runNumber, trig2L, flat_set<Trig1L>{trig1L},
612 globalEfficiencies);
613}
boost::container::flat_set< Key > flat_set

◆ globalEfficiency() [6/22]

template<typename Trig2L, typename Trig2Lmix>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2L trig2L,
const Trig2Lmix trig2Lmix,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2L::is2Lnomix() && Trig2Lmix::is2Lmix() && (Trig2Lmix::object1() == Trig2L::object() || Trig2Lmix::object2() == Trig2L::object()), bool>
private

One dilepton trigger + one mixed-flavour dilepton trigger.

Definition at line 1108 of file Calculator.cxx.

1115 {
1116 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Two2L() at line "
1117 << __LINE__);
1118 Efficiencies efficiencies1L, efficiencies2L, efficiencies2Lor1L;
1119 bool success =
1120 globalEfficiency(leptons, runNumber,
1121 trig2Lmix.template antiside<Trig2L>(), efficiencies1L);
1122 success =
1123 success && globalEfficiency(leptons, runNumber, trig2L, efficiencies2L);
1124 success = success && globalEfficiency(leptons, runNumber, trig2L,
1125 trig2Lmix.template side<Trig2L>(),
1126 efficiencies2Lor1L);
1127 globalEfficiencies =
1128 efficiencies2L * ~efficiencies1L + efficiencies1L * efficiencies2Lor1L;
1129 return success;
1130}

◆ globalEfficiency() [7/22]

template<typename Trig2L_obj1, typename Trig2L_obj2, typename Trig2Lmix, typename Trig1L_obj1, typename Trig1L_obj2>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2L_obj1 trig2L_obj1,
const Trig2L_obj2 trig2L_obj2,
const Trig2Lmix trig2Lmix,
const flat_set< Trig1L_obj1 > & trigs1L_obj1,
const flat_set< Trig1L_obj2 > & trigs1L_obj2,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lmix::is2Lmix() && Trig2L_obj1::is2Lnomix() && Trig2L_obj1::object() == Trig2Lmix::object1() && Trig2L_obj2::is2Lnomix() && Trig2L_obj2::object() == Trig2Lmix::object2() && Trig1L_obj1::is1L() && Trig1L_obj1::object() == Trig2Lmix::object1() && Trig1L_obj2::is1L() && Trig1L_obj2::object() == Trig2Lmix::object2(), bool>
private

Same combinaisons with 3 dilepton triggers, + single-lepton triggers.

Definition at line 1194 of file Calculator.cxx.

1210 {
1212 "Entered Calculator::globalEfficiency_Three2LSeveral1L() at line "
1213 << __LINE__);
1215 bool success = true;
1216 if (trig2L_obj1)
1217 success = success && globalEfficiency(leptons, runNumber, trig2L_obj1,
1218 trigs1L_obj1, efficiencies[0]);
1219 else
1220 success = success && globalEfficiency(leptons, runNumber, trigs1L_obj1,
1221 efficiencies[0]);
1222 if (trig2L_obj2)
1223 success = success && globalEfficiency(leptons, runNumber, trig2L_obj2,
1224 trigs1L_obj2, efficiencies[1]);
1225 else
1226 success = success && globalEfficiency(leptons, runNumber, trigs1L_obj2,
1227 efficiencies[1]);
1228 if (trig2Lmix && !trig2Lmix.hiddenBy(trigs1L_obj1)) {
1229 auto t = trig2Lmix.addTo(trigs1L_obj1);
1230 if (trig2L_obj1)
1231 success = success && globalEfficiency(leptons, runNumber, trig2L_obj1, t,
1232 efficiencies[2]);
1233 else
1234 success =
1235 success && globalEfficiency(leptons, runNumber, t, efficiencies[2]);
1236 } else
1237 efficiencies[2] = efficiencies[0];
1238 if (trig2Lmix && !trig2Lmix.hiddenBy(trigs1L_obj2)) {
1239 auto t = trig2Lmix.addTo(trigs1L_obj2);
1240 if (trig2L_obj2)
1241 success = success && globalEfficiency(leptons, runNumber, trig2L_obj2, t,
1242 efficiencies[3]);
1243 else
1244 success =
1245 success && globalEfficiency(leptons, runNumber, t, efficiencies[3]);
1246 } else
1247 efficiencies[3] = efficiencies[1];
1248 globalEfficiencies =
1249 Efficiencies(1.) - ~efficiencies[0] * ~efficiencies[1] +
1250 (efficiencies[2] - efficiencies[0]) * (efficiencies[3] - efficiencies[1]);
1251 return success;
1252}

◆ globalEfficiency() [8/22]

template<typename Trig2L_obj1, typename Trig2L_obj2, typename Trig2Lmix>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2L_obj1 trig2L_obj1,
const Trig2L_obj2 trig2L_obj2,
const Trig2Lmix trig2Lmix,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lmix::is2Lmix() && Trig2L_obj1::is2Lnomix() && Trig2L_obj1::object() == Trig2Lmix::object1() && Trig2L_obj2::is2Lnomix() && Trig2L_obj2::object() == Trig2Lmix::object2(), bool>
private

Combinaisons with 3 dilepton triggers including one mixed-flavour, and one sym.

/asym. dilepton for each flavour

Definition at line 1137 of file Calculator.cxx.

1147 {
1148 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Three2L() at line "
1149 << __LINE__);
1150 Efficiencies efficiencies2L[2] = {{0.}, {0.}},
1151 efficiencies2Lor1L[2] = {{0.}, {0.}};
1152 bool success = true;
1153 if (trig2L_obj1) {
1154 success = success && globalEfficiency(leptons, runNumber, trig2L_obj1,
1155 efficiencies2L[0]);
1156 if (trig2Lmix)
1157 success =
1158 success && globalEfficiency(leptons, runNumber, trig2L_obj1,
1159 trig2Lmix.template side<Trig2L_obj1>(),
1160 efficiencies2Lor1L[0]);
1161 else
1162 efficiencies2Lor1L[0] = efficiencies2L[0];
1163 } else if (trig2Lmix)
1164 success =
1165 success && globalEfficiency(leptons, runNumber,
1166 trig2Lmix.template side<Trig2L_obj1>(),
1167 efficiencies2Lor1L[0]);
1168 if (trig2L_obj2) {
1169 success = success && globalEfficiency(leptons, runNumber, trig2L_obj2,
1170 efficiencies2L[1]);
1171 if (trig2Lmix)
1172 success =
1173 success && globalEfficiency(leptons, runNumber, trig2L_obj2,
1174 trig2Lmix.template side<Trig2L_obj2>(),
1175 efficiencies2Lor1L[1]);
1176 else
1177 efficiencies2Lor1L[1] = efficiencies2L[1];
1178 } else if (trig2Lmix)
1179 success =
1180 success && globalEfficiency(leptons, runNumber,
1181 trig2Lmix.template side<Trig2L_obj2>(),
1182 efficiencies2Lor1L[1]);
1183 globalEfficiencies = efficiencies2L[0] * ~efficiencies2Lor1L[1] +
1184 efficiencies2L[1] * ~efficiencies2Lor1L[0] +
1185 efficiencies2Lor1L[0] * efficiencies2Lor1L[1];
1186 return success;
1187}

◆ globalEfficiency() [9/22]

template<typename Trig2L_obj1, typename Trig2Lsym_obj1, typename Trig2L_obj2, typename Trig2Lsym_obj2, typename Trig2Lmix, typename Trig1L_obj1, typename Trig1L_obj2>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2L_obj1 trig2L_obj1,
const Trig2Lsym_obj1 trig2Lsym_obj1,
const Trig2L_obj2 trig2L_obj2,
const Trig2Lsym_obj2 trig2Lsym_obj2,
const Trig2Lmix trig2Lmix1,
const Trig2Lmix trig2Lmix2,
const flat_set< Trig1L_obj1 > & trigs1L_obj1,
const flat_set< Trig1L_obj2 > & trigs1L_obj2,
Efficiencies & globalEfficiencies ) -> std::enable_if_t< Trig2Lmix::is2Lmix() && Trig2L_obj1::is2Lnomix() && Trig2L_obj1::object() == Trig2Lmix::object1() && Trig2L_obj2::is2Lnomix() && Trig2L_obj2::object() == Trig2Lmix::object2() && Trig2Lsym_obj1::is2Lsym() && Trig2Lsym_obj1::object() == Trig2Lmix::object1() && Trig2Lsym_obj2::is2Lsym() && Trig2Lsym_obj2::object() == Trig2Lmix::object2() && Trig1L_obj1::is1L() && Trig1L_obj1::object() == Trig2Lmix::object1() && Trig1L_obj2::is1L() && Trig1L_obj2::object() == Trig2Lmix::object2(), bool>
private

Six dilepton triggers (two mixed-flavour, two sym., two asym.

/sym.) for two object types

Definition at line 1261 of file Calculator.cxx.

1280 {
1281 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Six2LSeveral1L() at line "
1282 << __LINE__);
1283
1284 auto singleObjectFactor = [=](auto trig2L, auto trig2Lsym, auto& trigs1L,
1285 Efficiencies(&efficiencies)[4]) -> bool {
1286 auto eval_for = [=](const auto& trigs1L_extended,
1287 Efficiencies& eff) -> bool {
1288 if (trig2L && trig2Lsym)
1289 return this->globalEfficiency(leptons, runNumber, trig2L, trig2Lsym,
1290 trigs1L_extended, eff);
1291 else if (trig2L)
1292 return this->globalEfficiency(leptons, runNumber, trig2L,
1293 trigs1L_extended, eff);
1294 else if (trig2Lsym)
1295 return this->globalEfficiency(leptons, runNumber, trig2Lsym,
1296 trigs1L_extended, eff);
1297 else
1298 return this->globalEfficiency(leptons, runNumber, trigs1L_extended,
1299 eff);
1300 };
1301
1302 bool success = eval_for(trigs1L, efficiencies[0]);
1303 if (trig2Lmix1)
1304 success = success && eval_for(trig2Lmix1.addTo(trigs1L), efficiencies[1]);
1305 else
1306 efficiencies[1] = efficiencies[0];
1307 if (trig2Lmix2) {
1308 auto t = trig2Lmix2.addTo(trigs1L);
1309 success = success && eval_for(t, efficiencies[2]);
1310 if (trig2Lmix1)
1311 success&& eval_for(trig2Lmix1.addTo(t), efficiencies[3]);
1312 else
1313 efficiencies[3] = efficiencies[2];
1314 } else {
1315 efficiencies[2] = efficiencies[0];
1316 efficiencies[3] = efficiencies[1];
1317 }
1318 return success;
1319 };
1320
1321 Efficiencies efficiencies1[4], efficiencies2[4];
1322 bool success = singleObjectFactor(trig2L_obj1, trig2Lsym_obj1, trigs1L_obj1,
1323 efficiencies1) &&
1324 singleObjectFactor(trig2L_obj2, trig2Lsym_obj2, trigs1L_obj2,
1325 efficiencies2);
1326 globalEfficiencies = Efficiencies(1.) -
1327 ~efficiencies1[0] * ~efficiencies2[0] +
1328 (efficiencies1[1] - efficiencies1[0]) *
1329 (efficiencies2[1] - efficiencies2[0]) +
1330 (efficiencies1[2] - efficiencies1[0]) *
1331 (efficiencies2[2] - efficiencies2[0]) -
1332 (efficiencies1[0] - efficiencies1[1] - efficiencies1[2] +
1333 efficiencies1[3]) *
1334 (efficiencies2[0] - efficiencies2[1] -
1335 efficiencies2[2] + efficiencies2[3]);
1336 return success;
1337}

◆ globalEfficiency() [10/22]

template<typename Trig2Lasym, typename Trig1L>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2Lasym trig2L,
const flat_set< Trig1L > & trigs1L,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lasym::is2Lasym() && Trig1L::is1L() && Trig1L::object() == Trig2Lasym::object(), bool>
private

One asymmetric dilepton trigger + several single-lepton triggers.

S1 v S3

S2 v S3

Definition at line 675 of file Calculator.cxx.

681 {
682 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One2LSeveral1L() at line "
683 << __LINE__);
684 if (trig2L.symmetric())
685 return globalEfficiency(leptons, runNumber, trig2L.to_symmetric(), trigs1L,
686 globalEfficiencies);
687 if (!trigs1L.size())
688 return globalEfficiency(leptons, runNumber, trig2L, globalEfficiencies);
689 if (!trig2L || trig2L.hiddenBy(trigs1L))
690 return globalEfficiency(leptons, runNumber, trigs1L, globalEfficiencies);
691 globalEfficiencies = {0.};
692 Efficiencies twoSingleInefficiencies[2] = {{1.}, {1.}},
693 threeSingleInefficiencies = {1.};
694 bool success = true;
695 for (auto& lepton : leptons) {
696 if (trig2L.irrelevantFor(lepton))
697 continue;
698 flat_set<std::size_t> validLegs;
699 for (std::size_t leg : trig2L.legs)
700 if (aboveThreshold(lepton, leg))
701 validLegs.insert(leg);
702 Efficiencies efficiencies1L = {0.};
703 std::size_t loosest1lepLeg =
704 getLoosestLegAboveThreshold(lepton, trigs1L, success);
705 if (loosest1lepLeg) {
706 efficiencies1L = getCachedTriggerLegEfficiencies(lepton, runNumber,
707 loosest1lepLeg, success);
708 validLegs.insert(loosest1lepLeg);
709 }
710 if (!validLegs.size())
711 continue;
712 auto looseLegs = m_parent->getTwoLoosestLegs(lepton, validLegs, success);
713 auto efficienciesLoose =
714 (looseLegs.first == loosest1lepLeg)
715 ? efficiencies1L
717 looseLegs.first, success);
718 Efficiencies efficienciesMedium = {0.};
719 if (validLegs.size() >= 2)
720 efficienciesMedium =
721 (looseLegs.second == loosest1lepLeg)
722 ? efficiencies1L
723 : getCachedTriggerLegEfficiencies(lepton, runNumber,
724 looseLegs.second, success);
725 globalEfficiencies =
726 ~efficienciesLoose * globalEfficiencies + efficiencies1L;
727 if (loosest1lepLeg != looseLegs.first) {
728 globalEfficiencies +=
729 (efficienciesLoose - efficienciesMedium) *
730 ~twoSingleInefficiencies[looseLegs.first == trig2L.legs[0]];
731 if (loosest1lepLeg != looseLegs.second)
732 globalEfficiencies +=
733 (efficienciesMedium - efficiencies1L) * ~threeSingleInefficiencies;
734 }
735 threeSingleInefficiencies *= ~efficienciesLoose;
736 twoSingleInefficiencies[0] *= (looseLegs.first != trig2L.legs[1])
737 ? ~efficienciesLoose
738 : ~efficienciesMedium;
739 twoSingleInefficiencies[1] *= (looseLegs.first != trig2L.legs[0])
740 ? ~efficienciesLoose
741 : ~efficienciesMedium;
742 }
743 return success;
744}
if(febId1==febId2)
bool first
Definition DeMoScan.py:534

◆ globalEfficiency() [11/22]

template<typename Trig2Lasym, typename Trig2Lsym, typename Trig1L>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2Lasym trig2Lasym,
const Trig2Lsym trig2Lsym,
const flat_set< Trig1L > & trigs1L,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lasym::is2Lasym() && Trig2Lsym::is2Lsym() && Trig2Lsym::object() == Trig2Lasym::object() && Trig1L::is1L() && Trig1L::object() == Trig2Lasym::object(), bool>
private

Two dilepton triggers (one asym., one sym.) + several single-lepton triggers.

can't use tightestLeg==trig2Lsym because it might also be 0

this works because loosest1lepLeg is 0 if not on plateau...

note: secondLoosestLeg is valid because the loosest leg is either trig2Lasym(0) or trig2Lasym(1)

Definition at line 830 of file Calculator.cxx.

839 {
840 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Two2LSeveral1L() at line "
841 << __LINE__);
842 if (!trig2Lasym || trig2Lasym.hiddenBy(trigs1L))
843 return globalEfficiency(leptons, runNumber, trig2Lsym, trigs1L,
844 globalEfficiencies);
845 if (!trig2Lsym || trig2Lsym.hiddenBy(trigs1L))
846 return globalEfficiency(leptons, runNumber, trig2Lasym, trigs1L,
847 globalEfficiencies);
848 if (trig2Lasym(0) == trig2Lsym() || trig2Lasym(1) == trig2Lsym()) {
850 "implementation -- does this function work properly when the two 2L "
851 "triggers have one leg in common? Must be checked");
852 return false;
853 }
854 if (trig2Lasym.symmetric())
855 return globalEfficiency(leptons, runNumber, trig2Lasym.to_symmetric(),
856 trig2Lsym, trigs1L, globalEfficiencies);
857 globalEfficiencies = {0.};
858 Efficiencies singleInefficiencies[3] = {{1.}, {1.}, {1.}};
859 Efficiencies efficiencies2Lasym{0.},
860 efficiencies2Lsym[3] = {{0.}, {0.}, {0.}};
861
862 bool success = true;
863 for (auto& lepton : leptons) {
864 if (trig2Lasym.irrelevantFor(lepton))
865 continue;
866 flat_set<std::size_t> validLegs;
867 std::map<std::size_t, Efficiencies> efficiencies{{0, 0.}};
868 std::size_t loosest1lepLeg =
869 getLoosestLegAboveThreshold(lepton, trigs1L, success);
870 for (std::size_t leg :
871 {trig2Lasym(0), trig2Lasym(1), trig2Lsym(), loosest1lepLeg}) {
872 if (leg && aboveThreshold(lepton, leg)) {
873 validLegs.insert(leg);
875 lepton, runNumber, leg, success));
876 } else
877 efficiencies.emplace(leg, 0.);
878 }
879 if (!validLegs.size())
880 continue;
881
882 const auto sortedLegs = m_parent->getSortedLegs(lepton, validLegs, success);
883 if (!success)
884 return false;
885 std::size_t loosestLeg = sortedLegs[0];
886 std::size_t secondLoosestLeg = validLegs.size() >= 2 ? sortedLegs[1] : 0;
887 std::size_t secondTightestLeg = validLegs.size() >= 3 ? sortedLegs[2] : 0;
888 std::size_t tightestLeg = validLegs.size() >= 4 ? sortedLegs[3] : 0;
889 std::size_t lambda124 =
890 (loosestLeg != trig2Lasym(1)) ? loosestLeg : secondLoosestLeg;
891 std::size_t lambda134 =
892 (loosestLeg != trig2Lasym(0)) ? loosestLeg : secondLoosestLeg;
893 std::size_t lambda234 =
894 (loosestLeg != trig2Lsym()) ? loosestLeg : secondLoosestLeg;
895 std::size_t lambda14 = (lambda124 != trig2Lasym(0)) ? lambda124
896 : (lambda134 != trig2Lasym(1)) ? lambda134
897 : secondTightestLeg;
898 std::size_t lambda24 = (lambda124 != trig2Lsym()) ? lambda124
899 : (lambda234 != trig2Lasym(1)) ? lambda234
900 : secondTightestLeg;
901 std::size_t lambda34 = (lambda134 != trig2Lsym()) ? lambda134
902 : (lambda234 != trig2Lasym(0)) ? lambda234
903 : secondTightestLeg;
904 std::size_t tau13 = 0, tau12 = 0, tau23 = 0;
905 if (loosestLeg == trig2Lsym() || loosestLeg == trig2Lasym(0))
906 tau12 = (loosestLeg == trig2Lsym()) ? trig2Lasym(0) : trig2Lsym();
907 else if (secondLoosestLeg == trig2Lsym() ||
908 secondLoosestLeg == trig2Lasym(0))
909 tau12 = (secondLoosestLeg == trig2Lsym()) ? trig2Lasym(0) : trig2Lsym();
910 else if (secondTightestLeg == trig2Lsym() ||
911 secondTightestLeg == trig2Lasym(0))
912 tau12 = (secondTightestLeg == trig2Lsym()) ? trig2Lasym(0) : trig2Lsym();
913 else if (tightestLeg == trig2Lsym() || tightestLeg == trig2Lasym(0))
914 tau12 = (tightestLeg == trig2Lsym()) ? trig2Lasym(0) : trig2Lsym();
915 if (loosestLeg == trig2Lsym() || loosestLeg == trig2Lasym(1))
916 tau13 = (loosestLeg == trig2Lsym()) ? trig2Lasym(1) : trig2Lsym();
917 else if (secondLoosestLeg == trig2Lsym() ||
918 secondLoosestLeg == trig2Lasym(1))
919 tau13 = (secondLoosestLeg == trig2Lsym()) ? trig2Lasym(1) : trig2Lsym();
920 else if (secondTightestLeg == trig2Lsym() ||
921 secondTightestLeg == trig2Lasym(1))
922 tau13 = (secondTightestLeg == trig2Lsym()) ? trig2Lasym(1) : trig2Lsym();
923 else if (tightestLeg == trig2Lsym() || tightestLeg == trig2Lasym(1))
924 tau13 = (tightestLeg == trig2Lsym()) ? trig2Lasym(1) : trig2Lsym();
925 if (loosestLeg == trig2Lasym(0) || loosestLeg == trig2Lasym(1))
926 tau23 = (loosestLeg == trig2Lasym(0)) ? trig2Lasym(1) : trig2Lasym(0);
927 else if (secondLoosestLeg == trig2Lasym(0) ||
928 secondLoosestLeg == trig2Lasym(1))
929 tau23 =
930 (secondLoosestLeg == trig2Lasym(0)) ? trig2Lasym(1) : trig2Lasym(0);
931 else if (secondTightestLeg == trig2Lasym(0) ||
932 secondTightestLeg == trig2Lasym(1))
933 tau23 =
934 (secondTightestLeg == trig2Lasym(0)) ? trig2Lasym(1) : trig2Lasym(0);
935 else if (tightestLeg == trig2Lasym(0) || tightestLeg == trig2Lasym(1))
936 tau23 = (tightestLeg == trig2Lasym(0)) ? trig2Lasym(1) : trig2Lasym(0);
937
939 globalEfficiencies =
940 globalEfficiencies * ~efficiencies[loosestLeg] +
941 efficiencies[loosest1lepLeg] +
942 (efficiencies[tau13] - efficiencies[secondTightestLeg]) *
943 ~singleInefficiencies[0] +
944 (efficiencies[tau12] - efficiencies[secondTightestLeg]) *
945 ~singleInefficiencies[1] +
946 (efficiencies[tau23] - efficiencies[secondTightestLeg]) *
947 efficiencies2Lsym[2];
948 if (loosestLeg == trig2Lsym())
949 globalEfficiencies +=
950 (efficiencies[trig2Lsym()] - efficiencies[secondLoosestLeg]) *
951 efficiencies2Lasym;
952 else if (loosestLeg == trig2Lasym(1))
953 globalEfficiencies +=
954 (efficiencies[trig2Lasym(1)] - efficiencies[secondLoosestLeg]) *
955 efficiencies2Lsym[0];
956 else if (loosestLeg == trig2Lasym(0))
957 globalEfficiencies +=
958 (efficiencies[trig2Lasym(0)] - efficiencies[secondLoosestLeg]) *
959 efficiencies2Lsym[1];
960 if (secondTightestLeg &&
961 tightestLeg == loosest1lepLeg)
963 globalEfficiencies +=
964 (efficiencies[secondTightestLeg] - efficiencies[tightestLeg]) *
965 ~singleInefficiencies[2];
966
967 efficiencies2Lasym =
968 ~efficiencies[loosestLeg] * efficiencies2Lasym + efficiencies[lambda14];
969 if (loosestLeg == trig2Lasym(0) || loosestLeg == trig2Lasym(1)) {
972 efficiencies2Lasym +=
973 (efficiencies[loosestLeg] - efficiencies[secondLoosestLeg]) *
974 ~singleInefficiencies[loosestLeg == trig2Lasym(0)] +
975 (efficiencies[secondLoosestLeg] - efficiencies[lambda14]) *
976 ~singleInefficiencies[2];
977 }
978 efficiencies2Lsym[0] = ~efficiencies[lambda124] * efficiencies2Lsym[0] +
979 efficiencies[lambda24];
980 efficiencies2Lsym[1] = ~efficiencies[lambda134] * efficiencies2Lsym[1] +
981 efficiencies[lambda34];
982 efficiencies2Lsym[2] = ~efficiencies[loosestLeg] * efficiencies2Lsym[2] +
983 efficiencies[lambda234];
984 if (lambda124 == trig2Lsym())
985 efficiencies2Lsym[0] +=
986 (efficiencies[trig2Lsym()] - efficiencies[lambda24]) *
987 ~singleInefficiencies[0];
988 if (lambda134 == trig2Lsym())
989 efficiencies2Lsym[1] +=
990 (efficiencies[trig2Lsym()] - efficiencies[lambda34]) *
991 ~singleInefficiencies[1];
992 if (loosestLeg == trig2Lsym())
993 efficiencies2Lsym[2] +=
994 (efficiencies[trig2Lsym()] - efficiencies[lambda234]) *
995 ~singleInefficiencies[2];
996 singleInefficiencies[0] *= ~efficiencies[lambda124];
997 singleInefficiencies[1] *= ~efficiencies[lambda134];
998 singleInefficiencies[2] *= ~efficiencies[loosestLeg];
999 }
1000 return success;
1001}

◆ globalEfficiency() [12/22]

template<typename Trig2Lasym>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2Lasym trig,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lasym::is2Lasym(), bool>
private

One asymmetric dilepton trigger.

Definition at line 511 of file Calculator.cxx.

514 {
515 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One2L() at line "
516 << __LINE__);
517 if (trig.symmetric())
518 return globalEfficiency(leptons, runNumber, trig.to_symmetric(),
519 globalEfficiencies);
520 globalEfficiencies = {0.};
521 if (!trig)
522 return true;
523 Efficiencies singleInefficiencies[2] = {{1.}, {1.}},
524 twoSingleInefficiencies = {1.};
525 bool success = true;
526 for (auto& lepton : leptons) {
527 if (trig.irrelevantFor(lepton))
528 continue;
529 Efficiencies efficiencies[2] = {{0.}, {0.}};
530 int loosest = 0;
531 if (aboveThreshold(lepton, trig(0))) {
532 efficiencies[0] =
533 getCachedTriggerLegEfficiencies(lepton, runNumber, trig(0), success);
534 if (aboveThreshold(lepton, trig(1))) {
535 efficiencies[1] = getCachedTriggerLegEfficiencies(lepton, runNumber,
536 trig(1), success);
537 loosest = m_parent->getLoosestLeg(lepton, trig(0), trig(1), success) ==
538 trig(1);
539 }
540 } else if (aboveThreshold(lepton, trig(1))) {
541 efficiencies[1] =
542 getCachedTriggerLegEfficiencies(lepton, runNumber, trig(1), success);
543 loosest = 1;
544 } else
545 continue;
546 const int tightest = 1 - loosest;
547 globalEfficiencies = ~efficiencies[loosest] * globalEfficiencies +
548 (efficiencies[loosest] - efficiencies[tightest]) *
549 ~singleInefficiencies[tightest] +
550 efficiencies[tightest] * ~twoSingleInefficiencies;
551 twoSingleInefficiencies *= ~efficiencies[loosest];
552 for (int i = 0; i < 2; ++i)
553 singleInefficiencies[i] *= ~efficiencies[i];
554 }
555 return success;
556}

◆ globalEfficiency() [13/22]

template<typename Trig2Lmix, typename Trig1L_obj1, typename Trig1L_obj2>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2Lmix trig2Lmix,
const flat_set< Trig1L_obj1 > & trigs1L1,
const flat_set< Trig1L_obj2 > & trigs1L2,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lmix::is2Lmix() && Trig1L_obj1::is1L() && Trig2Lmix::object1() == Trig1L_obj1::object() && Trig1L_obj2::is1L() && Trig2Lmix::object2() == Trig1L_obj2::object(), bool>
private

One mixed-flavour dilepton trigger + single-lepton triggers.

Definition at line 562 of file Calculator.cxx.

571 {
572 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One2LSeveral1L() at line "
573 << __LINE__);
574 if (!(trigs1L1.size() + trigs1L2.size()))
575 return globalEfficiency(leptons, runNumber, trig2Lmix, globalEfficiencies);
576 if (trig2Lmix.hiddenBy(trigs1L1) || trig2Lmix.hiddenBy(trigs1L2))
577 return globalEfficiency(leptons, runNumber, trigs1L1, trigs1L2,
578 globalEfficiencies);
580 bool success =
581 globalEfficiency(leptons, runNumber, trigs1L1, efficiencies[0]) &&
582 globalEfficiency(leptons, runNumber, trigs1L2, efficiencies[1]) &&
583 globalEfficiency(leptons, runNumber, trig2Lmix.addTo(trigs1L1),
584 efficiencies[2]) &&
585 globalEfficiency(leptons, runNumber, trig2Lmix.addTo(trigs1L2),
586 efficiencies[3]);
587 if (success) {
588 globalEfficiencies = Efficiencies(1.) -
589 ~efficiencies[0] * ~efficiencies[1] +
590 (efficiencies[2] - efficiencies[0]) *
591 (efficiencies[3] - efficiencies[1]);
592 } else
593 globalEfficiencies = {0.};
594 return success;
595}

◆ globalEfficiency() [14/22]

template<typename Trig2Lmix>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2Lmix trig,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lmix::is2Lmix(), bool>
private

One mixed-flavour dilepton trigger.

Definition at line 463 of file Calculator.cxx.

466 {
467 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One2L() at line "
468 << __LINE__);
470 bool success =
471 globalEfficiency(leptons, runNumber, trig.side1(), efficiencies[0]) &&
472 globalEfficiency(leptons, runNumber, trig.side2(), efficiencies[1]);
473 if (success)
474 globalEfficiencies = efficiencies[0] * efficiencies[1];
475 else
476 globalEfficiencies = {0.};
477 return success;
478}

◆ globalEfficiency() [15/22]

template<typename Trig2Lsym, typename Trig1L>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2Lsym trig2L,
const flat_set< Trig1L > & trigs1L,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lsym::is2Lsym() && Trig1L::is1L() && Trig1L::object() == Trig2Lsym::object(), bool>
private

One symmetric dilepton trigger + several single-lepton triggers.

Definition at line 619 of file Calculator.cxx.

625 {
626 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One2LSeveral1L() at line "
627 << __LINE__);
628 if (!trigs1L.size())
629 return globalEfficiency(leptons, runNumber, trig2L, globalEfficiencies);
630 if (!trig2L || trig2L.hiddenBy(trigs1L))
631 return globalEfficiency(leptons, runNumber, trigs1L, globalEfficiencies);
632 globalEfficiencies = {0.};
633 Efficiencies twoSingleInefficiencies = {1.};
634 bool success = true;
635 for (auto& lepton : leptons) {
636 if (trig2L.irrelevantFor(lepton))
637 continue;
638 Efficiencies efficiencies1L(0.), efficiencies2L(0.);
639 const Efficiencies* loosestLegEfficiency;
640 std::size_t loosest1lepLeg =
641 getLoosestLegAboveThreshold(lepton, trigs1L, success);
642 if (loosest1lepLeg) {
643 efficiencies1L = getCachedTriggerLegEfficiencies(lepton, runNumber,
644 loosest1lepLeg, success);
645 if (aboveThreshold(lepton, trig2L())) {
646 efficiencies2L = getCachedTriggerLegEfficiencies(lepton, runNumber,
647 trig2L(), success);
648 loosestLegEfficiency =
649 (m_parent->getLoosestLeg(lepton, trig2L(), loosest1lepLeg,
650 success) == trig2L())
651 ? &efficiencies2L
652 : &efficiencies1L;
653 } else
654 loosestLegEfficiency = &efficiencies1L;
655 } else if (aboveThreshold(lepton, trig2L())) {
656 efficiencies2L =
657 getCachedTriggerLegEfficiencies(lepton, runNumber, trig2L(), success);
658 loosestLegEfficiency = &efficiencies2L;
659 } else
660 continue;
661 globalEfficiencies =
662 ~(*loosestLegEfficiency) * globalEfficiencies + efficiencies1L;
663 if (loosestLegEfficiency == &efficiencies2L)
664 globalEfficiencies +=
665 ~twoSingleInefficiencies * (efficiencies2L - efficiencies1L);
666 twoSingleInefficiencies *= ~(*loosestLegEfficiency);
667 }
668 return success;
669}

◆ globalEfficiency() [16/22]

template<typename Trig2Lsym, typename Trig1L>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2Lsym trig2L1,
const Trig2Lsym trig2L2,
const flat_set< Trig1L > & trigs1L,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lsym::is2Lsym() && Trig1L::is1L() && Trig1L::object() == Trig2Lsym::object(), bool>
private

Two symmetric dilepton triggers + several single-lepton triggers.

Definition at line 750 of file Calculator.cxx.

757 {
758 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Two2LSeveral1L() at line "
759 << __LINE__);
760 if (!trig2L1 || trig2L1 == trig2L2 || trig2L1.hiddenBy(trigs1L))
761 return globalEfficiency(leptons, runNumber, trig2L2, trigs1L,
762 globalEfficiencies);
763 if (!trig2L2 || trig2L2.hiddenBy(trigs1L))
764 return globalEfficiency(leptons, runNumber, trig2L1, trigs1L,
765 globalEfficiencies);
766 globalEfficiencies = {0.};
767 Efficiencies singleInefficiencies{1.};
768 Efficiencies efficiencies2Lsym[2] = {{0.}, {0.}};
769
770 bool success = true;
771 for (auto& lepton : leptons) {
772 if (trig2L1.irrelevantFor(lepton))
773 continue;
774 flat_set<std::size_t> validLegs;
775 std::map<std::size_t, Efficiencies> efficiencies{{0, 0.}};
776 std::size_t loosest1lepLeg =
777 getLoosestLegAboveThreshold(lepton, trigs1L, success);
778 for (std::size_t leg : {loosest1lepLeg, trig2L1(), trig2L2()}) {
779 if (leg && aboveThreshold(lepton, leg)) {
780 validLegs.insert(leg);
782 lepton, runNumber, leg, success));
783 } else
784 efficiencies.emplace(leg, 0.);
785 }
786 if (!validLegs.size())
787 continue;
788 auto looseLegs = m_parent->getTwoLoosestLegs(lepton, validLegs, success);
789 std::size_t lambda13 =
790 (looseLegs.first != trig2L2()) ? looseLegs.first : looseLegs.second;
791 std::size_t lambda23 =
792 (looseLegs.first != trig2L1()) ? looseLegs.first : looseLegs.second;
793 globalEfficiencies = globalEfficiencies * ~efficiencies[looseLegs.first] +
794 efficiencies[loosest1lepLeg];
795 if (looseLegs.first == trig2L1())
796 globalEfficiencies +=
797 efficiencies2Lsym[1] *
798 (efficiencies[trig2L1()] - efficiencies[looseLegs.second]);
799 if (looseLegs.first == trig2L2())
800 globalEfficiencies +=
801 efficiencies2Lsym[0] *
802 (efficiencies[trig2L2()] - efficiencies[looseLegs.second]);
803 if (looseLegs.first != loosest1lepLeg)
804 globalEfficiencies +=
805 ~singleInefficiencies *
806 (efficiencies[looseLegs.second] - efficiencies[loosest1lepLeg]);
807 efficiencies2Lsym[0] =
808 ~efficiencies[looseLegs.first] * efficiencies2Lsym[0] +
809 efficiencies[lambda23];
810 efficiencies2Lsym[1] =
811 ~efficiencies[looseLegs.first] * efficiencies2Lsym[1] +
812 efficiencies[lambda13];
813 if (looseLegs.first == trig2L1())
814 efficiencies2Lsym[0] +=
815 (efficiencies[trig2L1()] - efficiencies[lambda23]) *
816 ~singleInefficiencies;
817 if (looseLegs.first == trig2L2())
818 efficiencies2Lsym[1] +=
819 (efficiencies[trig2L2()] - efficiencies[lambda13]) *
820 ~singleInefficiencies;
821 singleInefficiencies *= ~efficiencies[looseLegs.first];
822 }
823 return success;
824}

◆ globalEfficiency() [17/22]

template<typename Trig2Lsym>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig2Lsym trig,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig2Lsym::is2Lsym(), bool>
private

One symmetric dilepton trigger.

Definition at line 484 of file Calculator.cxx.

487 {
488 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One2L() at line "
489 << __LINE__);
490 globalEfficiencies = {0.};
491 if (!trig)
492 return true;
493 Efficiencies singleInefficiencies(1.);
494 bool success = true;
495 for (auto& lepton : leptons) {
496 if (trig.irrelevantFor(lepton) || !aboveThreshold(lepton, trig()))
497 continue;
498 auto efficiencies =
499 getCachedTriggerLegEfficiencies(lepton, runNumber, trig(), success);
500 globalEfficiencies = ~efficiencies * globalEfficiencies +
501 efficiencies * ~singleInefficiencies;
502 singleInefficiencies *= ~efficiencies;
503 }
504 return success;
505}

◆ globalEfficiency() [18/22]

template<typename Trig3Lhalfsym>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig3Lhalfsym trig,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig3Lhalfsym::is3Lhalfsym(), bool>
private

One half-symmetric trilepton trigger.

Definition at line 1034 of file Calculator.cxx.

1037 {
1038 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One3L() at line "
1039 << __LINE__);
1040 if (trig.symmetric())
1041 return globalEfficiency(leptons, runNumber, trig.to_symmetric(),
1042 globalEfficiencies);
1043 globalEfficiencies = {0.};
1044 Efficiencies singleInefficiencies[2] = {{1.}, {1.}},
1045 twoSingleInefficiencies{1.};
1046 Efficiencies efficiencies2Lsym{0.}, efficiencies2Lasym{0.},
1047 efficiencies2L2L{0.};
1048 bool success = true;
1049 for (auto& lepton : leptons) {
1050 if (trig.irrelevantFor(lepton))
1051 continue;
1052 Efficiencies efficiencies[2] = {{0.}, {0.}};
1053 const int asym = 0, sym = 1;
1054 int loosestLeg;
1055 if (aboveThreshold(lepton, trig.asymLeg())) {
1057 lepton, runNumber, trig.asymLeg(), success);
1058 if (aboveThreshold(lepton, trig.symLeg())) {
1060 lepton, runNumber, trig.symLeg(), success);
1061 loosestLeg =
1062 m_parent->getLoosestLeg(lepton, trig.asymLeg(), trig.symLeg(),
1063 success) == trig.asymLeg()
1064 ? asym
1065 : sym;
1066 } else
1067 loosestLeg = asym;
1068 } else if (aboveThreshold(lepton, trig.symLeg())) {
1070 lepton, runNumber, trig.symLeg(), success);
1071 loosestLeg = sym;
1072 } else
1073 continue;
1074 Efficiencies delta = efficiencies[asym] - efficiencies[sym];
1075 if (loosestLeg == asym) {
1076 globalEfficiencies = ~efficiencies[asym] * globalEfficiencies +
1077 efficiencies[sym] * efficiencies2L2L +
1078 delta * efficiencies2Lsym;
1079 efficiencies2L2L = ~efficiencies[asym] * efficiencies2L2L +
1080 efficiencies[sym] * ~twoSingleInefficiencies +
1081 delta * ~singleInefficiencies[sym];
1082 efficiencies2Lasym = ~efficiencies[asym] * efficiencies2Lasym +
1083 efficiencies[sym] * ~twoSingleInefficiencies +
1084 delta * ~singleInefficiencies[sym];
1085 } else {
1086 globalEfficiencies = ~efficiencies[sym] * globalEfficiencies +
1087 efficiencies[asym] * efficiencies2L2L -
1088 delta * efficiencies2Lasym;
1089 efficiencies2L2L = ~efficiencies[sym] * efficiencies2L2L +
1090 efficiencies[sym] * ~twoSingleInefficiencies;
1091 efficiencies2Lasym = ~efficiencies[sym] * efficiencies2Lasym +
1092 efficiencies[asym] * ~twoSingleInefficiencies -
1093 delta * ~singleInefficiencies[asym];
1094 }
1095 efficiencies2Lsym = ~efficiencies[sym] * efficiencies2Lsym +
1096 efficiencies[sym] * ~singleInefficiencies[sym];
1097 twoSingleInefficiencies *= ~efficiencies[loosestLeg];
1098 singleInefficiencies[sym] *= ~efficiencies[sym];
1099 singleInefficiencies[asym] *= ~efficiencies[asym];
1100 }
1101 return success;
1102}

◆ globalEfficiency() [19/22]

template<typename Trig3Lmix>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig3Lmix trig,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig3Lmix::is3Lmix(), bool>
private

One mixed-flavour trilepton trigger.

Definition at line 1343 of file Calculator.cxx.

1346 {
1347 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One3L() at line "
1348 << __LINE__);
1349 Efficiencies efficiencies[2] = {{0.}, {0.}};
1350 bool success = globalEfficiency(leptons, runNumber,
1351 trig.template side<Trig3Lmix::object1()>(),
1352 efficiencies[0]) &&
1353 globalEfficiency(leptons, runNumber,
1354 trig.template side<Trig3Lmix::object2()>(),
1355 efficiencies[1]);
1356 globalEfficiencies = efficiencies[0] * efficiencies[1];
1357 return success;
1358}

◆ globalEfficiency() [20/22]

template<typename Trig3Lmix1, typename Trig3Lmix2>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig3Lmix1 trig1,
const Trig3Lmix2 trig2,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig3Lmix1::is3Lmix() && Trig3Lmix2::is3Lmix() && Trig3Lmix1::object1() == Trig3Lmix2::object2() && Trig3Lmix1::object2() == Trig3Lmix2::object1(), bool>
private

Two complementary mixed-flavour trilepton triggers.

Definition at line 1364 of file Calculator.cxx.

1371 {
1372 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Two3L() at line "
1373 << __LINE__);
1374 Efficiencies efficiencies[6] = {{0.}, {0.}, {0.}, {0.}, {0.}, {0.}};
1375 auto trig2La = trig1.template side<Trig3Lmix1::object1()>();
1376 auto trig1La = trig2.template side<Trig3Lmix2::object2()>();
1377 bool success =
1378 globalEfficiency(leptons, runNumber, trig1La, efficiencies[0]) &&
1379 globalEfficiency(leptons, runNumber, trig2La, efficiencies[1]);
1380 if (!trig2La.hiddenBy(trig1La))
1381 success = success && globalEfficiency(leptons, runNumber, trig2La, trig1La,
1382 efficiencies[2]);
1383 else
1384 efficiencies[2] = efficiencies[0];
1385 auto trig2Lb = trig2.template side<Trig3Lmix2::object1()>();
1386 auto trig1Lb = trig1.template side<Trig3Lmix1::object2()>();
1387 success = success &&
1388 globalEfficiency(leptons, runNumber, trig1Lb, efficiencies[3]) &&
1389 globalEfficiency(leptons, runNumber, trig2Lb, efficiencies[4]);
1390 if (!trig2Lb.hiddenBy(trig1Lb))
1391 success = success && globalEfficiency(leptons, runNumber, trig2Lb, trig1Lb,
1392 efficiencies[5]);
1393 else
1394 efficiencies[5] = efficiencies[3];
1395 globalEfficiencies =
1397 (efficiencies[2] - efficiencies[0] - efficiencies[1]) *
1398 (efficiencies[3] + efficiencies[4] - efficiencies[5]);
1399 return success;
1400}

◆ globalEfficiency() [21/22]

template<typename Trig3Lsym>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig3Lsym trig,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig3Lsym::is3Lsym(), bool>
private

One symmetric trilepton trigger.

Definition at line 1007 of file Calculator.cxx.

1010 {
1011 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One3L() at line "
1012 << __LINE__);
1013 globalEfficiencies = {0.};
1014 Efficiencies singleInefficiencies{1.}, efficiencies2L{0.};
1015 bool success = true;
1016 for (auto& lepton : leptons) {
1017 if (trig.irrelevantFor(lepton) || !aboveThreshold(lepton, trig()))
1018 continue;
1019 auto efficiencies =
1020 getCachedTriggerLegEfficiencies(lepton, runNumber, trig(), success);
1021 globalEfficiencies =
1022 ~efficiencies * globalEfficiencies + efficiencies * efficiencies2L;
1023 efficiencies2L =
1024 ~efficiencies * efficiencies2L + efficiencies * ~singleInefficiencies;
1025 singleInefficiencies *= ~efficiencies;
1026 }
1027 return success;
1028}

◆ globalEfficiency() [22/22]

template<typename Trig4Lsym>
auto Calculator::globalEfficiency ( const LeptonList & leptons,
unsigned runNumber,
const Trig4Lsym trig,
Efficiencies & globalEfficiencies ) -> std::enable_if_t<Trig4Lsym::is4Lsym(), bool>
private

One symmetric tetralepton trigger.

Definition at line 1406 of file Calculator.cxx.

1409 {
1410 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_One4L() at line "
1411 << __LINE__);
1412 globalEfficiencies = {0.};
1413 Efficiencies singleInefficiencies{1.}, efficiencies2L{0.}, efficiencies3L{0.};
1414 bool success = true;
1415 for (auto& lepton : leptons) {
1416 if (trig.irrelevantFor(lepton) || !aboveThreshold(lepton, trig()))
1417 continue;
1418 auto efficiencies =
1419 getCachedTriggerLegEfficiencies(lepton, runNumber, trig(), success);
1420 globalEfficiencies =
1421 ~efficiencies * globalEfficiencies + efficiencies * efficiencies3L;
1422 efficiencies3L =
1423 ~efficiencies * efficiencies3L + efficiencies * efficiencies2L;
1424 efficiencies2L =
1425 ~efficiencies * efficiencies2L + efficiencies * ~singleInefficiencies;
1426 singleInefficiencies *= ~efficiencies;
1427 }
1428 return success;
1429}

◆ globalEfficiency_Factorized2()

bool Calculator::globalEfficiency_Factorized2 ( const LeptonList & leptons,
unsigned runNumber,
GlobEffFunc func1,
GlobEffFunc func2,
Efficiencies & globalEfficiencies )
private

Definition at line 1431 of file Calculator.cxx.

1433 {
1435 if (!func1(this, leptons, runNumber, efficiencies[0]))
1436 return false;
1437 if (!func2(this, leptons, runNumber, efficiencies[1]))
1438 return false;
1439 globalEfficiencies = ~(~efficiencies[0] * ~efficiencies[1]);
1440 return true;
1441}

◆ globalEfficiency_Factorized3()

bool Calculator::globalEfficiency_Factorized3 ( const LeptonList & leptons,
unsigned runNumber,
GlobEffFunc func1,
GlobEffFunc func2,
GlobEffFunc func3,
Efficiencies & globalEfficiencies )
private

Definition at line 1443 of file Calculator.cxx.

1445 {
1447 if (!func1(this, leptons, runNumber, efficiencies[0]))
1448 return false;
1449 if (!func2(this, leptons, runNumber, efficiencies[1]))
1450 return false;
1451 if (!func3(this, leptons, runNumber, efficiencies[2]))
1452 return false;
1453 globalEfficiencies =
1454 ~(~efficiencies[0] * ~efficiencies[1] * ~efficiencies[2]);
1455 return true;
1456}

◆ globalEfficiency_Toys()

bool Calculator::globalEfficiency_Toys ( const LeptonList & leptons,
unsigned runNumber,
const std::vector< TrigDef > & triggers,
Efficiencies & globalEfficiencies )
private

0 = data, 1 = MC

Definition at line 1524 of file Calculator.cxx.

1527 {
1528 ATH_MSG_DEBUG("Entered Calculator::globalEfficiency_Toys() at line "
1529 << __LINE__);
1530 globalEfficiencies = {0.};
1531 if (m_parent->m_numberOfToys <= 0) {
1532 ATH_MSG_ERROR("The specified number of toys is <= 0");
1533 return false;
1534 }
1535 std::map<const Lepton*, std::vector<std::pair<std::size_t, Efficiencies>>>
1536 leptonEfficiencies;
1537 for (auto& lepton : leptons) {
1538 flat_set<std::size_t> validLegs;
1539 if (!fillListOfLegsFor(lepton, triggers, validLegs))
1540 return false;
1541 auto& efficiencies = leptonEfficiencies[&lepton];
1542 const int nLegs = validLegs.size();
1543 if (nLegs) {
1544 bool success = true;
1545 for (std::size_t leg :
1546 m_parent->getSortedLegs(lepton, validLegs, success)) {
1548 lepton, runNumber, leg, success));
1549 }
1550 if (!success)
1551 return false;
1552 }
1553 }
1554 unsigned long seed;
1555 if (!m_parent->m_useInternalSeed) {
1556 if (!m_parent->retrieveEventNumber(seed)) {
1557 ATH_MSG_WARNING("Will use internal seed instead of event number");
1558 seed = m_parent->m_seed++;
1559 }
1560 } else
1561 seed = m_parent->m_seed++;
1562 std::mt19937_64 randomEngine(seed);
1563 std::uniform_real_distribution<double> uniformPdf(0., 1.);
1564 std::vector<flat_set<std::size_t>> firedLegs(leptonEfficiencies.size());
1565 unsigned long nPassed[2] = {0, 0};
1566 for (unsigned long toy = 0; toy < m_parent->m_numberOfToys; ++toy) {
1567 for (int step = 0; step < 2; ++step)
1568 {
1569 auto legs = firedLegs.begin();
1570 for (auto& kv : leptonEfficiencies) {
1571 legs->clear();
1572 double x = uniformPdf(randomEngine);
1573 for (auto& p : kv.second) {
1574 if (x < (step ? p.second.mc() : p.second.data()))
1575 legs->emplace(p.first);
1576 }
1577 ++legs;
1578 }
1579 for (auto& trig : triggers) {
1580 if (!canTriggerBeFired(trig, firedLegs))
1581 continue;
1582 ++nPassed[step];
1583 break;
1584 }
1585 }
1586 }
1587 globalEfficiencies.data() =
1588 double(nPassed[0]) / double(m_parent->m_numberOfToys);
1589 globalEfficiencies.mc() =
1590 double(nPassed[1]) / double(m_parent->m_numberOfToys);
1591 return true;
1592}
#define ATH_MSG_WARNING(x)

◆ initMessaging()

void AthMessaging::initMessaging ( ) const
privateinherited

Initialize our message level and MessageSvc.

This method should only be called once.

Definition at line 39 of file AthMessaging.cxx.

40{
42 // If user did not set an explicit level, set a default
43 if (m_lvl == MSG::NIL) {
44 m_lvl = m_imsg ?
45 static_cast<MSG::Level>( m_imsg.load()->outputLevel(m_nm) ) :
46 MSG::INFO;
47 }
48}
std::string m_nm
Message source name.
std::atomic< IMessageSvc * > m_imsg
MessageSvc pointer.
std::atomic< MSG::Level > m_lvl
Current logging level.
IMessageSvc * getMessageSvc(bool quiet=false)

◆ msg() [1/2]

MsgStream & asg::AsgMessaging::msg ( ) const
inherited

The standard message stream.

Returns
A reference to the default message stream of this object.

Definition at line 49 of file AsgMessaging.cxx.

49 {
50#ifndef XAOD_STANDALONE
51 return ::AthMessaging::msg();
52#else // not XAOD_STANDALONE
53 return m_msg;
54#endif // not XAOD_STANDALONE
55 }

◆ msg() [2/2]

MsgStream & asg::AsgMessaging::msg ( const MSG::Level lvl) const
inherited

The standard message stream.

Parameters
lvlThe message level to set the stream to
Returns
A reference to the default message stream, set to level "lvl"

Definition at line 57 of file AsgMessaging.cxx.

57 {
58#ifndef XAOD_STANDALONE
59 return ::AthMessaging::msg( lvl );
60#else // not XAOD_STANDALONE
61 m_msg << lvl;
62 return m_msg;
63#endif // not XAOD_STANDALONE
64 }

◆ msgLvl()

bool asg::AsgMessaging::msgLvl ( const MSG::Level lvl) const
inherited

Test the output level of the object.

Parameters
lvlThe message level to test against
Returns
boolean Indicting if messages at given level will be printed
true If messages at level "lvl" will be printed

Definition at line 41 of file AsgMessaging.cxx.

41 {
42#ifndef XAOD_STANDALONE
43 return ::AthMessaging::msgLvl( lvl );
44#else // not XAOD_STANDALONE
45 return m_msg.msgLevel( lvl );
46#endif // not XAOD_STANDALONE
47 }

◆ setLevel()

void AthMessaging::setLevel ( MSG::Level lvl)
inherited

Change the current logging level.

Use this rather than msg().setLevel() for proper operation with MT.

Definition at line 28 of file AthMessaging.cxx.

29{
30 m_lvl = lvl;
31}

◆ CheckConfig

friend class CheckConfig
friend

Definition at line 320 of file Calculator.h.

Member Data Documentation

◆ ATLAS_THREAD_SAFE

std::atomic_flag m_initialized AthMessaging::ATLAS_THREAD_SAFE = ATOMIC_FLAG_INIT
mutableprivateinherited

Messaging initialized (initMessaging)

Definition at line 141 of file AthMessaging.h.

◆ m_cachedEfficiencies

std::map<std::pair<const Lepton*, std::size_t>, Efficiencies> TrigGlobEffCorr::Calculator::m_cachedEfficiencies
private

Definition at line 71 of file Calculator.h.

◆ m_forceUnitSF

bool TrigGlobEffCorr::Calculator::m_forceUnitSF
private

Definition at line 72 of file Calculator.h.

◆ m_imsg

std::atomic<IMessageSvc*> AthMessaging::m_imsg { nullptr }
mutableprivateinherited

MessageSvc pointer.

Definition at line 135 of file AthMessaging.h.

135{ nullptr };

◆ m_lvl

std::atomic<MSG::Level> AthMessaging::m_lvl { MSG::NIL }
mutableprivateinherited

Current logging level.

Definition at line 138 of file AthMessaging.h.

138{ MSG::NIL };

◆ m_msg_tls

boost::thread_specific_ptr<MsgStream> AthMessaging::m_msg_tls
mutableprivateinherited

MsgStream instance (a std::cout like with print-out levels)

Definition at line 132 of file AthMessaging.h.

◆ m_nm

std::string AthMessaging::m_nm
privateinherited

Message source name.

Definition at line 129 of file AthMessaging.h.

◆ m_parent

TrigGlobalEfficiencyCorrectionTool* TrigGlobEffCorr::Calculator::m_parent
private

Definition at line 66 of file Calculator.h.

◆ m_periods

std::vector<Period> TrigGlobEffCorr::Calculator::m_periods
private

pointer updated at each call to compute() because the parent tool might have been moved in-between

Definition at line 69 of file Calculator.h.


The documentation for this class was generated from the following files: