Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2024-04-06 12:09:54

0001 #include "DQMOffline/Trigger/interface/EgHLTOfflineSource.h"
0002 
0003 #include "DQMOffline/Trigger/interface/EgHLTEleHLTFilterMon.h"
0004 #include "DQMOffline/Trigger/interface/EgHLTPhoHLTFilterMon.h"
0005 
0006 #include "DQMOffline/Trigger/interface/EgHLTDQMCut.h"
0007 #include "DQMOffline/Trigger/interface/EgHLTTrigTools.h"
0008 
0009 #include "DQMServices/Core/interface/DQMStore.h"
0010 
0011 #include "FWCore/Framework/interface/Run.h"
0012 #include "HLTrigger/HLTcore/interface/HLTConfigProvider.h"
0013 
0014 #include <boost/algorithm/string.hpp>
0015 
0016 //#include "DQMOffline/Trigger/interface/EgHLTCutCodes.h"
0017 #include "DataFormats/TrackReco/interface/Track.h"
0018 #include "DataFormats/EgammaCandidates/interface/ElectronFwd.h"
0019 #include "DataFormats/HLTReco/interface/TriggerFilterObjectWithRefs.h"
0020 using namespace egHLT;
0021 
0022 EgHLTOfflineSource::EgHLTOfflineSource(const edm::ParameterSet& iConfig) : nrEventsProcessed_(0) {
0023   binData_.setup(iConfig.getParameter<edm::ParameterSet>("binData"));
0024   cutMasks_.setup(iConfig.getParameter<edm::ParameterSet>("cutMasks"));
0025   eleHLTFilterNames_ = iConfig.getParameter<std::vector<std::string> >("eleHLTFilterNames");
0026   eleHLTFilterNames2Leg_ = iConfig.getParameter<std::vector<std::string> >("eleHLTFilterNames2Leg");
0027   phoHLTFilterNames_ = iConfig.getParameter<std::vector<std::string> >("phoHLTFilterNames");
0028   eleTightLooseTrigNames_ = iConfig.getParameter<std::vector<std::string> >("eleTightLooseTrigNames");
0029   diEleTightLooseTrigNames_ = iConfig.getParameter<std::vector<std::string> >("diEleTightLooseTrigNames");
0030   phoTightLooseTrigNames_ = iConfig.getParameter<std::vector<std::string> >("phoTightLooseTrigNames");
0031   diPhoTightLooseTrigNames_ = iConfig.getParameter<std::vector<std::string> >("diPhoTightLooseTrigNames");
0032 
0033   filterInactiveTriggers_ = iConfig.getParameter<bool>("filterInactiveTriggers");
0034   hltTag_ = iConfig.getParameter<std::string>("hltTag");
0035   dohep_ = iConfig.getParameter<bool>("doHEP");
0036 
0037   dirName_ = iConfig.getParameter<std::string>(
0038       "DQMDirName");  //"HLT/EgHLTOfflineSource_" + iConfig.getParameter<std::string>("@module_label");
0039 
0040   subdirName_ = iConfig.getParameter<std::string>("subDQMDirName");
0041 
0042   offEvtHelper_.setup(iConfig, consumesCollector());
0043 }
0044 
0045 EgHLTOfflineSource::~EgHLTOfflineSource() {
0046   // LogDebug("EgHLTOfflineSource") << "destructor called";
0047   for (auto& eleFilterMonHist : eleFilterMonHists_) {
0048     delete eleFilterMonHist;
0049   }
0050   for (auto& phoFilterMonHist : phoFilterMonHists_) {
0051     delete phoFilterMonHist;
0052   }
0053   for (auto& eleMonElem : eleMonElems_) {
0054     delete eleMonElem;
0055   }
0056   for (auto& phoMonElem : phoMonElems_) {
0057     delete phoMonElem;
0058   }
0059 }
0060 
0061 void EgHLTOfflineSource::bookHistograms(DQMStore::IBooker& iBooker, edm::Run const& run, edm::EventSetup const& c) {
0062   iBooker.setCurrentFolder(dirName_);
0063 
0064   //the one monitor element the source fills directly
0065   dqmErrsMonElem_ = iBooker.book1D("dqmErrors", "EgHLTOfflineSource Errors", 101, -0.5, 100.5);
0066   nrEventsProcessedMonElem_ = iBooker.bookInt("nrEventsProcessed");
0067 
0068   //if the HLTConfig changes during the job, the results are "un predictable" but in practice should be fine
0069   //the HLTConfig is used for working out which triggers are active, working out which filternames correspond to paths and L1 seeds
0070   //assuming those dont change for E/g it *should* be fine
0071   HLTConfigProvider hltConfig;
0072   bool changed = false;
0073   hltConfig.init(run, c, hltTag_, changed);
0074   if (filterInactiveTriggers_)
0075     filterTriggers(hltConfig);
0076 
0077   std::vector<std::string> hltFiltersUsed;
0078   getHLTFilterNamesUsed(hltFiltersUsed);
0079   trigCodes.reset(TrigCodes::makeCodes(hltFiltersUsed));
0080 
0081   offEvtHelper_.setupTriggers(hltConfig, hltFiltersUsed, *trigCodes);
0082 
0083   MonElemFuncs monElemFuncs(iBooker, *trigCodes);
0084 
0085   //now book ME's
0086   iBooker.setCurrentFolder(dirName_ + "/" + subdirName_);
0087   //each trigger path with generate object distributions and efficiencies (BUT not trigger efficiencies...)
0088   for (auto const& eleHLTFilterName : eleHLTFilterNames_) {
0089     iBooker.setCurrentFolder(dirName_ + "/" + subdirName_ + "/" + eleHLTFilterName);
0090     addEleTrigPath(monElemFuncs, eleHLTFilterName);
0091   }
0092   for (auto const& phoHLTFilterName : phoHLTFilterNames_) {
0093     iBooker.setCurrentFolder(dirName_ + "/" + subdirName_ + "/" + phoHLTFilterName);
0094     addPhoTrigPath(monElemFuncs, phoHLTFilterName);
0095   }
0096   //efficiencies of one trigger path relative to another
0097   monElemFuncs.initTightLooseTrigHists(eleMonElems_, eleTightLooseTrigNames_, binData_, "gsfEle");
0098   //new EgHLTDQMVarCut<OffEle>(cutMasks_.stdEle,&OffEle::cutCode));
0099   //monElemFuncs.initTightLooseTrigHistsTrigCuts(eleMonElems_,eleTightLooseTrigNames_,binData_);
0100 
0101   monElemFuncs.initTightLooseTrigHists(phoMonElems_, phoTightLooseTrigNames_, binData_, "pho");
0102   //    new EgHLTDQMVarCut<OffPho>(cutMasks_.stdPho,&OffPho::cutCode));
0103   //monElemFuncs.initTightLooseTrigHistsTrigCuts(phoMonElems_,phoTightLooseTrigNames_,binData_);
0104 
0105   //di-object triggers
0106   monElemFuncs.initTightLooseTrigHists(eleMonElems_, diEleTightLooseTrigNames_, binData_, "gsfEle");
0107   //    new EgDiEleCut(cutMasks_.stdEle,&OffEle::cutCode));
0108   monElemFuncs.initTightLooseTrigHists(phoMonElems_, diPhoTightLooseTrigNames_, binData_, "pho");
0109   //                new EgDiPhoCut(cutMasks_.stdPho,&OffPho::cutCode));
0110 
0111   monElemFuncs.initTightLooseDiObjTrigHistsTrigCuts(eleMonElems_, diEleTightLooseTrigNames_, binData_);
0112   monElemFuncs.initTightLooseDiObjTrigHistsTrigCuts(phoMonElems_, diPhoTightLooseTrigNames_, binData_);
0113 
0114   //tag and probe trigger efficiencies
0115   //this is to do measure the trigger efficiency with respect to a fully selected offline electron
0116   //using a tag and probe technique (note: this will be different to the trigger efficiency normally calculated)
0117   bool doTrigTagProbeEff = false;
0118   if (doTrigTagProbeEff && (!dohep_)) {
0119     for (auto const& eleHLTFilterName : eleHLTFilterNames_) {
0120       iBooker.setCurrentFolder(dirName_ + "/" + subdirName_ + "/" + eleHLTFilterName);
0121       monElemFuncs.initTrigTagProbeHist(eleMonElems_, eleHLTFilterName, cutMasks_.trigTPEle, binData_);
0122     }
0123     for (auto const& phoHLTFilterName : phoHLTFilterNames_) {
0124       iBooker.setCurrentFolder(dirName_ + "/" + subdirName_ + "/" + phoHLTFilterName);
0125       monElemFuncs.initTrigTagProbeHist(phoMonElems_, phoHLTFilterName, cutMasks_.trigTPPho, binData_);
0126     }
0127     for (auto& i : eleHLTFilterNames2Leg_) {
0128       iBooker.setCurrentFolder(dirName_ + "/" + subdirName_ + "/" + i.substr(i.find("::") + 2));
0129       //std::cout<<"FilterName: "<<eleHLTFilterNames2Leg_[i]<<std::endl;
0130       //std::cout<<"Folder: "<<eleHLTFilterNames2Leg_[i].substr(eleHLTFilterNames2Leg_[i].find("::")+2)<<std::endl;
0131       monElemFuncs.initTrigTagProbeHist_2Leg(eleMonElems_, i, cutMasks_.trigTPEle, binData_);
0132     }
0133     //tag and probe not yet implimented for photons (attemping to see if it makes sense first)
0134     // monElemFuncs.initTrigTagProbeHists(phoMonElems,phoHLTFilterNames_);
0135   }
0136 
0137   iBooker.setCurrentFolder(dirName_);
0138 }
0139 
0140 void EgHLTOfflineSource::analyze(const edm::Event& iEvent, const edm::EventSetup& iSetup) {
0141   const double weight = 1.;  //we have the ability to weight but its disabled for now - maybe use this for prescales?
0142   nrEventsProcessed_++;
0143   nrEventsProcessedMonElem_->Fill(nrEventsProcessed_);
0144   int errCode = offEvtHelper_.makeOffEvt(iEvent, iSetup, offEvt_, *trigCodes);
0145   if (errCode != 0) {
0146     dqmErrsMonElem_->Fill(errCode);
0147     return;
0148   }
0149 
0150   for (auto& eleFilterMonHist : eleFilterMonHists_) {
0151     eleFilterMonHist->fill(offEvt_, weight);
0152   }
0153   for (auto& phoFilterMonHist : phoFilterMonHists_) {
0154     phoFilterMonHist->fill(offEvt_, weight);
0155   }
0156 
0157   for (auto& eleMonElem : eleMonElems_) {
0158     const std::vector<OffEle>& eles = offEvt_.eles();
0159     for (auto const& ele : eles) {
0160       eleMonElem->fill(ele, offEvt_, weight);
0161     }
0162   }
0163 
0164   for (auto& phoMonElem : phoMonElems_) {
0165     const std::vector<OffPho>& phos = offEvt_.phos();
0166     for (auto const& pho : phos) {
0167       phoMonElem->fill(pho, offEvt_, weight);
0168     }
0169   }
0170 }
0171 
0172 void EgHLTOfflineSource::addEleTrigPath(MonElemFuncs& monElemFuncs, const std::string& name) {
0173   auto* filterMon =
0174       new EleHLTFilterMon(monElemFuncs, name, trigCodes->getCode(name.c_str()), binData_, cutMasks_, dohep_);
0175   eleFilterMonHists_.push_back(filterMon);
0176   std::sort(eleFilterMonHists_.begin(), eleFilterMonHists_.end(), [](auto const& x, auto const& y) { return *x < *y; });
0177   //takes a minor efficiency hit at initalisation to ensure that the vector is always sorted
0178 }
0179 
0180 void EgHLTOfflineSource::addPhoTrigPath(MonElemFuncs& monElemFuncs, const std::string& name) {
0181   PhoHLTFilterMon* filterMon =
0182       new PhoHLTFilterMon(monElemFuncs, name, trigCodes->getCode(name.c_str()), binData_, cutMasks_, dohep_);
0183   phoFilterMonHists_.push_back(filterMon);
0184   std::sort(phoFilterMonHists_.begin(), phoFilterMonHists_.end(), [](auto const& x, auto const& y) { return *x < *y; });
0185   //takes a minor efficiency hit at initalisation to ensure that the vector is always sorted
0186 }
0187 
0188 //this function puts every filter name used in a std::vector
0189 //due to the design, to ensure we get every filter, filters will be inserted multiple times
0190 //eg electron filters will contain photon triggers which are also in the photon filters
0191 //but only want one copy in the vector
0192 //this function is intended to be called once per job so some inefficiency can can be tolerated
0193 //therefore we will use a std::set to ensure that each filtername is only inserted once
0194 //and then convert to a std::vector
0195 void EgHLTOfflineSource::getHLTFilterNamesUsed(std::vector<std::string>& filterNames) const {
0196   std::set<std::string> filterNameSet;
0197   for (auto const& eleHLTFilterName : eleHLTFilterNames_)
0198     filterNameSet.insert(eleHLTFilterName);
0199   for (auto const& phoHLTFilterName : phoHLTFilterNames_)
0200     filterNameSet.insert(phoHLTFilterName);
0201   //here we are little more complicated as entries are of the form "tightTrig:looseTrig"
0202   //so we need to split them first
0203   for (auto const& eleTightLooseTrigName : eleTightLooseTrigNames_) {
0204     std::vector<std::string> trigNames;
0205     boost::split(trigNames, eleTightLooseTrigName, boost::is_any_of(std::string(":")));
0206     if (trigNames.size() != 2)
0207       continue;  //format incorrect
0208     filterNameSet.insert(trigNames[0]);
0209     filterNameSet.insert(trigNames[1]);
0210   }
0211   for (auto const& diEleTightLooseTrigName : diEleTightLooseTrigNames_) {
0212     std::vector<std::string> trigNames;
0213     boost::split(trigNames, diEleTightLooseTrigName, boost::is_any_of(std::string(":")));
0214     if (trigNames.size() != 2)
0215       continue;  //format incorrect
0216     filterNameSet.insert(trigNames[0]);
0217     filterNameSet.insert(trigNames[1]);
0218   }
0219   for (auto const& phoTightLooseTrigName : phoTightLooseTrigNames_) {
0220     std::vector<std::string> trigNames;
0221     boost::split(trigNames, phoTightLooseTrigName, boost::is_any_of(std::string(":")));
0222     if (trigNames.size() != 2)
0223       continue;  //format incorrect
0224     filterNameSet.insert(trigNames[0]);
0225     filterNameSet.insert(trigNames[1]);
0226   }
0227   for (auto const& diPhoTightLooseTrigName : diPhoTightLooseTrigNames_) {
0228     std::vector<std::string> trigNames;
0229     boost::split(trigNames, diPhoTightLooseTrigName, boost::is_any_of(std::string(":")));
0230     if (trigNames.size() != 2)
0231       continue;  //format incorrect
0232     filterNameSet.insert(trigNames[0]);
0233     filterNameSet.insert(trigNames[1]);
0234   }
0235   //right all the triggers are inserted once and only once in the set, convert to vector
0236   //very lazy, create a new vector so can use the constructor and then use swap to transfer
0237   std::vector<std::string>(filterNameSet.begin(), filterNameSet.end()).swap(filterNames);
0238 }
0239 
0240 void EgHLTOfflineSource::filterTriggers(const HLTConfigProvider& hltConfig) {
0241   std::vector<std::string> activeFilters;
0242   std::vector<std::string> activeEleFilters;
0243   std::vector<std::string> activeEle2LegFilters;
0244   std::vector<std::string> activePhoFilters;
0245   std::vector<std::string> activePho2LegFilters;
0246 
0247   trigTools::getActiveFilters(
0248       hltConfig, activeFilters, activeEleFilters, activeEle2LegFilters, activePhoFilters, activePho2LegFilters);
0249 
0250   trigTools::filterInactiveTriggers(eleHLTFilterNames_, activeEleFilters);
0251   trigTools::filterInactiveTriggers(phoHLTFilterNames_, activePhoFilters);
0252   trigTools::filterInactiveTriggers(eleHLTFilterNames2Leg_, activeEle2LegFilters);
0253   trigTools::filterInactiveTightLooseTriggers(eleTightLooseTrigNames_, activeEleFilters);
0254   trigTools::filterInactiveTightLooseTriggers(diEleTightLooseTrigNames_, activeEleFilters);
0255   trigTools::filterInactiveTightLooseTriggers(phoTightLooseTrigNames_, activePhoFilters);
0256   trigTools::filterInactiveTightLooseTriggers(diPhoTightLooseTrigNames_, activePhoFilters);
0257 }
0258 
0259 #include "FWCore/Framework/interface/MakerMacros.h"
0260 DEFINE_FWK_MODULE(EgHLTOfflineSource);