00001 #include "PhysicsTools/PFCandProducer/interface/PFTopProjector.h"
00002 #include "PhysicsTools/PFCandProducer/interface/FetchCollection.h"
00003
00004 #include "DataFormats/ParticleFlowCandidate/interface/PileUpPFCandidate.h"
00005 #include "DataFormats/ParticleFlowCandidate/interface/PileUpPFCandidateFwd.h"
00006 #include "DataFormats/ParticleFlowCandidate/interface/IsolatedPFCandidate.h"
00007 #include "DataFormats/ParticleFlowCandidate/interface/IsolatedPFCandidateFwd.h"
00008 #include "DataFormats/JetReco/interface/PFJet.h"
00009 #include "DataFormats/JetReco/interface/PFJetCollection.h"
00010 #include "DataFormats/TauReco/interface/PFTau.h"
00011 #include "DataFormats/TauReco/interface/PFTauFwd.h"
00012
00013
00014 #include "DataFormats/TrackReco/interface/Track.h"
00015
00016 #include "FWCore/Framework/interface/ESHandle.h"
00017
00018
00019 #include "FWCore/Utilities/interface/Exception.h"
00020 #include "FWCore/Framework/interface/EventSetup.h"
00021
00022 #include "DataFormats/Math/interface/deltaR.h"
00023
00024 using namespace std;
00025 using namespace edm;
00026 using namespace reco;
00027
00028 const char* PFTopProjector::pfJetsOutLabel_ = "PFJets";
00029 const char* PFTopProjector::pfCandidatesOutLabel_ = "PFCandidates";
00030
00031 PFTopProjector::PFTopProjector(const edm::ParameterSet& iConfig) {
00032
00033 inputTagPFCandidates_
00034 = iConfig.getParameter<InputTag>("PFCandidates");
00035
00036 inputTagPileUpPFCandidates_
00037 = iConfig.getParameter<InputTag>("PileUpPFCandidates");
00038
00039 inputTagIsolatedElectrons_
00040 = iConfig.getParameter<InputTag>("IsolatedElectrons");
00041
00042 inputTagIsolatedMuons_
00043 = iConfig.getParameter<InputTag>("IsolatedMuons");
00044
00045 inputTagPFJets_
00046 = iConfig.getParameter<InputTag>("PFJets");
00047
00048 inputTagPFTaus_
00049 = iConfig.getParameter<InputTag>("PFTaus");
00050
00051 verbose_ =
00052 iConfig.getUntrackedParameter<bool>("verbose",false);
00053
00054
00055
00056
00057
00058 produces<reco::PFCandidateCollection>(pfCandidatesOutLabel_);
00059 produces<reco::PFJetCollection>(pfJetsOutLabel_);
00060
00061 if(verbose_) {
00062 ostringstream msg;
00063 msg<<"input PFCandidateCollection : "
00064 <<inputTagPFCandidates_<<endl
00065 <<"input PileUpPFCandidateCollection : "
00066 <<inputTagPileUpPFCandidates_<<endl
00067 <<"input IsolatedPFCandidates of type muon : "
00068 <<inputTagIsolatedMuons_<<endl
00069 <<"input IsolatedPFCandidates of type electron : "
00070 <<inputTagIsolatedElectrons_<<endl
00071 <<"input PFJetCollection : "
00072 <<inputTagPFJets_<<endl
00073 <<"input PFTauCollection : "
00074 <<inputTagPFTaus_<<endl;
00075 cout<<msg.str()<<endl;
00076
00077 }
00078 }
00079
00080
00081
00082 PFTopProjector::~PFTopProjector() { }
00083
00084
00085
00086 void PFTopProjector::beginJob(const edm::EventSetup & es) { }
00087
00088
00089 void PFTopProjector::produce(Event& iEvent,
00090 const EventSetup& iSetup) {
00091
00092
00093 if( verbose_)
00094 cout<<"Event -------------------- "<<iEvent.id().event()<<endl;
00095
00096
00097
00098
00099
00100 Handle<PFCandidateCollection> pfCandidates;
00101 pfpat::fetchCollection(pfCandidates,
00102 inputTagPFCandidates_,
00103 iEvent );
00104
00105 if( !pfCandidates.isValid() ) {
00106 std::ostringstream err;
00107 err<<"The collection of input PFCandidates must be supplied."<<endl
00108 <<"It is now set to : "<<inputTagPFCandidates_<<endl;
00109 edm::LogError("PFPAT")<<err.str();
00110 throw cms::Exception( "MissingProduct", err.str());
00111 }
00112
00113 edm::ProductID pfCandidatesID = pfCandidates.id();
00114
00115
00116
00117
00118
00119
00120
00121
00122 Handle<PileUpPFCandidateCollection> pfPileUpCandidates;
00123 pfpat::fetchCollection(pfPileUpCandidates,
00124 inputTagPileUpPFCandidates_,
00125 iEvent );
00126
00127 Handle<PFCandidateCollection> pfIsolatedElectrons;
00128 pfpat::fetchCollection(pfIsolatedElectrons,
00129 inputTagIsolatedElectrons_,
00130 iEvent );
00131
00132 Handle<PFCandidateCollection> pfIsolatedMuons;
00133 pfpat::fetchCollection(pfIsolatedMuons,
00134 inputTagIsolatedMuons_,
00135 iEvent );
00136
00137 Handle<PFJetCollection> pfJets;
00138 pfpat::fetchCollection(pfJets,
00139 inputTagPFJets_,
00140 iEvent );
00141
00142 Handle<PFTauCollection> pfTaus;
00143 pfpat::fetchCollection(pfTaus,
00144 inputTagPFTaus_,
00145 iEvent );
00146
00147 if(verbose_) {
00148 cout<<"Top projector: event "<<iEvent.id().event()<<endl;
00149 cout<<"product Ids --------------------"<<endl;
00150 cout<<"PF : "<<pfCandidates.id()<<endl
00151 <<"PFPU : "<<pfPileUpCandidates.id()<<endl
00152 <<"PFIso e : "<<pfIsolatedElectrons.id()<<endl
00153 <<"PFIso mu : "<<pfIsolatedMuons.id()<<endl
00154 <<"PFJets : "<<pfJets.id()<<endl
00155 <<"PFTaus : "<<pfTaus.id()<<endl;
00156 }
00157
00158
00159
00160
00161 auto_ptr< reco::PFCandidateCollection >
00162 pPFCandidateOutput( new reco::PFCandidateCollection );
00163
00164 auto_ptr< reco::PFJetCollection >
00165 pPFJetOutput( new reco::PFJetCollection );
00166
00167
00168
00169 vector<bool> masked( pfCandidates->size(), false);
00170
00171 assert( pfCandidates.isValid() );
00172
00173
00174 processCollection( pfTaus, pfCandidates, masked,
00175 "PFTau");
00176 processCollection( pfJets, pfCandidates, masked,
00177 "PFJet");
00178 processCollection( pfPileUpCandidates, pfCandidates, masked,
00179 "PileUpParticle");
00180 processCollection( pfIsolatedElectrons, pfCandidates, masked,
00181 "IsoElectron");
00182 processCollection( pfIsolatedMuons, pfCandidates, masked,
00183 "IsoMuon");
00184
00185
00186 const PFCandidateCollection& inCands = *pfCandidates;
00187
00188 if(verbose_)
00189 cout<<" Remaining PFCandidates ------ "<<endl;
00190
00191 for(unsigned i=0; i<inCands.size(); i++) {
00192
00193 if(masked[i]) {
00194 if(verbose_)
00195 cout<<"X "<<i<<" "<<inCands[i]<<endl;
00196 continue;
00197 }
00198 else {
00199 if(verbose_)
00200 cout<<"O "<<i<<" "<<inCands[i]<<endl;
00201 PFCandidatePtr motherPtr( pfCandidates, i );
00202 pPFCandidateOutput->push_back( inCands[i] );
00203 pPFCandidateOutput->back().setSourcePtr(motherPtr);
00204 }
00205 }
00206
00207 iEvent.put( pPFCandidateOutput, pfCandidatesOutLabel_ );
00208
00209
00210
00211
00212 if( pfJets.isValid() ) {
00213 vector<bool> maskedJets( pfJets->size(), false);
00214
00215
00216 processCollection( pfTaus, pfJets, maskedJets,
00217 "PFTau masking PFJets");
00218
00219
00220 const PFJetCollection& inJets = *pfJets;
00221
00222 if(verbose_)
00223 cout<<" Remaining PFJets ------ "<<endl;
00224
00225 for(unsigned i=0; i<inJets.size(); i++) {
00226
00227 if(maskedJets[i]) {
00228 if(verbose_)
00229 cout<<"X "<<i<<" "<<inJets[i]<<endl;
00230 continue;
00231 }
00232 else {
00233 if(verbose_)
00234 cout<<"O "<<i<<" "<<inJets[i]<<endl;
00235 pPFJetOutput->push_back( inJets[i] );
00236 }
00237 }
00238 }
00239
00240
00241
00242 iEvent.put( pPFJetOutput, pfJetsOutLabel_);
00243
00244
00245
00246 }
00247
00248
00249 void
00250 PFTopProjector::ptrToAncestor( reco::CandidatePtr candPtr,
00251 reco::CandidatePtrVector& ancestors,
00252 const edm::ProductID& ancestorsID ) const {
00253
00254
00255
00256 unsigned nSources = candPtr->numberOfSourceCandidatePtrs();
00257
00258
00259
00260
00261
00262 for(unsigned i=0; i<nSources; i++) {
00263
00264 CandidatePtr mother = candPtr->sourceCandidatePtr(i);
00265
00266
00267 if( mother.id() != ancestorsID ) {
00268
00269 ptrToAncestor( mother, ancestors, ancestorsID);
00270 }
00271 else {
00272
00273 ancestors.push_back( mother );
00274 }
00275 }
00276 }
00277
00278
00279
00280 void PFTopProjector::maskAncestors( const reco::CandidatePtrVector& ancestors,
00281 std::vector<bool>& masked ) const {
00282
00283 for(unsigned i=0; i<ancestors.size(); i++) {
00284 unsigned index = ancestors[i].key();
00285 assert( index<masked.size() );
00286
00287
00288
00289
00290
00291 masked[index] = true;
00292 }
00293 }
00294
00295
00296
00297
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307
00308
00309
00310
00311
00312
00313