Go to the documentation of this file.00001 #ifndef CandAlgos_NamedCandCombiner_h
00002 #define CandAlgos_NamedCandCombiner_h
00003
00015 #include "FWCore/Framework/interface/EDProducer.h"
00016 #include "FWCore/Framework/interface/Frameworkfwd.h"
00017 #include "CommonTools/CandUtils/interface/NamedCandCombiner.h"
00018 #include "CommonTools/CandAlgos/interface/decayParser.h"
00019 #include "CommonTools/Utilities/interface/StringCutObjectSelector.h"
00020 #include "DataFormats/Common/interface/Handle.h"
00021 #include "FWCore/Framework/interface/Event.h"
00022 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00023 #include "CommonTools/UtilAlgos/interface/ParameterAdapter.h"
00024 #include "CommonTools/UtilAlgos/interface/EventSetupInitTrait.h"
00025 #include "CommonTools/Utilities/interface/cutParser.h"
00026 #include "DataFormats/Candidate/interface/Candidate.h"
00027 #include "DataFormats/Candidate/interface/NamedCompositeCandidate.h"
00028 #include "DataFormats/Candidate/interface/NamedCompositeCandidateFwd.h"
00029 #include "FWCore/Utilities/interface/EDMException.h"
00030 #include <string>
00031 #include <vector>
00032 #include <algorithm>
00033
00034 namespace edm {
00035 class ParameterSet;
00036 }
00037
00038 namespace reco {
00039 namespace modules {
00040
00041 struct NamedCandCombinerBase : public edm::EDProducer {
00042 NamedCandCombinerBase( const edm::ParameterSet & cfg ) :
00043 setLongLived_(false),
00044 setMassConstraint_(false),
00045 setPdgId_(false) {
00046 using namespace cand::parser;
00047 using namespace std;
00048 string decay(cfg.getParameter<string>("decay"));
00049 if(decayParser(decay, labels_))
00050 for(vector<ConjInfo>::iterator label = labels_.begin();
00051 label != labels_.end(); ++label)
00052 if(label->mode_ == ConjInfo::kPlus)
00053 dauCharge_.push_back( 1 );
00054 else if (label->mode_ == ConjInfo::kMinus)
00055 dauCharge_.push_back(-1);
00056 else
00057 dauCharge_.push_back(0);
00058 else
00059 throw edm::Exception(edm::errors::Configuration,
00060 "failed to parse \"" + decay + "\"");
00061
00062 int lists = labels_.size();
00063 if(lists != 2 && lists != 3)
00064 throw edm::Exception(edm::errors::LogicError,
00065 "invalid number of collections");
00066 bool found;
00067 const string setLongLived("setLongLived");
00068 vector<string> vBoolParams = cfg.getParameterNamesForType<bool>();
00069 found = find(vBoolParams.begin(), vBoolParams.end(), setLongLived) != vBoolParams.end();
00070 if(found) setLongLived_ = cfg.getParameter<bool>("setLongLived");
00071 const string setMassConstraint("setMassConstraint");
00072 found = find(vBoolParams.begin(), vBoolParams.end(), setMassConstraint) != vBoolParams.end();
00073 if(found) setMassConstraint_ = cfg.getParameter<bool>("setMassConstraint");
00074 const string setPdgId("setPdgId");
00075 vector<string> vIntParams = cfg.getParameterNamesForType<int>();
00076 found = find(vIntParams.begin(), vIntParams.end(), setPdgId) != vIntParams.end();
00077 if(found) { setPdgId_ = true; pdgId_ = cfg.getParameter<int>("setPdgId"); }
00078
00079 name_ = cfg.getParameter<std::string>( "name" );
00080 roles_= cfg.getParameter<std::vector<std::string> > ( "roles" );
00081 }
00082 protected:
00084 std::vector<cand::parser::ConjInfo> labels_;
00086 std::vector<int> dauCharge_;
00088 bool setLongLived_;
00090 bool setMassConstraint_;
00092 bool setPdgId_;
00094 int pdgId_;
00096 std::string name_;
00097
00098 std::vector<std::string> roles_;
00099 };
00100
00101 template<typename Selector,
00102 typename PairSelector = AnyPairSelector,
00103 typename Cloner = ::combiner::helpers::NormalClone,
00104 typename Setup = AddFourMomenta,
00105 typename Init = typename ::reco::modules::EventSetupInit<Setup>::type
00106 >
00107 class NamedCandCombiner : public NamedCandCombinerBase {
00108 public:
00110 explicit NamedCandCombiner( const edm::ParameterSet & cfg ) :
00111 NamedCandCombinerBase( cfg ),
00112 combiner_( name_,
00113 reco::modules::make<Selector>( cfg ),
00114 reco::modules::make<PairSelector>( cfg ),
00115 Setup( cfg ),
00116 cfg.existsAs<bool>("checkCharge") ? cfg.getParameter<bool>("checkCharge") : true,
00117 cfg.existsAs<bool>("checkOverlap") ? cfg.getParameter<bool>("checkOverlap") : true,
00118 dauCharge_ ) {
00119 produces<reco::NamedCompositeCandidateCollection>();
00120 }
00122 virtual ~NamedCandCombiner() { }
00123
00124 private:
00126 void produce(edm::Event& evt, const edm::EventSetup& es) {
00127 using namespace std;
00128 using namespace reco;
00129 Init::init(combiner_.setup(), evt, es);
00130 int n = labels_.size();
00131 std::vector<edm::Handle<CandidateView> > colls(n);
00132 for(int i = 0; i < n; ++i) {
00133 evt.getByLabel(labels_[i].tag_, colls[i]);
00134 }
00135 std::vector<CandidatePtrVector> cv;
00136 for(typename std::vector<edm::Handle<CandidateView> >::const_iterator c = colls.begin();
00137 c != colls.end(); ++ c) {
00138 CandidatePtrVector r;
00139 CandidateView::size_type n_view = (*c)->size();
00140 for ( CandidateView::size_type iview = 0; iview < n_view; ++iview ) {
00141 CandidatePtr ri( *c, iview );
00142 r.push_back( ri );
00143 }
00144 cv.push_back(r);
00145 }
00146 std::auto_ptr<NamedCompositeCandidateCollection> out = combiner_.combine(cv, roles_);
00147 if(setLongLived_ || setMassConstraint_ || setPdgId_) {
00148 typename NamedCompositeCandidateCollection::iterator i = out->begin(), e = out->end();
00149 for(; i != e; ++i) {
00150 i->setName( name_ );
00151 i->setRoles( roles_ );
00152 i->applyRoles();
00153 if(setLongLived_) i->setLongLived();
00154 if(setMassConstraint_) i->setMassConstraint();
00155 if(setPdgId_) i->setPdgId(pdgId_);
00156 }
00157 }
00158 evt.put(out);
00159 }
00161 ::NamedCandCombiner<Selector, PairSelector, Cloner, Setup> combiner_;
00162 };
00163
00164 }
00165 }
00166
00167 #endif