CMS 3D CMS Logo

/data/refman/pasoursint/CMSSW_6_1_2_SLHC2/src/PhysicsTools/PatAlgos/plugins/PATCleaner.h

Go to the documentation of this file.
00001 #ifndef PhysicsTools_PatAlgos_plugins_PATCleaner_h
00002 #define PhysicsTools_PatAlgos_plugins_PATCleaner_h
00003 //
00004 // $Id: PATCleaner.h,v 1.3 2010/10/20 23:08:30 wmtan Exp $
00005 //
00006 
00018 #include "FWCore/Framework/interface/EDProducer.h"
00019 #include "FWCore/Framework/interface/Event.h"
00020 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00021 #include "FWCore/Utilities/interface/InputTag.h"
00022 
00023 #include "CommonTools/Utils/interface/StringObjectFunction.h"
00024 #include "CommonTools/Utils/interface/StringCutObjectSelector.h"
00025 
00026 #include "DataFormats/PatCandidates/interface/Electron.h"
00027 #include "DataFormats/PatCandidates/interface/Muon.h"
00028 #include "DataFormats/PatCandidates/interface/Tau.h"
00029 #include "DataFormats/PatCandidates/interface/Photon.h"
00030 #include "DataFormats/PatCandidates/interface/Jet.h"
00031 #include "DataFormats/PatCandidates/interface/MET.h"
00032 #include "DataFormats/PatCandidates/interface/GenericParticle.h"
00033 #include "DataFormats/PatCandidates/interface/PFParticle.h"
00034 
00035 #include "PhysicsTools/PatAlgos/interface/OverlapTest.h"
00036 #include <boost/ptr_container/ptr_vector.hpp>
00037 
00038 namespace pat {
00039 
00040   template<class PATObjType>
00041   class PATCleaner : public edm::EDProducer {
00042     public:
00043       explicit PATCleaner(const edm::ParameterSet & iConfig);
00044       virtual ~PATCleaner() {}
00045 
00046       virtual void produce(edm::Event & iEvent, const edm::EventSetup & iSetup);
00047 
00048     private:
00049       typedef StringCutObjectSelector<PATObjType> Selector;
00050 
00051       edm::InputTag src_;
00052       bool doPreselection_, doFinalCut_;  
00053       Selector preselectionCut_;
00054       Selector finalCut_;
00055 
00056       typedef pat::helper::OverlapTest OverlapTest;
00057       // make a list of overlap tests (ptr_vector instead of std::vector because they're polymorphic)
00058       boost::ptr_vector<OverlapTest> overlapTests_;
00059   };
00060 
00061 } // namespace
00062 
00063 template <class PATObjType>
00064 pat::PATCleaner<PATObjType>::PATCleaner(const edm::ParameterSet & iConfig) :
00065     src_(iConfig.getParameter<edm::InputTag>("src")),
00066     preselectionCut_(iConfig.getParameter<std::string>("preselection")),
00067     finalCut_(iConfig.getParameter<std::string>("finalCut"))
00068 {
00069     // pick parameter set for overlaps
00070     edm::ParameterSet overlapPSet = iConfig.getParameter<edm::ParameterSet>("checkOverlaps");
00071     // get all the names of the tests (all nested PSets in this PSet)
00072     std::vector<std::string> overlapNames = overlapPSet.getParameterNamesForType<edm::ParameterSet>();
00073     // loop on them
00074     for (std::vector<std::string>::const_iterator itn = overlapNames.begin(); itn != overlapNames.end(); ++itn) {
00075         // retrieve configuration
00076         edm::ParameterSet cfg = overlapPSet.getParameter<edm::ParameterSet>(*itn);
00077         // skip empty parameter sets
00078         if (cfg.empty()) continue; 
00079         // get the name of the algorithm to use
00080         std::string algorithm = cfg.getParameter<std::string>("algorithm");
00081         // create the appropriate OverlapTest
00082         if (algorithm == "byDeltaR") {
00083             overlapTests_.push_back(new pat::helper::BasicOverlapTest(*itn, cfg));
00084         } else if (algorithm == "bySuperClusterSeed") {
00085             overlapTests_.push_back(new pat::helper::OverlapBySuperClusterSeed(*itn, cfg));
00086         } else {
00087             throw cms::Exception("Configuration") << "PATCleaner for " << src_ << ": unsupported algorithm '" << algorithm << "'\n";
00088         }
00089     }
00090         
00091 
00092     produces<std::vector<PATObjType> >();
00093 }
00094 
00095 template <class PATObjType>
00096 void 
00097 pat::PATCleaner<PATObjType>::produce(edm::Event & iEvent, const edm::EventSetup & iSetup) {
00098 
00099   // Read the input. We use edm::View<> in case the input happes to be something different than a std::vector<>
00100   edm::Handle<edm::View<PATObjType> > candidates;
00101   iEvent.getByLabel(src_, candidates);
00102 
00103   // Prepare a collection for the output
00104   std::auto_ptr< std::vector<PATObjType> > output(new std::vector<PATObjType>());
00105 
00106   // initialize the overlap tests
00107   for (boost::ptr_vector<OverlapTest>::iterator itov = overlapTests_.begin(), edov = overlapTests_.end(); itov != edov; ++itov) {
00108     itov->readInput(iEvent,iSetup);
00109   }
00110 
00111   for (typename edm::View<PATObjType>::const_iterator it = candidates->begin(), ed = candidates->end(); it != ed; ++it) {
00112       // Apply a preselection to the inputs and copy them in the output
00113       if (!preselectionCut_(*it)) continue; 
00114 
00115       // Add it to the list and take a reference to it, so it can be modified (e.g. to set the overlaps)
00116       // If at some point I'll decide to drop this item, I'll use pop_back to remove it
00117       output->push_back(*it);
00118       PATObjType &obj = output->back();
00119 
00120       // Look for overlaps
00121       bool badForOverlap = false;
00122       for (boost::ptr_vector<OverlapTest>::iterator itov = overlapTests_.begin(), edov = overlapTests_.end(); itov != edov; ++itov) {
00123         reco::CandidatePtrVector overlaps;
00124         bool hasOverlap = itov->fillOverlapsForItem(obj, overlaps);
00125         if (hasOverlap && itov->requireNoOverlaps()) { 
00126             badForOverlap = true; // mark for discarding
00127             break; // no point in checking the others, as this item will be discarded
00128         }
00129         obj.setOverlaps(itov->name(), overlaps);
00130       }
00131       if (badForOverlap) { output->pop_back(); continue; }
00132 
00133       // Apply one final selection cut
00134       if (!finalCut_(obj)) output->pop_back();
00135   }
00136 
00137   iEvent.put(output);
00138 }
00139 
00140 
00141 #endif