00001 #ifndef TtSemiLepHitFitProducer_h
00002 #define TtSemiLepHitFitProducer_h
00003
00004 #include "FWCore/Framework/interface/Event.h"
00005 #include "FWCore/Framework/interface/EDProducer.h"
00006 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00007
00008 #include "PhysicsTools/JetMCUtils/interface/combination.h"
00009 #include "AnalysisDataFormats/TopObjects/interface/TtSemiLepEvtPartons.h"
00010 #include "DataFormats/PatCandidates/interface/Lepton.h"
00011 #include "AnalysisDataFormats/TopObjects/interface/TtSemiEvtSolution.h"
00012
00013 #include "TopQuarkAnalysis/TopHitFit/interface/RunHitFit.h"
00014 #include "TopQuarkAnalysis/TopHitFit/interface/Top_Decaykin.h"
00015 #include "TopQuarkAnalysis/TopHitFit/interface/LeptonTranslatorBase.h"
00016 #include "TopQuarkAnalysis/TopHitFit/interface/JetTranslatorBase.h"
00017 #include "TopQuarkAnalysis/TopHitFit/interface/METTranslatorBase.h"
00018
00019 template <typename LeptonCollection>
00020 class TtSemiLepHitFitProducer : public edm::EDProducer {
00021
00022 public:
00023
00024 explicit TtSemiLepHitFitProducer(const edm::ParameterSet&);
00025 ~TtSemiLepHitFitProducer();
00026
00027 private:
00028
00029 virtual void produce(edm::Event&, const edm::EventSetup&);
00030
00031 edm::InputTag jets_;
00032 edm::InputTag leps_;
00033 edm::InputTag mets_;
00034
00036 int maxNJets_;
00038 int maxNComb_;
00039
00041 double maxEtaMu_;
00043 double maxEtaEle_;
00045 double maxEtaJet_;
00046
00048 std::string bTagAlgo_;
00050 double minBTagValueBJet_;
00052 double maxBTagValueNonBJet_;
00054 bool useBTag_;
00055
00057 double mW_;
00058 double mTop_;
00059
00061 std::string jetCorrectionLevel_;
00062
00064 double jes_;
00065 double jesB_;
00066
00067 struct FitResult {
00068 int Status;
00069 double Chi2;
00070 double Prob;
00071 double MT;
00072 double SigMT;
00073 pat::Particle HadB;
00074 pat::Particle HadP;
00075 pat::Particle HadQ;
00076 pat::Particle LepB;
00077 pat::Particle LepL;
00078 pat::Particle LepN;
00079 std::vector<int> JetCombi;
00080 bool operator< (const FitResult& rhs) { return Chi2 < rhs.Chi2; };
00081 };
00082
00083 typedef hitfit::RunHitFit<pat::Electron,pat::Muon,pat::Jet,pat::MET> PatHitFit;
00084
00085 edm::FileInPath hitfitDefault_;
00086 edm::FileInPath hitfitElectronResolution_;
00087 edm::FileInPath hitfitMuonResolution_;
00088 edm::FileInPath hitfitUdscJetResolution_;
00089 edm::FileInPath hitfitBJetResolution_;
00090 edm::FileInPath hitfitMETResolution_;
00091
00092 hitfit::LeptonTranslatorBase<pat::Electron> electronTranslator_;
00093 hitfit::LeptonTranslatorBase<pat::Muon> muonTranslator_;
00094 hitfit::JetTranslatorBase<pat::Jet> jetTranslator_;
00095 hitfit::METTranslatorBase<pat::MET> metTranslator_;
00096
00097 PatHitFit* HitFit;
00098 };
00099
00100 template<typename LeptonCollection>
00101 TtSemiLepHitFitProducer<LeptonCollection>::TtSemiLepHitFitProducer(const edm::ParameterSet& cfg):
00102 jets_ (cfg.getParameter<edm::InputTag>("jets")),
00103 leps_ (cfg.getParameter<edm::InputTag>("leps")),
00104 mets_ (cfg.getParameter<edm::InputTag>("mets")),
00105 maxNJets_ (cfg.getParameter<int> ("maxNJets" )),
00106 maxNComb_ (cfg.getParameter<int> ("maxNComb" )),
00107 bTagAlgo_ (cfg.getParameter<std::string> ("bTagAlgo" )),
00108 minBTagValueBJet_ (cfg.getParameter<double> ("minBDiscBJets" )),
00109 maxBTagValueNonBJet_ (cfg.getParameter<double> ("maxBDiscLightJets" )),
00110 useBTag_ (cfg.getParameter<bool> ("useBTagging" )),
00111 mW_ (cfg.getParameter<double> ("mW" )),
00112 mTop_ (cfg.getParameter<double> ("mTop" )),
00113 jetCorrectionLevel_ (cfg.getParameter<std::string> ("jetCorrectionLevel" )),
00114 jes_ (cfg.getParameter<double> ("jes" )),
00115 jesB_ (cfg.getParameter<double> ("jesB" )),
00116
00117
00118
00119 hitfitDefault_ (cfg.getUntrackedParameter<edm::FileInPath>(std::string("hitfitDefault"),
00120 edm::FileInPath(std::string("TopQuarkAnalysis/TopHitFit/data/setting/RunHitFitConfiguration.txt")))),
00121 hitfitElectronResolution_(cfg.getUntrackedParameter<edm::FileInPath>(std::string("hitfitElectronResolution"),
00122 edm::FileInPath(std::string("TopQuarkAnalysis/TopHitFit/data/resolution/tqafElectronResolution.txt")))),
00123 hitfitMuonResolution_ (cfg.getUntrackedParameter<edm::FileInPath>(std::string("hitfitMuonResolution"),
00124 edm::FileInPath(std::string("TopQuarkAnalysis/TopHitFit/data/resolution/tqafMuonResolution.txt")))),
00125 hitfitUdscJetResolution_ (cfg.getUntrackedParameter<edm::FileInPath>(std::string("hitfitUdscJetResolution"),
00126 edm::FileInPath(std::string("TopQuarkAnalysis/TopHitFit/data/resolution/tqafUdscJetResolution.txt")))),
00127 hitfitBJetResolution_ (cfg.getUntrackedParameter<edm::FileInPath>(std::string("hitfitBJetResolution"),
00128 edm::FileInPath(std::string("TopQuarkAnalysis/TopHitFit/data/resolution/tqafBJetResolution.txt")))),
00129 hitfitMETResolution_ (cfg.getUntrackedParameter<edm::FileInPath>(std::string("hitfitMETResolution"),
00130 edm::FileInPath(std::string("TopQuarkAnalysis/TopHitFit/data/resolution/tqafKtResolution.txt")))),
00131
00132
00133
00134 electronTranslator_(hitfitElectronResolution_.fullPath()),
00135 muonTranslator_ (hitfitMuonResolution_.fullPath()),
00136 jetTranslator_ (hitfitUdscJetResolution_.fullPath(), hitfitBJetResolution_.fullPath(), jetCorrectionLevel_, jes_, jesB_),
00137 metTranslator_ (hitfitMETResolution_.fullPath())
00138
00139 {
00140
00141 HitFit = new PatHitFit(electronTranslator_,
00142 muonTranslator_,
00143 jetTranslator_,
00144 metTranslator_,
00145 hitfitDefault_.fullPath(),
00146 mW_,
00147 mW_,
00148 mTop_);
00149
00150 maxEtaMu_ = 2.4;
00151 maxEtaEle_ = 2.5;
00152 maxEtaJet_ = 2.5;
00153
00154 edm::LogVerbatim( "TopHitFit" )
00155 << "\n"
00156 << "+++++++++++ TtSemiLepHitFitProducer ++++++++++++ \n"
00157 << " Due to the eta ranges for which resolutions \n"
00158 << " are provided in \n"
00159 << " TopQuarkAnalysis/TopHitFit/data/resolution/ \n"
00160 << " so far, the following cuts are currently \n"
00161 << " implemented in the TtSemiLepHitFitProducer: \n"
00162 << " |eta(muons )| <= " << maxEtaMu_ << " \n"
00163 << " |eta(electrons)| <= " << maxEtaEle_ << " \n"
00164 << " |eta(jets )| <= " << maxEtaJet_ << " \n"
00165 << "++++++++++++++++++++++++++++++++++++++++++++++++ \n";
00166
00167 produces< std::vector<pat::Particle> >("PartonsHadP");
00168 produces< std::vector<pat::Particle> >("PartonsHadQ");
00169 produces< std::vector<pat::Particle> >("PartonsHadB");
00170 produces< std::vector<pat::Particle> >("PartonsLepB");
00171 produces< std::vector<pat::Particle> >("Leptons");
00172 produces< std::vector<pat::Particle> >("Neutrinos");
00173
00174 produces< std::vector<std::vector<int> > >();
00175 produces< std::vector<double> >("Chi2");
00176 produces< std::vector<double> >("Prob");
00177 produces< std::vector<double> >("MT");
00178 produces< std::vector<double> >("SigMT");
00179 produces< std::vector<int> >("Status");
00180 produces< int >("NumberOfConsideredJets");
00181 }
00182
00183 template<typename LeptonCollection>
00184 TtSemiLepHitFitProducer<LeptonCollection>::~TtSemiLepHitFitProducer()
00185 {
00186 delete HitFit;
00187 }
00188
00189 template<typename LeptonCollection>
00190 void TtSemiLepHitFitProducer<LeptonCollection>::produce(edm::Event& evt, const edm::EventSetup& setup)
00191 {
00192 std::auto_ptr< std::vector<pat::Particle> > pPartonsHadP( new std::vector<pat::Particle> );
00193 std::auto_ptr< std::vector<pat::Particle> > pPartonsHadQ( new std::vector<pat::Particle> );
00194 std::auto_ptr< std::vector<pat::Particle> > pPartonsHadB( new std::vector<pat::Particle> );
00195 std::auto_ptr< std::vector<pat::Particle> > pPartonsLepB( new std::vector<pat::Particle> );
00196 std::auto_ptr< std::vector<pat::Particle> > pLeptons ( new std::vector<pat::Particle> );
00197 std::auto_ptr< std::vector<pat::Particle> > pNeutrinos ( new std::vector<pat::Particle> );
00198
00199 std::auto_ptr< std::vector<std::vector<int> > > pCombi ( new std::vector<std::vector<int> > );
00200 std::auto_ptr< std::vector<double> > pChi2 ( new std::vector<double> );
00201 std::auto_ptr< std::vector<double> > pProb ( new std::vector<double> );
00202 std::auto_ptr< std::vector<double> > pMT ( new std::vector<double> );
00203 std::auto_ptr< std::vector<double> > pSigMT ( new std::vector<double> );
00204 std::auto_ptr< std::vector<int> > pStatus( new std::vector<int> );
00205 std::auto_ptr< int > pJetsConsidered( new int );
00206
00207 edm::Handle<std::vector<pat::Jet> > jets;
00208 evt.getByLabel(jets_, jets);
00209
00210 edm::Handle<std::vector<pat::MET> > mets;
00211 evt.getByLabel(mets_, mets);
00212
00213 edm::Handle<LeptonCollection> leps;
00214 evt.getByLabel(leps_, leps);
00215
00216
00217
00218
00219
00220
00221 const unsigned int nPartons = 4;
00222
00223
00224 HitFit->clear();
00225
00226
00227 bool foundLepton = false;
00228 if(!leps->empty()) {
00229 double maxEtaLep = maxEtaMu_;
00230 if( !dynamic_cast<const reco::Muon*>(&((*leps)[0])) )
00231 maxEtaLep = maxEtaEle_;
00232 for(unsigned iLep=0; iLep<(*leps).size() && !foundLepton; ++iLep) {
00233 if(std::abs((*leps)[iLep].eta()) <= maxEtaLep) {
00234 HitFit->AddLepton((*leps)[iLep]);
00235 foundLepton = true;
00236 }
00237 }
00238 }
00239
00240
00241 unsigned int nJetsFound = 0;
00242 for(unsigned iJet=0; iJet<(*jets).size() && (int)nJetsFound!=maxNJets_; ++iJet) {
00243 double jet_eta = (*jets)[iJet].eta();
00244 if ( (*jets)[iJet].isCaloJet() ) {
00245 jet_eta = ((reco::CaloJet*) ((*jets)[iJet]).originalObject())->detectorP4().eta();
00246 }
00247 if(std::abs(jet_eta) <= maxEtaJet_) {
00248 HitFit->AddJet((*jets)[iJet]);
00249 nJetsFound++;
00250 }
00251 }
00252 *pJetsConsidered = nJetsFound;
00253
00254
00255 if(!mets->empty())
00256 HitFit->SetMet((*mets)[0]);
00257
00258 if( !foundLepton || mets->empty() || nJetsFound<nPartons ) {
00259
00260 pPartonsHadP->push_back( pat::Particle() );
00261 pPartonsHadQ->push_back( pat::Particle() );
00262 pPartonsHadB->push_back( pat::Particle() );
00263 pPartonsLepB->push_back( pat::Particle() );
00264 pLeptons ->push_back( pat::Particle() );
00265 pNeutrinos ->push_back( pat::Particle() );
00266
00267 std::vector<int> invalidCombi;
00268 for(unsigned int i = 0; i < nPartons; ++i)
00269 invalidCombi.push_back( -1 );
00270 pCombi->push_back( invalidCombi );
00271
00272 pChi2->push_back( -1. );
00273
00274 pProb->push_back( -1. );
00275
00276 pMT->push_back( -1. );
00277 pSigMT->push_back( -1. );
00278
00279 pStatus->push_back( -1 );
00280
00281 evt.put(pCombi);
00282 evt.put(pPartonsHadP, "PartonsHadP");
00283 evt.put(pPartonsHadQ, "PartonsHadQ");
00284 evt.put(pPartonsHadB, "PartonsHadB");
00285 evt.put(pPartonsLepB, "PartonsLepB");
00286 evt.put(pLeptons , "Leptons" );
00287 evt.put(pNeutrinos , "Neutrinos" );
00288 evt.put(pChi2 , "Chi2" );
00289 evt.put(pProb , "Prob" );
00290 evt.put(pMT , "MT" );
00291 evt.put(pSigMT , "SigMT" );
00292 evt.put(pStatus , "Status" );
00293 evt.put(pJetsConsidered, "NumberOfConsideredJets");
00294 return;
00295 }
00296
00297 std::list<FitResult> FitResultList;
00298
00299
00300
00301
00302
00303
00304
00305
00306
00307 size_t nHitFit = 0 ;
00308
00309
00310 size_t nHitFitJet = 0 ;
00311
00312
00313 std::vector<hitfit::Fit_Result> hitFitResult;
00314
00315
00316
00317
00318
00319
00320
00321 nHitFit = HitFit->FitAllPermutation();
00322
00323
00324
00325
00326
00327
00328 nHitFitJet = HitFit->GetUnfittedEvent()[0].njets();
00329
00330
00331 hitFitResult = HitFit->GetFitAllPermutation();
00332
00333
00334 for (size_t fit = 0 ; fit != nHitFit ; ++fit) {
00335
00336
00337 hitfit::Lepjets_Event fittedEvent = hitFitResult[fit].ev();
00338
00339
00340
00341
00342
00343
00344
00345
00346 std::vector<int> hitCombi(4);
00347 for (size_t jet = 0 ; jet != nHitFitJet ; ++jet) {
00348 int jet_type = fittedEvent.jet(jet).type();
00349
00350 switch(jet_type) {
00351 case 11: hitCombi[TtSemiLepEvtPartons::LepB ] = jet;
00352 break;
00353 case 12: hitCombi[TtSemiLepEvtPartons::HadB ] = jet;
00354 break;
00355 case 13: hitCombi[TtSemiLepEvtPartons::LightQ ] = jet;
00356 break;
00357 case 14: hitCombi[TtSemiLepEvtPartons::LightQBar] = jet;
00358 break;
00359 }
00360 }
00361
00362
00363
00364 hitfit::Lepjets_Event_Jet hadP_ = fittedEvent.jet(hitCombi[TtSemiLepEvtPartons::LightQ ]);
00365 hitfit::Lepjets_Event_Jet hadQ_ = fittedEvent.jet(hitCombi[TtSemiLepEvtPartons::LightQBar]);
00366 hitfit::Lepjets_Event_Jet hadB_ = fittedEvent.jet(hitCombi[TtSemiLepEvtPartons::HadB ]);
00367 hitfit::Lepjets_Event_Jet lepB_ = fittedEvent.jet(hitCombi[TtSemiLepEvtPartons::LepB ]);
00368 hitfit::Lepjets_Event_Lep lepL_ = fittedEvent.lep(0);
00369
00370
00372
00374
00376
00378
00379
00380
00381 if ( hitFitResult[fit].chisq() > 0
00382 && (!useBTag_ || ( useBTag_
00383 && jets->at(hitCombi[TtSemiLepEvtPartons::LightQ ]).bDiscriminator(bTagAlgo_) < maxBTagValueNonBJet_
00384 && jets->at(hitCombi[TtSemiLepEvtPartons::LightQBar]).bDiscriminator(bTagAlgo_) < maxBTagValueNonBJet_
00385 && jets->at(hitCombi[TtSemiLepEvtPartons::HadB ]).bDiscriminator(bTagAlgo_) > minBTagValueBJet_
00386 && jets->at(hitCombi[TtSemiLepEvtPartons::LepB ]).bDiscriminator(bTagAlgo_) > minBTagValueBJet_
00387 )
00388 )
00389 ) {
00390 FitResult result;
00391 result.Status = 0;
00392 result.Chi2 = hitFitResult[fit].chisq();
00393 result.Prob = exp(-1.0*(hitFitResult[fit].chisq())/2.0);
00394 result.MT = hitFitResult[fit].mt();
00395 result.SigMT= hitFitResult[fit].sigmt();
00396 result.HadB = pat::Particle(reco::LeafCandidate(0,
00397 math::XYZTLorentzVector(hadB_.p().x(), hadB_.p().y(),
00398 hadB_.p().z(), hadB_.p().t()), math::XYZPoint()));
00399 result.HadP = pat::Particle(reco::LeafCandidate(0,
00400 math::XYZTLorentzVector(hadP_.p().x(), hadP_.p().y(),
00401 hadP_.p().z(), hadP_.p().t()), math::XYZPoint()));
00402 result.HadQ = pat::Particle(reco::LeafCandidate(0,
00403 math::XYZTLorentzVector(hadQ_.p().x(), hadQ_.p().y(),
00404 hadQ_.p().z(), hadQ_.p().t()), math::XYZPoint()));
00405 result.LepB = pat::Particle(reco::LeafCandidate(0,
00406 math::XYZTLorentzVector(lepB_.p().x(), lepB_.p().y(),
00407 lepB_.p().z(), lepB_.p().t()), math::XYZPoint()));
00408 result.LepL = pat::Particle(reco::LeafCandidate(0,
00409 math::XYZTLorentzVector(lepL_.p().x(), lepL_.p().y(),
00410 lepL_.p().z(), lepL_.p().t()), math::XYZPoint()));
00411 result.LepN = pat::Particle(reco::LeafCandidate(0,
00412 math::XYZTLorentzVector(fittedEvent.met().x(), fittedEvent.met().y(),
00413 fittedEvent.met().z(), fittedEvent.met().t()), math::XYZPoint()));
00414 result.JetCombi = hitCombi;
00415
00416 FitResultList.push_back(result);
00417 }
00418
00419 }
00420
00421
00422 FitResultList.sort();
00423
00424
00425
00426
00427
00428
00429 if( ((unsigned)FitResultList.size())<1 ) {
00430 pPartonsHadP->push_back( pat::Particle() );
00431 pPartonsHadQ->push_back( pat::Particle() );
00432 pPartonsHadB->push_back( pat::Particle() );
00433 pPartonsLepB->push_back( pat::Particle() );
00434 pLeptons ->push_back( pat::Particle() );
00435 pNeutrinos ->push_back( pat::Particle() );
00436
00437 std::vector<int> invalidCombi;
00438 for(unsigned int i = 0; i < nPartons; ++i)
00439 invalidCombi.push_back( -1 );
00440 pCombi->push_back( invalidCombi );
00441
00442 pChi2->push_back( -1. );
00443
00444 pProb->push_back( -1. );
00445
00446 pMT->push_back( -1. );
00447 pSigMT->push_back( -1. );
00448
00449 pStatus->push_back( -1 );
00450 }
00451 else {
00452 unsigned int iComb = 0;
00453 for(typename std::list<FitResult>::const_iterator result = FitResultList.begin(); result != FitResultList.end(); ++result) {
00454 if(maxNComb_ >= 1 && iComb == (unsigned int) maxNComb_) break;
00455 iComb++;
00456
00457 pPartonsHadP->push_back( result->HadP );
00458 pPartonsHadQ->push_back( result->HadQ );
00459 pPartonsHadB->push_back( result->HadB );
00460 pPartonsLepB->push_back( result->LepB );
00461
00462 pLeptons->push_back( result->LepL );
00463
00464 pNeutrinos->push_back( result->LepN );
00465
00466 pCombi->push_back( result->JetCombi );
00467
00468 pChi2->push_back( result->Chi2 );
00469
00470 pProb->push_back( result->Prob );
00471
00472 pMT->push_back( result->MT );
00473 pSigMT->push_back( result->SigMT );
00474
00475 pStatus->push_back( result->Status );
00476 }
00477 }
00478 evt.put(pCombi);
00479 evt.put(pPartonsHadP, "PartonsHadP");
00480 evt.put(pPartonsHadQ, "PartonsHadQ");
00481 evt.put(pPartonsHadB, "PartonsHadB");
00482 evt.put(pPartonsLepB, "PartonsLepB");
00483 evt.put(pLeptons , "Leptons" );
00484 evt.put(pNeutrinos , "Neutrinos" );
00485 evt.put(pChi2 , "Chi2" );
00486 evt.put(pProb , "Prob" );
00487 evt.put(pMT , "MT" );
00488 evt.put(pSigMT , "SigMT" );
00489 evt.put(pStatus , "Status" );
00490 evt.put(pJetsConsidered, "NumberOfConsideredJets");
00491 }
00492
00493 #endif