ATLAS Offline Software
ScaleFactorCalculator.cxx
Go to the documentation of this file.
1 /*
2  Copyright (C) 2002-2020 CERN for the benefit of the ATLAS collaboration
3  */
4 
6 
7 #include <string>
8 
10 #include "TopEvent/EventTools.h"
11 
13 
14 #include <sstream>
15 
16 namespace top {
18  asg::AsgTool(name),
19  m_config(nullptr),
20 
21  m_photonSF(nullptr),
22  m_electronSF(nullptr),
23  m_fwdElectronSF(nullptr),
24  m_muonSF(nullptr),
25  m_tauSF(nullptr),
26  m_jetSF(nullptr),
27  m_btagSF(nullptr),
28  m_pileupSF(nullptr),
29  m_sherpa_22_reweight_tool("PMGSherpa22VJetsWeightTool"),
30  m_globalLeptonTriggerSF(nullptr),
31  m_pmg_truth_weight_tool("PMGTruthWeightTool"),
32  m_nominal_weight_name("") {
33  declareProperty("config", m_config);
34  }
35 
37  ATH_MSG_INFO(" top::ScaleFactorCalculator initialize");
38 
39  m_photonSF = std::make_unique<top::PhotonScaleFactorCalculator>("top::PhotonScaleFactorCalculator");
40  m_electronSF = std::make_unique<top::ElectronScaleFactorCalculator>("top::ElectronScaleFactorCalculator");
41  m_fwdElectronSF = std::make_unique<top::FwdElectronScaleFactorCalculator>("top::FwdElectronScaleFactorCalculator");
42  m_muonSF = std::make_unique<top::MuonScaleFactorCalculator>("top::MuonScaleFactorCalculator");
43  m_tauSF = std::make_unique<top::TauScaleFactorCalculator>("top::TauScaleFactorCalculator");
44  m_jetSF = std::make_unique<top::JetScaleFactorCalculator>("top::JetScaleFactorCalculator");
45  m_btagSF = std::make_unique<top::BTagScaleFactorCalculator>("top::BTagScaleFactorCalculator");
46  m_pileupSF = std::make_unique<top::PileupScaleFactorCalculator>("top::PileupScaleFactorCalculator");
48  std::make_unique<top::GlobalLeptonTriggerCalculator>("top::GlobalLeptonTriggerCalculator");
49 
50  if (m_config->isMC()) {
51  if (m_config->usePhotons()) {
52  top::check(m_photonSF->setProperty("config", m_config), "Failed to setProperty");
53  top::check(m_photonSF->initialize(), "Failed to initialize");
54  }
55 
56  if (m_config->useElectrons()) {
57  top::check(m_electronSF->setProperty("config", m_config), "Failed to setProperty");
58  top::check(m_electronSF->initialize(), "Failed to initialize");
59  }
60 
61  if (m_config->useFwdElectrons()) {
62  top::check(m_fwdElectronSF->setProperty("config", m_config), "Failed to setProperty");
63  top::check(m_fwdElectronSF->initialize(), "Failed to initialize");
64  }
65 
66  if (m_config->useMuons() && !m_config->isTruthDxAOD()) {
67  top::check(m_muonSF->setProperty("config", m_config), "Failed to setProperty");
68  top::check(m_muonSF->initialize(), "Failed to initialize");
69  }
70 
71  if (m_config->useTaus()) {
72  top::check(m_tauSF->setProperty("config", m_config), "Failed to setProperty");
73  top::check(m_tauSF->initialize(), "Failed to initialize");
74  }
75 
76  if (m_config->useJets()) {
77  top::check(m_jetSF->setProperty("config", m_config), "Failed to setProperty");
78  top::check(m_jetSF->initialize(), "Failed to initialize");
79 
80  top::check(m_btagSF->setProperty("config", m_config), "Failed to setProperty");
81  top::check(m_btagSF->initialize(), "Failed to initialize");
82  }
83 
84  if (m_config->isSherpa22Vjets()) top::check(m_sherpa_22_reweight_tool.retrieve(),
85  "Failed to retrieve PMGSherpa22VJetsWeightTool");
86 
87  if ((m_config->useElectrons() || m_config->useMuons()) && m_config->useGlobalTrigger()) {
88  top::check(m_globalLeptonTriggerSF->setProperty("config", m_config), "Failed to setProperty");
89  top::check(m_globalLeptonTriggerSF->initialize(), "Failed to initalize");
90  }
91 
92  top::check(initialize_nominal_MC_weight(), "Failed to initialize nominal MC weight in SF calculator");
93  }
94 
95  if (m_config->doPileupReweighting()) {
96  top::check(m_pileupSF->setProperty("config", m_config), "Failed to add config to pileup SF calculator");
97  top::check(m_pileupSF->initialize(), "Failed to initialize pileup SF calculator");
98  }
99 
100  return StatusCode::SUCCESS;
101  }
102 
104  // check if user force-requested to use plain MC weights vector index
105  // in that case ignore all the additional checks if metadata broken
106  // as well as the method to determine nominal weight by name
107  if (m_config->forceNominalWeightFallbackIndex()) {
108  ATH_MSG_WARNING("ForceNominalWeightFallbackIndex option was set to true."
109  << "\nWill use weight with index: " << m_config->nominalWeightIndex()
110  << " instead of determining it from metadata!");
111  return StatusCode::SUCCESS;
112  }
114  // in case PMGTruthWeightTool init fails, e.g. due to broken metadata
115  // leave the possibility to force nominal weight above
116  if (!m_pmg_truth_weight_tool.retrieve()) {
117  ATH_MSG_ERROR("\nPMGTruthWeightTool instance could not be retrieved."
118  << "\nWe cannot determine if this sample has multiple weights, "
119  << "nor which one is nominal. Please specify the index of "
120  << "nominal MC weight via config option NominalWeightFallbackIndex, "
121  << " and set ForceNominalWeightFallbackIndex to true.");
122  return StatusCode::FAILURE;
123  }
124 
125  // PMGTruthWeightTool was initialized succesfully, let's see if we have weights
126  const std::vector<std::string>& pmg_weight_names = m_pmg_truth_weight_tool->getWeightNames();
127 
128  // scenario 1 -- sample has only one weight
129  if (pmg_weight_names.size() == 1) {
130  ATH_MSG_INFO("PMGTruthWeightTool reports single weight in sample, assuming nominal weight index = 0");
131  m_config->setNominalWeightIndex(0);
132  return StatusCode::SUCCESS;
133  }
134 
135  // scenario 2 -- sample has multiple weights, try to find the nominal one
136  // one should not blindly assume that 0th weight is nominal
137  // here we try to find the first weight name from the NominalWeightNames config option,
138  // which that matches any MC weight in the sample
139  const std::vector<std::string> &nominal_weight_names = m_config->nominalWeightNames();
140  bool found_match = false;
141  std::vector<std::string> multiple_matches;
142  for (const std::string& weight_name : nominal_weight_names) {
143  // Check whether this weight name does exist
144  if (m_pmg_truth_weight_tool->hasWeight(weight_name)) {
145  // pick only the first match, but check if there are multiple matches -- that is a problem
146  if (!found_match)
148  found_match = true;
149  multiple_matches.push_back(weight_name);
150  }
151  }
152  // we have to find the index, because PMGTruthWeightTool has no method to give us the index
153  auto weight_index = std::find(pmg_weight_names.begin(), pmg_weight_names.end(), m_nominal_weight_name);
154  m_config->setNominalWeightName(m_nominal_weight_name);
155  m_config->setNominalWeightIndex(weight_index - pmg_weight_names.begin());
156  if (multiple_matches.size() > 1) {
157  std::stringstream s_multiple_matches;
158  for (const std::string &wname : multiple_matches)
159  s_multiple_matches << "\"" << wname << "\"\n";
160  ATH_MSG_WARNING("Multiple NominalWeightNames match for this MC sample!\n" + s_multiple_matches.str()
161  + "\nThe one we will use is \"" + m_nominal_weight_name + "\". Check whether this is really correct!");
162  }
163  if (!found_match) {
164  // if we get here, it means we are missing the correct name of the nominal weight
165  // user has to find it in the sample meta-data and add it to AT config file
166  ATH_MSG_ERROR("No MC weight matches any of the names specified by NominalWeightNames "
167  "option\nThis may indicate a sample with non-standard nominal MC weight name!");
168  std::stringstream weights_log;
169  for (size_t w_indx=0; w_indx < pmg_weight_names.size(); ++w_indx) {
170  weights_log << "Weight " << w_indx << ": \"" << pmg_weight_names.at(w_indx) << "\"\n";
171  }
172  ATH_MSG_ERROR("The following weight names are available based on sample metadata:\n" + weights_log.str()
173  + "\nAdd the correct nominal weight name from this list into the NominalWeightNames option in your config file.");
174  return StatusCode::FAILURE;
175  }
176 
177  ATH_MSG_INFO("Using the following MC weight as nominal: \"" + m_config->nominalWeightName()
178  << "\", index: " << m_config->nominalWeightIndex());
179  return StatusCode::SUCCESS;
180  }
181 
183  if (m_config->isMC()) {
184  if (m_config->usePhotons()) top::check(m_photonSF->execute(), "Failed to execute photon SF");
185  if (m_config->useElectrons()) top::check(m_electronSF->execute(), "Failed to execute electron SF");
186  if (m_config->useFwdElectrons()) top::check(m_fwdElectronSF->execute(), "Failed to execute fwd electron SF");
187  if (m_config->useMuons() &&
188  !m_config->isTruthDxAOD()) top::check(m_muonSF->execute(), "Failed to execute muon SF");
189  if (m_config->useTaus()) top::check(m_tauSF->execute(), "Failed to execute tau SF");
190  if (m_config->useJets()) top::check(m_jetSF->execute(), "Failed to execute jet SF");
191  if (m_config->useJets()) {
192  top::check(m_btagSF->execute(), "Failed to execute btag SF");
193  }
194  // Add Sherpa 22 weights directly here, if we get more
195  // PMG tools for reweighting then we should consider making
196  // a m_PMG_SF class, as with other corrections
197  if (m_config->isSherpa22Vjets()) {
198  const xAOD::EventInfo* eventInfo(nullptr);
199  top::check(evtStore()->retrieve(eventInfo, m_config->sgKeyEventInfo()), "Failed to retrieve EventInfo");
200  double sherpa_weight = m_sherpa_22_reweight_tool->getWeight();
201  eventInfo->auxdecor<double>("Sherpa22VJetsWeight") = sherpa_weight;
202  }
203  if ((m_config->useElectrons() || m_config->useMuons()) && m_config->useGlobalTrigger()) {
204  top::check(m_globalLeptonTriggerSF->execute(), "Failed to exectute global trigger SF");
205  }
206  }
207  return StatusCode::SUCCESS;
208  }
209 
211  if (m_config->doPileupReweighting()) top::check(m_pileupSF->execute(), "Failed to execute pileup SF");
212  return StatusCode::SUCCESS;
213  }
214 
216  float sf(1.);
217 
218  if (!m_config->isMC()) {
219  return sf;
220  }
221 
222  const xAOD::EventInfo* eventInfo(nullptr);
223  top::check(evtStore()->retrieve(eventInfo, m_config->sgKeyEventInfo()),
224  "Failed to retrieve EventInfo");
225 
226  if (eventInfo->isAvailable<float>("PileupWeight")) sf = eventInfo->auxdataConst<float>("PileupWeight");
227 
228  return sf;
229  }
230 
232  float sf(1.);
233 
234  if (!m_config->isMC()) {
235  return sf;
236  }
237  // Decorate the updated nominal weight if appropriate - note this is called early in top-xaod
238  const xAOD::EventInfo* eventInfo(nullptr);
239  top::check(evtStore()->retrieve(eventInfo, m_config->sgKeyEventInfo()), "Failed to retrieve EventInfo");
240 
241  // Check if the decoration is already present, and return it if so
242  if (eventInfo->isAvailable<float>("AnalysisTop_eventWeight")) return eventInfo->auxdataConst<float>(
243  "AnalysisTop_eventWeight");
244 
245  try {
246  sf = eventInfo->mcEventWeights().at(m_config->nominalWeightIndex());
247  eventInfo->auxdecor<float>("AnalysisTop_eventWeight") = sf;
248  } catch (std::out_of_range &e) {
249  ATH_MSG_ERROR("MC weight specified by index " << m_config->nominalWeightIndex()
250  << " does not exist: ");
251  throw;
252  }
253  return sf;
254  }
255 } // namespace top
python.PyKernel.retrieve
def retrieve(aClass, aKey=None)
Definition: PyKernel.py:110
top::ScaleFactorCalculator::m_pmg_truth_weight_tool
ToolHandle< PMGTools::IPMGTruthWeightTool > m_pmg_truth_weight_tool
Definition: ScaleFactorCalculator.h:73
top
TopConfig A simple configuration that is NOT a singleton.
Definition: AnalysisTrackingHelper.cxx:58
ATH_MSG_INFO
#define ATH_MSG_INFO(x)
Definition: AthMsgStreamMacros.h:31
find
std::string find(const std::string &s)
return a remapped string
Definition: hcg.cxx:135
top::ScaleFactorCalculator::m_electronSF
std::unique_ptr< top::ElectronScaleFactorCalculator > m_electronSF
Definition: ScaleFactorCalculator.h:64
xAOD::EventInfo_v1::mcEventWeights
const std::vector< float > & mcEventWeights() const
The weights of all the MC events used in the simulation.
AthCommonDataStore< AthCommonMsg< AlgTool > >::declareProperty
Gaudi::Details::PropertyBase & declareProperty(Gaudi::Property< T > &t)
Definition: AthCommonDataStore.h:145
top::ScaleFactorCalculator::mcEventWeight
float mcEventWeight() const
Definition: ScaleFactorCalculator.cxx:231
top::ScaleFactorCalculator::initialize_nominal_MC_weight
StatusCode initialize_nominal_MC_weight()
Definition: ScaleFactorCalculator.cxx:103
asg
Definition: DataHandleTestTool.h:28
top::ScaleFactorCalculator::m_globalLeptonTriggerSF
std::unique_ptr< top::GlobalLeptonTriggerCalculator > m_globalLeptonTriggerSF
Definition: ScaleFactorCalculator.h:72
top::ScaleFactorCalculator::initialize
StatusCode initialize()
Dummy implementation of the initialisation function.
Definition: ScaleFactorCalculator.cxx:36
SG::AuxElement::auxdecor
Decorator< T, ALLOC >::reference_type auxdecor(const std::string &name) const
Fetch an aux decoration, as a non-const reference.
EventTools.h
A few functions for doing operations on particles / events. Currently holds code for dR,...
SG::AuxElement::auxdataConst
Accessor< T, ALLOC >::const_reference_type auxdataConst(const std::string &name) const
Fetch an aux data variable, as a const reference.
AthCommonDataStore< AthCommonMsg< AlgTool > >::evtStore
ServiceHandle< StoreGateSvc > & evtStore()
The standard StoreGateSvc (event store) Returns (kind of) a pointer to the StoreGateSvc.
Definition: AthCommonDataStore.h:85
top::ScaleFactorCalculator::m_nominal_weight_name
std::string m_nominal_weight_name
Definition: ScaleFactorCalculator.h:75
ATH_MSG_ERROR
#define ATH_MSG_ERROR(x)
Definition: AthMsgStreamMacros.h:33
top::ScaleFactorCalculator::m_btagSF
std::unique_ptr< top::BTagScaleFactorCalculator > m_btagSF
Definition: ScaleFactorCalculator.h:69
top::ScaleFactorCalculator::m_sherpa_22_reweight_tool
ToolHandle< PMGTools::PMGSherpa22VJetsWeightTool > m_sherpa_22_reweight_tool
Definition: ScaleFactorCalculator.h:71
EL::StatusCode
::StatusCode StatusCode
StatusCode definition for legacy code.
Definition: PhysicsAnalysis/D3PDTools/EventLoop/EventLoop/StatusCode.h:22
top::ScaleFactorCalculator::pileupWeight
float pileupWeight() const
Definition: ScaleFactorCalculator.cxx:215
top::check
void check(bool thingToCheck, const std::string &usefulFailureMessage)
Print an error message and terminate if thingToCheck is false.
Definition: EventTools.cxx:15
top::ScaleFactorCalculator::m_jetSF
std::unique_ptr< top::JetScaleFactorCalculator > m_jetSF
Definition: ScaleFactorCalculator.h:68
top::ScaleFactorCalculator::execute
StatusCode execute()
Definition: ScaleFactorCalculator.cxx:182
SG::AuxElement::isAvailable
bool isAvailable(const std::string &name, const std::string &clsname="") const
Check if an aux variable is available for reading.
name
std::string name
Definition: Control/AthContainers/Root/debug.cxx:192
TopConfig.h
top::ScaleFactorCalculator::m_tauSF
std::unique_ptr< top::TauScaleFactorCalculator > m_tauSF
Definition: ScaleFactorCalculator.h:67
EventInfo.h
xAOD::EventInfo_v1
Class describing the basic event information.
Definition: EventInfo_v1.h:43
top::ScaleFactorCalculator::m_muonSF
std::unique_ptr< top::MuonScaleFactorCalculator > m_muonSF
Definition: ScaleFactorCalculator.h:66
DiTauMassTools::MaxHistStrategyV2::e
e
Definition: PhysicsAnalysis/TauID/DiTauMassTools/DiTauMassTools/HelperFunctions.h:26
top::ScaleFactorCalculator::m_pileupSF
std::unique_ptr< top::PileupScaleFactorCalculator > m_pileupSF
Definition: ScaleFactorCalculator.h:70
mc.weight_name
weight_name
Definition: mc.PhPy8EG_A14NNPDF23_NNLOPS_example.py:37
mapkey::sf
@ sf
Definition: TElectronEfficiencyCorrectionTool.cxx:38
ATH_MSG_WARNING
#define ATH_MSG_WARNING(x)
Definition: AthMsgStreamMacros.h:32
top::ScaleFactorCalculator::executePileup
StatusCode executePileup()
Definition: ScaleFactorCalculator.cxx:210
top::ScaleFactorCalculator::ScaleFactorCalculator
ScaleFactorCalculator(const std::string &name)
Definition: ScaleFactorCalculator.cxx:17
ScaleFactorCalculator.h
top::ScaleFactorCalculator::m_config
std::shared_ptr< top::TopConfig > m_config
Definition: ScaleFactorCalculator.h:61
top::ScaleFactorCalculator::m_fwdElectronSF
std::unique_ptr< top::FwdElectronScaleFactorCalculator > m_fwdElectronSF
Definition: ScaleFactorCalculator.h:65
top::ScaleFactorCalculator::m_photonSF
std::unique_ptr< top::PhotonScaleFactorCalculator > m_photonSF
Definition: ScaleFactorCalculator.h:63