CMS 3D CMS Logo

CMSSW_4_4_3_patch1/src/DQMOffline/JetMET/src/JPTJetAnalyzer.cc

Go to the documentation of this file.
00001 #include "DQMOffline/JetMET/interface/JPTJetAnalyzer.h"
00002 #include "DQMServices/Core/interface/MonitorElement.h"
00003 #include "DQMServices/Core/interface/DQMStore.h"
00004 #include "DataFormats/TrackReco/interface/Track.h"
00005 #include "DataFormats/JetReco/interface/CaloJet.h"
00006 #include "FWCore/Framework/interface/Event.h"
00007 #include "FWCore/Framework/interface/EventSetup.h"
00008 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00009 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00010 #include "DataFormats/Common/interface/Handle.h"
00011 #include "FWCore/Framework/interface/ESHandle.h"
00012 #include "DataFormats/Math/interface/deltaR.h"
00013 #include "RecoJets/JetAssociationAlgorithms/interface/JetTracksAssociationDRCalo.h"
00014 #include "DataFormats/Math/interface/Point3D.h"
00015 #include "MagneticField/Records/interface/IdealMagneticFieldRecord.h"
00016 #include "TrackingTools/Records/interface/TrackingComponentsRecord.h"
00017 #include "DataFormats/TrackingRecHit/interface/TrackingRecHit.h"
00018 #include "DataFormats/TrackerRecHit2D/interface/SiStripMatchedRecHit2D.h"
00019 #include "DataFormats/TrackerRecHit2D/interface/ProjectedSiStripRecHit2D.h"
00020 #include "DataFormats/TrackerRecHit2D/interface/SiStripRecHit2D.h"
00021 #include "DataFormats/TrackingRecHit/interface/InvalidTrackingRecHit.h"
00022 #include "DataFormats/SiStripCluster/interface/SiStripCluster.h"
00023 #include "DataFormats/DetId/interface/DetId.h"
00024 #include "DataFormats/SiStripDetId/interface/SiStripDetId.h"
00025 #include "CalibFormats/SiStripObjects/interface/SiStripQuality.h"
00026 #include "CondFormats/SiStripObjects/interface/SiStripNoises.h"
00027 #include "CalibFormats/SiStripObjects/interface/SiStripGain.h"
00028 #include "CalibTracker/Records/interface/SiStripQualityRcd.h"
00029 #include "CondFormats/DataRecord/interface/SiStripNoisesRcd.h"
00030 #include "CalibTracker/Records/interface/SiStripGainRcd.h"
00031 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00032 #include "RecoJets/JetProducers/interface/JetIDHelper.h"
00033 #include <cmath>
00034 #include <string>
00035 #include <memory>
00036 #include <vector>
00037 
00038 namespace jptJetAnalysis {
00039   
00040   // Helpper class to propagate tracks to the calo surface using the same implementation as the JetTrackAssociator
00041   class TrackPropagatorToCalo
00042   {
00043    public:
00044     TrackPropagatorToCalo();
00045     void update(const edm::EventSetup& eventSetup);
00046     math::XYZPoint impactPoint(const reco::Track& track) const;
00047    private:
00048     const MagneticField* magneticField_;
00049     const Propagator* propagator_;
00050     uint32_t magneticFieldCacheId_;
00051     uint32_t propagatorCacheId_;
00052   };
00053   
00054   // Helpper class to calculate strip signal to noise and manage the necessary ES objects
00055   class StripSignalOverNoiseCalculator
00056   {
00057    public:
00058     StripSignalOverNoiseCalculator(const std::string& theQualityLabel = std::string(""));
00059     void update(const edm::EventSetup& eventSetup);
00060     double signalOverNoise(const SiStripCluster& cluster,
00061                            const uint32_t& id) const;
00062     double operator () (const SiStripCluster& cluster,
00063                         const uint32_t& id) const
00064     { return signalOverNoise(cluster,id); }
00065    private:
00066     const std::string qualityLabel_;
00067     const SiStripQuality* quality_;
00068     const SiStripNoises* noise_;
00069     const SiStripGain* gain_;
00070     uint32_t qualityCacheId_;
00071     uint32_t noiseCacheId_;
00072     uint32_t gainCacheId_;
00073   };
00074   
00075 }
00076 
00077 const char* JPTJetAnalyzer::messageLoggerCatregory = "JetPlusTrackDQM";
00078 
00079 JPTJetAnalyzer::JPTJetAnalyzer(const edm::ParameterSet& config)
00080   : histogramPath_(config.getParameter<std::string>("HistogramPath")),
00081     verbose_(config.getUntrackedParameter<bool>("PrintDebugMessages",false)),
00082     writeDQMStore_(config.getUntrackedParameter<bool>("WriteDQMStore")),
00083     dqmStoreFileName_(),
00084     n90HitsMin_(config.getParameter<int>("n90HitsMin")),
00085     fHPDMax_(config.getParameter<double>("fHPDMax")),
00086     resEMFMin_(config.getParameter<double>("resEMFMin")),
00087     correctedPtMin_(config.getParameter<double>("correctedPtThreshold")),
00088     trackPropagator_(new jptJetAnalysis::TrackPropagatorToCalo),
00089     sOverNCalculator_(new jptJetAnalysis::StripSignalOverNoiseCalculator),
00090     jetID_(new reco::helper::JetIDHelper(config.getParameter<edm::ParameterSet>("JetIDParams")))
00091 {
00092   //print config to debug log
00093   std::ostringstream debugStream;
00094   if (verbose_) {
00095     debugStream << "Configuration for JPTJetAnalyzer: " << std::endl
00096                 << "\tHistogramPath: " << histogramPath_ << std::endl
00097                 << "\tPrintDebugMessages? " << (verbose_ ? "yes" : "no") << std::endl;
00098   }
00099   if (writeDQMStore_) {
00100     dqmStoreFileName_ = config.getUntrackedParameter<std::string>("DQMStoreFileName");
00101   }
00102   
00103   //don't generate debug mesages if debug is disabled
00104   std::ostringstream* pDebugStream = (verbose_ ? &debugStream : NULL);
00105   
00106   //get histogram configuration
00107   getConfigForHistogram("E",config,pDebugStream);
00108   getConfigForHistogram("Et",config,pDebugStream);
00109   getConfigForHistogram("P",config,pDebugStream);
00110   getConfigForHistogram("Mass",config,pDebugStream);
00111   getConfigForHistogram("Pt",config,pDebugStream);
00112   getConfigForHistogram("Pt1",config,pDebugStream);
00113   getConfigForHistogram("Pt2",config,pDebugStream);
00114   getConfigForHistogram("Pt3",config,pDebugStream);
00115   getConfigForHistogram("Px",config,pDebugStream);
00116   getConfigForHistogram("Py",config,pDebugStream);
00117   getConfigForHistogram("Pz",config,pDebugStream);
00118   getConfigForHistogram("Eta",config,pDebugStream);
00119   getConfigForHistogram("Phi",config,pDebugStream);
00120   getConfigForHistogram("deltaEta",config,pDebugStream);
00121   getConfigForHistogram("deltaPhi",config,pDebugStream);
00122   getConfigForHistogram("PhiVsEta",config,pDebugStream);
00123   getConfigForHistogram("N90Hits",config,pDebugStream);
00124   getConfigForHistogram("fHPD",config,pDebugStream);
00125   getConfigForHistogram("ResEMF",config,pDebugStream);
00126   getConfigForHistogram("fRBX",config,pDebugStream);
00127   getConfigForHistogram("TrackSiStripHitStoN",config,pDebugStream);
00128   getConfigForHistogram("InCaloTrackDirectionJetDR",config,pDebugStream);
00129   getConfigForHistogram("OutCaloTrackDirectionJetDR",config,pDebugStream);
00130   getConfigForHistogram("InVertexTrackImpactPointJetDR",config,pDebugStream);
00131   getConfigForHistogram("OutVertexTrackImpactPointJetDR",config,pDebugStream);
00132   getConfigForHistogram("PtFractionInCone",config,pDebugStream);
00133   getConfigForHistogram("PtFractionInConeVsJetRawEt",config,pDebugStream);
00134   getConfigForHistogram("PtFractionInConeVsJetEta",config,pDebugStream);
00135   getConfigForHistogram("nTracks",config,pDebugStream);
00136   getConfigForHistogram("nTracksVsJetEt",config,pDebugStream);
00137   getConfigForHistogram("nTracksVsJetEta",config,pDebugStream);
00138   getConfigForHistogram("CorrFactor",config,pDebugStream);
00139   getConfigForHistogram("CorrFactorVsJetEt",config,pDebugStream);
00140   getConfigForHistogram("CorrFactorVsJetEta",config,pDebugStream);
00141   getConfigForHistogram("ZSPCorrFactor",config,pDebugStream);
00142   getConfigForHistogram("ZSPCorrFactorVsJetEt",config,pDebugStream);
00143   getConfigForHistogram("ZSPCorrFactorVsJetEta",config,pDebugStream);
00144   getConfigForHistogram("JPTCorrFactor",config,pDebugStream);
00145   getConfigForHistogram("JPTCorrFactorVsJetEt",config,pDebugStream);
00146   getConfigForHistogram("JPTCorrFactorVsJetEta",config,pDebugStream);
00147   getConfigForTrackHistograms("AllPions",config,pDebugStream);
00148   getConfigForTrackHistograms("InCaloInVertexPions",config,pDebugStream);
00149   getConfigForTrackHistograms("InCaloOutVertexPions",config,pDebugStream);
00150   getConfigForTrackHistograms("OutCaloInVertexPions",config,pDebugStream);
00151   getConfigForTrackHistograms("AllMuons",config,pDebugStream);
00152   getConfigForTrackHistograms("InCaloInVertexMuons",config,pDebugStream);
00153   getConfigForTrackHistograms("InCaloOutVertexMuons",config,pDebugStream);
00154   getConfigForTrackHistograms("OutCaloInVertexMuons",config,pDebugStream); 
00155   getConfigForTrackHistograms("AllElectrons",config,pDebugStream);
00156   getConfigForTrackHistograms("InCaloInVertexElectrons",config,pDebugStream);
00157   getConfigForTrackHistograms("InCaloOutVertexElectrons",config,pDebugStream);
00158   getConfigForTrackHistograms("OutCaloInVertexElectrons",config,pDebugStream);
00159   
00160   if (verbose_) LogTrace(messageLoggerCatregory) << debugStream.str();
00161 }
00162 
00163 JPTJetAnalyzer::~JPTJetAnalyzer()
00164 {}
00165 
00166 void JPTJetAnalyzer::beginJob(DQMStore* dqmStore)
00167 {
00168   dqm_ = dqmStore;
00169   //book histograms
00170   dqmStore->setCurrentFolder(histogramPath_);
00171   bookHistograms(dqmStore);
00172 }
00173 
00174 
00175 void JPTJetAnalyzer::analyze(const edm::Event& event, const edm::EventSetup& eventSetup, const reco::JPTJetCollection& jptJets)
00176 {
00177   double pt1 = 0;
00178   double pt2 = 0;
00179   double pt3 = 0;
00180   for (reco::JPTJetCollection::const_iterator iJet = jptJets.begin(); iJet != jptJets.end(); ++iJet) {
00181     analyze(event,eventSetup,*iJet,pt1,pt2,pt3);
00182   }
00183   if (pt1) fillHistogram(JetPt1_,pt1);
00184   if (pt2) fillHistogram(JetPt2_,pt2);
00185   if (pt3) fillHistogram(JetPt3_,pt3);
00186 }
00187 
00188 void JPTJetAnalyzer::analyze(const edm::Event& event, const edm::EventSetup& eventSetup, const reco::JPTJet& jptJet, double& pt1, double& pt2, double& pt3)
00189 {
00190   
00191   //update the track propagator and strip noise calculator
00192   trackPropagator_->update(eventSetup);
00193   sOverNCalculator_->update(eventSetup);
00194   
00195   //make corrected jets
00196   const double factorZSP = jptJet.getZSPCor();
00197   const reco::Jet& rawJet = *jptJet.getCaloJetRef();
00198   const double factorZSPJPT = jptJet.energy()/rawJet.energy();
00199   
00200   //check jet is correctable by JPT
00201   if ( fabs(rawJet.eta()) > 2.1) return;
00202   
00203   //get consitiuents of jet
00204   const reco::TrackRefVector& pionsInVertexInCalo = jptJet.getPionsInVertexInCalo();
00205   const reco::TrackRefVector& pionsInVertexOutCalo = jptJet.getPionsInVertexOutCalo();
00206   const reco::TrackRefVector& pionsOutVertexInCalo = jptJet.getPionsOutVertexInCalo();
00207   const reco::TrackRefVector& muonsInVertexInCalo = jptJet.getMuonsInVertexInCalo();
00208   const reco::TrackRefVector& muonsInVertexOutCalo = jptJet.getMuonsInVertexOutCalo();
00209   const reco::TrackRefVector& muonsOutVertexInCalo = jptJet.getMuonsOutVertexInCalo();
00210   const reco::TrackRefVector& electronsInVertexInCalo = jptJet.getElecsInVertexInCalo();
00211   const reco::TrackRefVector& electronsInVertexOutCalo = jptJet.getElecsInVertexOutCalo();
00212   const reco::TrackRefVector& electronsOutVertexInCalo = jptJet.getElecsOutVertexInCalo();
00213   
00214   //check pt against highest values
00215   const double pt = jptJet.pt();
00216   if (pt > pt1) {
00217     pt3 = pt2;
00218     pt2 = pt1;
00219     pt1 = pt;
00220   } else if (pt > pt2) {
00221     pt3 = pt2;
00222     pt2 = pt;
00223   } else if (pt > pt3) {
00224     pt3 = pt;
00225   }
00226   
00227   //fill histograms
00228   try {
00229     const reco::CaloJet& rawCaloJet = dynamic_cast<const reco::CaloJet&>(rawJet);
00230     jetID_->calculate(event,rawCaloJet);
00231   } catch (const std::bad_cast&) {
00232     edm::LogError(messageLoggerCatregory) << "Failed to cast raw jet to CaloJet. JPT Jet does not appear to have been built from a CaloJet. "
00233                                           << "Histograms not filled. ";
00234     return;
00235   }
00236   const bool idPassed = ( (jetID_->n90Hits() >= n90HitsMin_) && (jetID_->fHPD() < fHPDMax_) && (jetID_->restrictedEMF() >= resEMFMin_) );
00237   fillHistogram(JetN90Hits_,jetID_->n90Hits());
00238   fillHistogram(JetfHPD_,jetID_->fHPD());
00239   fillHistogram(JetResEMF_,jetID_->restrictedEMF());
00240   fillHistogram(JetfRBX_,jetID_->fRBX());
00241   if (idPassed) {
00242     const double deltaEta = jptJet.eta() - rawJet.eta();
00243     const double deltaPhi = jptJet.phi() - rawJet.phi();
00244     if (jptJet.pt() > correctedPtMin_) {
00245       fillHistogram(JetE_,jptJet.energy());
00246       fillHistogram(JetEt_,jptJet.et());
00247       fillHistogram(JetP_,jptJet.p());
00248       fillHistogram(JetMass_,jptJet.mass());
00249       fillHistogram(JetPt_,jptJet.pt());
00250       fillHistogram(JetPx_,jptJet.px());
00251       fillHistogram(JetPy_,jptJet.py());
00252       fillHistogram(JetPz_,jptJet.pz());
00253 
00254       fillHistogram(JetEta_,jptJet.eta());
00255       fillHistogram(JetPhi_,jptJet.phi());
00256       fillHistogram(JetDeltaEta_,deltaEta);
00257       fillHistogram(JetDeltaPhi_,deltaPhi);
00258       fillHistogram(JetPhiVsEta_,jptJet.phi(),jptJet.eta());
00259       const uint16_t totalTracks = jptJet.chargedMultiplicity();
00260       fillHistogram(NTracksPerJetHisto_,totalTracks);
00261       fillHistogram(NTracksPerJetVsJetEtHisto_,rawJet.et(),totalTracks);
00262       fillHistogram(NTracksPerJetVsJetEtaHisto_,rawJet.eta(),totalTracks);
00263       fillHistogram(CorrFactorHisto_,factorZSPJPT);
00264       fillHistogram(CorrFactorVsJetEtHisto_,rawJet.et(),factorZSPJPT);
00265       fillHistogram(CorrFactorVsJetEtaHisto_,rawJet.eta(),factorZSPJPT);
00266       fillHistogram(ZSPCorrFactorHisto_,factorZSP);
00267       fillHistogram(ZSPCorrFactorVsJetEtHisto_,rawJet.et(),factorZSP);
00268       fillHistogram(ZSPCorrFactorVsJetEtaHisto_,rawJet.eta(),factorZSP);
00269       const double factorJPT = factorZSPJPT / factorZSP;
00270       fillHistogram(JPTCorrFactorHisto_,factorJPT);
00271       fillHistogram(JPTCorrFactorVsJetEtHisto_,rawJet.et(),factorJPT);
00272       fillHistogram(JPTCorrFactorVsJetEtaHisto_,rawJet.eta(),factorJPT);
00273       const double ptFractionInCone = findPtFractionInCone(pionsInVertexInCalo,pionsInVertexOutCalo);
00274       fillHistogram(PtFractionInConeHisto_,ptFractionInCone);
00275       fillHistogram(PtFractionInConeVsJetRawEtHisto_,rawJet.et(),ptFractionInCone);
00276       fillHistogram(PtFractionInConeVsJetEtaHisto_,rawJet.eta(),ptFractionInCone);
00277       //fill track level histograms
00278       fillTrackHistograms(allPionHistograms_,inCaloInVertexPionHistograms_,inCaloOutVertexPionHistograms_,outCaloInVertexPionHistograms_,
00279                           pionsInVertexInCalo,pionsOutVertexInCalo,pionsInVertexOutCalo,rawJet);
00280       fillTrackHistograms(allMuonHistograms_,inCaloInVertexMuonHistograms_,inCaloOutVertexMuonHistograms_,outCaloInVertexMuonHistograms_,
00281                           muonsInVertexInCalo,muonsOutVertexInCalo,muonsInVertexOutCalo,rawJet);
00282       fillTrackHistograms(allElectronHistograms_,inCaloInVertexElectronHistograms_,inCaloOutVertexElectronHistograms_,outCaloInVertexElectronHistograms_,
00283                           electronsInVertexInCalo,electronsOutVertexInCalo,electronsInVertexOutCalo,rawJet);
00284     }
00285   }
00286 }
00287 
00288 void JPTJetAnalyzer::endJob()
00289 {
00290   if(writeDQMStore_) dqm_->save(dqmStoreFileName_);
00291 }
00292 
00293 void JPTJetAnalyzer::getConfigForHistogram(const std::string& configName, const edm::ParameterSet& psetContainingConfigPSet,
00294                                            std::ostringstream* pDebugStream)
00295 {
00296   const std::string psetName = configName+std::string("HistogramConfig");
00297   if (!psetContainingConfigPSet.exists(psetName)) {
00298     edm::LogWarning(messageLoggerCatregory) << "Histogram " << configName << " config not found" << std::endl;
00299     histogramConfig_[configName] = HistogramConfig();
00300   } else {
00301     if (pDebugStream) {
00302       (*pDebugStream) << "Histogram " << configName << " config found and loaded" << std::endl;
00303     }
00304     const edm::ParameterSet& pset = psetContainingConfigPSet.getParameter<edm::ParameterSet>(psetName);
00305     const bool enabled = (pset.exists("Enabled") ? pset.getParameter<bool>("Enabled") : true);
00306     if (!enabled) {
00307       histogramConfig_[configName] = HistogramConfig();
00308       if (pDebugStream) {
00309         (*pDebugStream) << "\tHistogram: " << configName << " Disabled" << std::endl;
00310       }
00311     } else {
00312       const unsigned int nBins = (pset.exists("NBins") ? pset.getParameter<unsigned int>("NBins") : 0);
00313       const double min = (pset.exists("Min") ? pset.getParameter<double>("Min") : 0);
00314       const double max = (pset.exists("Max") ? pset.getParameter<double>("Max") : 0);
00315       const unsigned int nBinsY = (pset.exists("NBinsY") ? pset.getParameter<unsigned int>("NBinsY") : 0);
00316       const double minY = (pset.exists("MinY") ? pset.getParameter<double>("MinY") : 0);
00317       const double maxY = (pset.exists("MaxY") ? pset.getParameter<double>("MaxY") : 0);
00318       if (nBins) {
00319         if (pDebugStream) {
00320           (*pDebugStream) << "\tHistogram: " << configName << "\tEnabled"
00321                           << "\tNBins: " << nBins << "\tMin: " << min << "\tMax: " << max;
00322           if (nBinsY) (*pDebugStream) << "\tNBinsY: " << nBinsY << "\tMinY: " << minY << "\tMaxY: " << maxY;
00323           (*pDebugStream) << std::endl;
00324         }
00325         if (nBinsY) {
00326           histogramConfig_[configName] = HistogramConfig(nBins,min,max,nBinsY,minY,maxY);
00327         } else {
00328           histogramConfig_[configName] = HistogramConfig(nBins,min,max);
00329         }
00330       }
00331     }
00332   }
00333 }
00334 
00335 void JPTJetAnalyzer::getConfigForTrackHistograms(const std::string& tag, const edm::ParameterSet& psetContainingConfigPSet,
00336                                                   std::ostringstream* pDebugStream)
00337 {
00338   getConfigForHistogram("n"+tag+"TracksPerJet",psetContainingConfigPSet,pDebugStream);
00339   getConfigForHistogram(tag+"TrackPt",psetContainingConfigPSet,pDebugStream);
00340   getConfigForHistogram(tag+"TrackPhi",psetContainingConfigPSet,pDebugStream);
00341   getConfigForHistogram(tag+"TrackEta",psetContainingConfigPSet,pDebugStream);
00342   getConfigForHistogram(tag+"TrackNHits",psetContainingConfigPSet,pDebugStream);
00343   getConfigForHistogram(tag+"TrackNLayers",psetContainingConfigPSet,pDebugStream);
00344   getConfigForHistogram(tag+"TrackNLayers",psetContainingConfigPSet,pDebugStream);
00345   getConfigForHistogram(tag+"TrackPtVsEta",psetContainingConfigPSet,pDebugStream);
00346   getConfigForHistogram(tag+"TrackDz",psetContainingConfigPSet,pDebugStream);
00347   getConfigForHistogram(tag+"TrackDxy",psetContainingConfigPSet,pDebugStream);
00348 }
00349 
00350 MonitorElement* JPTJetAnalyzer::bookHistogram(const std::string& name, const std::string& title, const std::string& xAxisTitle, DQMStore* dqm)
00351 {
00352   std::map<std::string,HistogramConfig>::const_iterator configIterator = histogramConfig_.find(name);
00353   if (configIterator == histogramConfig_.end()) {
00354     edm::LogWarning(messageLoggerCatregory) << "Trying to book histogram with name " << name << " when no config was not retrieved from ParameterSet";
00355     return NULL;
00356   }
00357   const HistogramConfig& histoConfig = (*configIterator).second;
00358   if (histoConfig.enabled) {
00359     MonitorElement* histo = dqm->book1D(name,title,histoConfig.nBins,histoConfig.min,histoConfig.max);
00360     histo->setAxisTitle(xAxisTitle,1);
00361     return histo;
00362   } else {
00363     return NULL;
00364   }
00365 }
00366 
00367 MonitorElement* JPTJetAnalyzer::book2DHistogram(const std::string& name, const std::string& title,
00368                                                 const std::string& xAxisTitle, const std::string& yAxisTitle, DQMStore* dqm)
00369 {
00370   std::map<std::string,HistogramConfig>::const_iterator configIterator = histogramConfig_.find(name);
00371   if (configIterator == histogramConfig_.end()) {
00372     edm::LogWarning(messageLoggerCatregory) << "Trying to book histogram with name " << name << " when no config was not retrieved from ParameterSet";
00373     return NULL;
00374   }
00375   const HistogramConfig& histoConfig = (*configIterator).second;
00376   if (histoConfig.enabled) {
00377     MonitorElement* histo = dqm->book2D(name,title,histoConfig.nBins,histoConfig.min,histoConfig.max,histoConfig.nBinsY,histoConfig.minY,histoConfig.maxY);
00378     histo->setAxisTitle(xAxisTitle,1);
00379     histo->setAxisTitle(yAxisTitle,2);
00380     return histo;
00381   } else {
00382     return NULL;
00383   }
00384 }
00385 
00386 MonitorElement* JPTJetAnalyzer::bookProfile(const std::string& name, const std::string& title,
00387                                             const std::string& xAxisTitle, const std::string& yAxisTitle, DQMStore* dqm)
00388 {
00389   std::map<std::string,HistogramConfig>::const_iterator configIterator = histogramConfig_.find(name);
00390   if (configIterator == histogramConfig_.end()) {
00391     edm::LogWarning(messageLoggerCatregory) << "Trying to book histogram with name " << name << " when no config was not retrieved from ParameterSet";
00392     return NULL;
00393   }
00394   const HistogramConfig& histoConfig = (*configIterator).second;
00395   if (histoConfig.enabled) {
00396     TProfile* underlyingRootObject = new TProfile(name.c_str(),title.c_str(),histoConfig.nBins,histoConfig.min,histoConfig.max);
00397     MonitorElement* histo = dqm->bookProfile(name,underlyingRootObject);
00398     histo->setAxisTitle(xAxisTitle,1);
00399     histo->setAxisTitle(yAxisTitle,2);
00400     return histo;
00401   } else {
00402     return NULL;
00403   }
00404 }
00405 
00406 void JPTJetAnalyzer::bookHistograms(DQMStore* dqm)
00407 {
00408   JetE_        = bookHistogram("E","Corrected Jet Energy","E /GeV",dqm);
00409   JetEt_       = bookHistogram("Et","Corrected Jet E_{T}","E_{T} /GeV",dqm);
00410   JetP_        = bookHistogram("P","Corrected Jet Momentum","p /GeV/c",dqm);
00411   JetMass_     = bookHistogram("Mass","Jet mass","Mass /GeV/c^{2}",dqm);
00412   JetPt_       = bookHistogram("Pt","Jet p_{T}","p_{T} /GeV/c",dqm);
00413   JetPt1_      = bookHistogram("Pt1","1st Jet p_{T}","p_{T} /GeV/c",dqm);
00414   JetPt2_      = bookHistogram("Pt2","2nd Jet p_{T}","p_{T} /GeV/c",dqm);
00415   JetPt3_      = bookHistogram("Pt3","3rd Jet p_{T}","p_{T} /GeV/c",dqm);
00416   JetPx_       = bookHistogram("Px","Jet p_{X}","p_{X} /GeV/c",dqm);
00417   JetPy_       = bookHistogram("Py","Jet p_{Y}","p_{Y} /GeV/c",dqm);
00418   JetPz_       = bookHistogram("Pz","Jet p_{Z}","p_{Z} /GeV/c",dqm);
00419   JetEta_      = bookHistogram("Eta","Jet #eta","#eta",dqm);
00420   JetPhi_      = bookHistogram("Phi","Jet #phi","#phi",dqm);
00421   JetDeltaEta_ = bookHistogram("deltaEta","Change in #eta","#Delta #eta",dqm);
00422   JetDeltaPhi_ = bookHistogram("deltaPhi","Change in #phi","#Delta #phi",dqm);
00423   JetPhiVsEta_ = book2DHistogram("PhiVsEta","Corrected jet #phi vs #eta","jet #phi","jet #eta",dqm);
00424   JetN90Hits_  = bookHistogram("N90Hits","Jet N90Hits","N90 Hits",dqm);
00425   JetfHPD_     = bookHistogram("fHPD","Jet fHPD","fHPD",dqm);
00426   JetResEMF_   = bookHistogram("ResEMF","Jet restricted EM fraction","restricted EMF",dqm);
00427   JetfRBX_     = bookHistogram("fRBX","Jet fRBX","fRBX",dqm);
00428   
00429   TrackSiStripHitStoNHisto_            = bookHistogram("TrackSiStripHitStoN","Signal to noise of track SiStrip hits","S/N",dqm);
00430   InCaloTrackDirectionJetDRHisto_      = bookHistogram("InCaloTrackDirectionJetDR",
00431                                                        "#Delta R between track direrction at vertex and jet axis (track in cone at calo)","#Delta R",dqm);
00432   OutCaloTrackDirectionJetDRHisto_     = bookHistogram("OutCaloTrackDirectionJetDR",
00433                                                        "#Delta R between track direrction at vertex and jet axis (track out of cone at calo)","#Delta R",dqm);
00434   InVertexTrackImpactPointJetDRHisto_  = bookHistogram("InVertexTrackImpactPointJetDR",
00435                                                        "#Delta R between track impact point on calo and jet axis (track in cone at vertex)","#Delta R",dqm);
00436   OutVertexTrackImpactPointJetDRHisto_ = bookHistogram("OutVertexTrackImpactPointJetDR",
00437                                                        "#Delta R between track impact point on calo and jet axis (track out of cone at vertex)","#Delta R",dqm);
00438   
00439   NTracksPerJetHisto_         = bookHistogram("nTracks","Number of tracks for correction per jet","n tracks",dqm);
00440   NTracksPerJetVsJetEtHisto_  = bookProfile("nTracksVsJetEt","Number of tracks for correction per jet vs jet raw E_{T}","Jet raw E_{T} /GeV","n Tracks",dqm);
00441   NTracksPerJetVsJetEtaHisto_ = bookProfile("nTracksVsJetEta","Number of tracks for correction per jet vs jet #eta","Jet #eta","n Tracks",dqm);
00442   
00443   PtFractionInConeHisto_           = bookHistogram("PtFractionInCone","#frac{p_{T}^{in-cone}}{p_{T}^{in-cone}+p_{T}^{out-of-cone}}",
00444                                                  "#frac{p_{T}^{in-cone}}{p_{T}^{in-cone}+p_{T}^{out-of-cone}}",dqm);
00445   PtFractionInConeVsJetRawEtHisto_ = bookProfile("PtFractionInConeVsJetRawEt","#frac{p_{T}^{in-cone}}{p_{T}^{in-cone}+p_{T}^{out-of-cone}} vs jet raw E_{T}",
00446                                                  "Jet raw E_{T} / GeV","#frac{p_{T}^{in-cone}}{p_{T}^{in-cone}+p_{T}^{out-of-cone}}",dqm);
00447   PtFractionInConeVsJetEtaHisto_   = bookProfile("PtFractionInConeVsJetEta","#frac{p_{T}^{in-cone}}{p_{T}^{in-cone}+p_{T}^{out-of-cone}} vs jet #eta",
00448                                                  "Jet #eta","#frac{p_{T}^{in-cone}}{p_{T}^{in-cone}+p_{T}^{out-of-cone}}",dqm);
00449   
00450   CorrFactorHisto_            = bookHistogram("CorrFactor","Correction factor","Correction factor",dqm);
00451   CorrFactorVsJetEtHisto_     = bookProfile("CorrFactorVsJetEt","Correction factor vs jet raw E_{T}","Jet raw E_{T}","#frac{E_{T}^{corr}}{E_{T}^{raw}}",dqm);
00452   CorrFactorVsJetEtaHisto_    = bookProfile("CorrFactorVsJetEta","Correction factor vs jet #eta","Jet #eta","#frac{E_{T}^{corr}}{E_{T}^{raw}}",dqm);
00453   ZSPCorrFactorHisto_         = bookHistogram("ZSPCorrFactor","Correction factor from ZSP step","Correction factor",dqm);
00454   ZSPCorrFactorVsJetEtHisto_  = bookProfile("ZSPCorrFactorVsJetEt","Correction factor from ZSP step vs jet raw E_{T}",
00455                                             "Jet raw E_{T}","#frac{E_{T}^{corr}}{E_{T}^{raw}}",dqm);
00456   ZSPCorrFactorVsJetEtaHisto_ = bookProfile("ZSPCorrFactorVsJetEta","Correction factor from ZSP step vs jet #eta",
00457                                             "Jet #eta","#frac{E_{T}^{corr}}{E_{T}^{raw}}",dqm);
00458   JPTCorrFactorHisto_         = bookHistogram("JPTCorrFactor","Correction factor from JPT step","Correction factor",dqm);
00459   JPTCorrFactorVsJetEtHisto_  = bookProfile("JPTCorrFactorVsJetEt","Correction factor from JPT step vs jet raw E_{T}",
00460                                             "Jet raw E_{T}","#frac{E_{T}^{corr}}{E_{T}^{raw}}",dqm);
00461   JPTCorrFactorVsJetEtaHisto_ = bookProfile("JPTCorrFactorVsJetEta","Correction factor from JPT step vs jet #eta",
00462                                             "Jet #eta","#frac{E_{T}^{corr}}{E_{T}^{raw}}",dqm);
00463 
00464 
00465   
00466   bookTrackHistograms(&allPionHistograms_,"AllPions","pion",NULL,NULL,dqm);
00467   bookTrackHistograms(&inCaloInVertexPionHistograms_,"InCaloInVertexPions","pions in cone at calo and vertex",
00468                       InCaloTrackDirectionJetDRHisto_,InVertexTrackImpactPointJetDRHisto_,dqm);
00469   bookTrackHistograms(&inCaloOutVertexPionHistograms_,"InCaloOutVertexPions","pions in cone at calo but out at vertex",
00470                       InCaloTrackDirectionJetDRHisto_,OutVertexTrackImpactPointJetDRHisto_,dqm);
00471   bookTrackHistograms(&outCaloInVertexPionHistograms_,"OutCaloInVertexPions","pions out of cone at calo but in at vertex",
00472                       OutCaloTrackDirectionJetDRHisto_,InVertexTrackImpactPointJetDRHisto_,dqm);
00473   
00474   bookTrackHistograms(&allMuonHistograms_,"AllMuons","muon",NULL,NULL,dqm);
00475   bookTrackHistograms(&inCaloInVertexMuonHistograms_,"InCaloInVertexMuons","muons in cone at calo and vertex",
00476                       InCaloTrackDirectionJetDRHisto_,InVertexTrackImpactPointJetDRHisto_,dqm);
00477   bookTrackHistograms(&inCaloOutVertexMuonHistograms_,"InCaloOutVertexMuons","muons in cone at calo but out at vertex",
00478                       InCaloTrackDirectionJetDRHisto_,OutVertexTrackImpactPointJetDRHisto_,dqm);
00479   bookTrackHistograms(&outCaloInVertexMuonHistograms_,"OutCaloInVertexMuons","muons out of cone at calo but in at vertex",
00480                       OutCaloTrackDirectionJetDRHisto_,InVertexTrackImpactPointJetDRHisto_,dqm);
00481   
00482   bookTrackHistograms(&allElectronHistograms_,"AllElectrons","electron",NULL,NULL,dqm);
00483   bookTrackHistograms(&inCaloInVertexElectronHistograms_,"InCaloInVertexElectrons","electrons in cone at calo and vertex",
00484                       InCaloTrackDirectionJetDRHisto_,InVertexTrackImpactPointJetDRHisto_,dqm);
00485   bookTrackHistograms(&inCaloOutVertexElectronHistograms_,"InCaloOutVertexElectrons","electrons in cone at calo but out at vertex",
00486                       InCaloTrackDirectionJetDRHisto_,OutVertexTrackImpactPointJetDRHisto_,dqm);
00487   bookTrackHistograms(&outCaloInVertexElectronHistograms_,"OutCaloInVertexElectrons","electrons out of cone at calo but in at vertex",
00488                       OutCaloTrackDirectionJetDRHisto_,InVertexTrackImpactPointJetDRHisto_,dqm);
00489 }
00490 
00491 void JPTJetAnalyzer::bookTrackHistograms(TrackHistograms* histos, const std::string& tag, const std::string& titleTag,
00492                                          MonitorElement* trackDirectionJetDRHisto, MonitorElement* trackImpactPointJetDRHisto, DQMStore* dqm)
00493 {
00494   histos->nTracksHisto = bookHistogram("n"+tag+"TracksPerJet","Number of "+titleTag+" tracks per jet","n Tracks",dqm);
00495   histos->ptHisto = bookHistogram(tag+"TrackPt",titleTag+" p_{T}","p_{T} /GeV/c",dqm);
00496   histos->phiHisto = bookHistogram(tag+"TrackPhi",titleTag+" track #phi","#phi",dqm);
00497   histos->etaHisto = bookHistogram(tag+"TrackEta",titleTag+" track #eta","#eta",dqm);
00498   histos->nHitsHisto = bookHistogram(tag+"TrackNHits",titleTag+" track N hits","N hits",dqm);
00499   histos->nLayersHisto = bookHistogram(tag+"TrackNLayers",titleTag+" track N layers with hits","N layers",dqm);
00500   histos->ptVsEtaHisto = bookProfile(tag+"TrackPtVsEta",titleTag+" track p_{T} vs #eta","#eta","p_{T} /GeV/c",dqm);
00501   histos->dzHisto = bookHistogram(tag+"TrackDz",titleTag+" track dz","dz /cm",dqm);
00502   histos->dxyHisto = bookHistogram(tag+"TrackDxy",titleTag+" track dxy","dxy /cm",dqm);
00503   histos->trackDirectionJetDRHisto = trackDirectionJetDRHisto;
00504   histos->trackImpactPointJetDRHisto = trackImpactPointJetDRHisto;
00505 }
00506 
00507 void JPTJetAnalyzer::fillTrackHistograms(TrackHistograms& allTracksHistos, TrackHistograms& inCaloInVertexHistos,
00508                                          TrackHistograms& inCaloOutVertexHistos, TrackHistograms& outCaloInVertexHistos,
00509                                          const reco::TrackRefVector& inVertexInCalo,
00510                                          const reco::TrackRefVector& outVertexInCalo,
00511                                          const reco::TrackRefVector& inVertexOutCalo,
00512                                          const reco::Jet& rawJet)
00513 {
00514   fillTrackHistograms(allTracksHistos,inVertexInCalo,rawJet);
00515   fillTrackHistograms(allTracksHistos,outVertexInCalo,rawJet);
00516   fillTrackHistograms(allTracksHistos,inVertexOutCalo,rawJet);
00517   fillHistogram(allTracksHistos.nTracksHisto,inVertexInCalo.size()+outVertexInCalo.size()+inVertexOutCalo.size());
00518   fillSiStripSoNForTracks(inVertexInCalo);
00519   fillSiStripSoNForTracks(outVertexInCalo);
00520   fillSiStripSoNForTracks(inVertexOutCalo);
00521   fillTrackHistograms(inCaloInVertexHistos,inVertexInCalo,rawJet);
00522   fillHistogram(inCaloInVertexHistos.nTracksHisto,inVertexInCalo.size());
00523   fillTrackHistograms(inCaloOutVertexHistos,outVertexInCalo,rawJet);
00524   fillHistogram(inCaloOutVertexHistos.nTracksHisto,outVertexInCalo.size());
00525   fillTrackHistograms(outCaloInVertexHistos,inVertexOutCalo,rawJet);
00526   fillHistogram(outCaloInVertexHistos.nTracksHisto,inVertexOutCalo.size());
00527 }
00528 
00529 void JPTJetAnalyzer::fillTrackHistograms(TrackHistograms& histos, const reco::TrackRefVector& tracks, const reco::Jet& rawJet)
00530 {
00531   const reco::TrackRefVector::const_iterator tracksEnd = tracks.end();
00532   for (reco::TrackRefVector::const_iterator iTrack = tracks.begin(); iTrack != tracksEnd; ++iTrack) {
00533     const reco::Track& track = **iTrack;
00534     const double pt = track.pt();
00535     const double phi = track.phi();
00536     const double eta = track.eta();
00537     const unsigned int nHits = track.found();
00538     const unsigned int nLayers = track.hitPattern().trackerLayersWithMeasurement();
00539     const double dz = track.dz();
00540     const double dxy = track.dxy();
00541     fillHistogram(histos.ptHisto,pt);
00542     fillHistogram(histos.phiHisto,phi);
00543     fillHistogram(histos.etaHisto,eta);
00544     fillHistogram(histos.nHitsHisto,nHits);
00545     fillHistogram(histos.nLayersHisto,nLayers);
00546     fillHistogram(histos.ptVsEtaHisto,eta,pt);
00547     fillHistogram(histos.dzHisto,dz);
00548     fillHistogram(histos.dxyHisto,dxy);
00549     const double trackDirectionJetDR = deltaR(rawJet,track);
00550     fillHistogram(histos.trackDirectionJetDRHisto,trackDirectionJetDR);
00551     const double impactPointJetDR = deltaR(rawJet,trackPropagator_->impactPoint(track));
00552     fillHistogram(histos.trackImpactPointJetDRHisto,impactPointJetDR);
00553   }
00554 }
00555 
00556 void JPTJetAnalyzer::fillSiStripSoNForTracks(const reco::TrackRefVector& tracks)
00557 {
00558   const reco::TrackRefVector::const_iterator tracksEnd = tracks.end();
00559   for (reco::TrackRefVector::const_iterator iTrack = tracks.begin(); iTrack != tracksEnd; ++iTrack) {
00560     const trackingRecHit_iterator trackRecHitsEnd = (*iTrack)->recHitsEnd();
00561     for (trackingRecHit_iterator iHit = (*iTrack)->recHitsBegin(); iHit != trackRecHitsEnd; ++iHit) {
00562       fillSiStripHitSoN(**iHit);
00563     }
00564   }
00565 }
00566 
00567 void JPTJetAnalyzer::fillSiStripHitSoN(const TrackingRecHit& hit)
00568 {
00569   //check it is an SiStrip hit
00570   DetId detId(hit.geographicalId());
00571   if (!( (detId.det() == DetId::Tracker) &&
00572         ( (detId.subdetId() == SiStripDetId::TIB) ||
00573           (detId.subdetId() == SiStripDetId::TID) ||
00574           (detId.subdetId() == SiStripDetId::TOB) ||
00575           (detId.subdetId() == SiStripDetId::TEC)
00576         )
00577      )) return;
00578   //try to determine the type of the hit
00579   const TrackingRecHit* pHit = &hit;
00580   const SiStripRecHit2D* pRecHit2D = dynamic_cast<const SiStripRecHit2D*>(pHit);
00581   const SiStripMatchedRecHit2D* pMatchedRecHit2D = dynamic_cast<const SiStripMatchedRecHit2D*>(pHit);
00582   const ProjectedSiStripRecHit2D* pProjctedRecHit2D = dynamic_cast<const ProjectedSiStripRecHit2D*>(pHit);
00583   const InvalidTrackingRecHit* pInvalidHit = dynamic_cast<const InvalidTrackingRecHit*>(pHit);
00584   //fill signal to noise for appropriate hit
00585   if (pMatchedRecHit2D) {
00586     fillSiStripHitSoNForSingleHit(*pMatchedRecHit2D->monoHit());
00587     fillSiStripHitSoNForSingleHit(*pMatchedRecHit2D->stereoHit());
00588   } else if (pProjctedRecHit2D) {
00589     fillSiStripHitSoNForSingleHit(pProjctedRecHit2D->originalHit());
00590   } else if (pRecHit2D) {
00591     fillSiStripHitSoNForSingleHit(*pRecHit2D);
00592   } else if (pInvalidHit) {
00593     return;
00594   } else {
00595     edm::LogInfo(messageLoggerCatregory) << "Hit on det ID " << hit.geographicalId().rawId() << " cannot be converted to a strip hit";
00596   }
00597 }
00598 
00599 void JPTJetAnalyzer::fillSiStripHitSoNForSingleHit(const SiStripRecHit2D& hit)
00600 {
00601   //get the cluster
00602   const SiStripCluster* cluster = NULL;
00603   const SiStripRecHit2D::ClusterRegionalRef& regionalClusterRef = hit.cluster_regional();
00604   const SiStripRecHit2D::ClusterRef& normalClusterRef = hit.cluster();
00605   if (regionalClusterRef.isNonnull()) {
00606     cluster = &*regionalClusterRef;
00607   } else if (normalClusterRef.isNonnull()) {
00608     cluster = &*normalClusterRef;
00609   } else {
00610     edm::LogError(messageLoggerCatregory) << "Unable to get cluster from SiStripRecHit2D with det ID " << hit.geographicalId().rawId();
00611     return;
00612   }
00613   //calculate signal to noise for cluster
00614   const double sOverN = (*sOverNCalculator_)(*cluster,hit.geographicalId());
00615   //fill histogram
00616   fillHistogram(TrackSiStripHitStoNHisto_,sOverN);
00617 }
00618 
00619 double JPTJetAnalyzer::findPtFractionInCone(const reco::TrackRefVector& inConeTracks, const reco::TrackRefVector& outOfConeTracks)
00620 {
00621   double totalPt = 0;
00622   double inConePt = 0;
00623   const reco::TrackRefVector::const_iterator inConeTracksEnd = inConeTracks.end();
00624   for (reco::TrackRefVector::const_iterator iInConeTrack = inConeTracks.begin(); iInConeTrack != inConeTracksEnd; ++iInConeTrack) {
00625     const double pt = (*iInConeTrack)->pt();
00626     totalPt += pt;
00627     inConePt += pt;
00628   }
00629   const reco::TrackRefVector::const_iterator outOfConeTracksEnd = outOfConeTracks.end();
00630   for (reco::TrackRefVector::const_iterator iOutOfConeTrack = outOfConeTracks.begin(); iOutOfConeTrack != outOfConeTracksEnd; ++iOutOfConeTrack) {
00631     const double pt = (*iOutOfConeTrack)->pt();
00632     totalPt += pt;
00633   }
00634   if (totalPt) return inConePt/totalPt;
00635   //return 0 if there are no tracks at all
00636   else return 0;
00637 }
00638 
00639 
00640 
00641 JPTJetAnalyzer::HistogramConfig::HistogramConfig()
00642   : enabled(false),
00643     nBins(0),
00644     min(0),
00645     max(0),
00646     nBinsY(0),
00647     minY(0),
00648     maxY(0)
00649 {}
00650 
00651 JPTJetAnalyzer::HistogramConfig::HistogramConfig(const unsigned int theNBins, const double theMin, const double theMax)
00652   : enabled(true),
00653     nBins(theNBins),
00654     min(theMin),
00655     max(theMax),
00656     nBinsY(0),
00657     minY(0),
00658     maxY(0)
00659 {}
00660 
00661 JPTJetAnalyzer::HistogramConfig::HistogramConfig(const unsigned int theNBinsX, const double theMinX, const double theMaxX,
00662                                                  const unsigned int theNBinsY, const double theMinY, const double theMaxY)
00663   : enabled(true),
00664     nBins(theNBinsX),
00665     min(theMinX),
00666     max(theMaxX),
00667     nBinsY(theNBinsY),
00668     minY(theMinY),
00669     maxY(theMaxY)
00670 {}
00671 
00672 JPTJetAnalyzer::TrackHistograms::TrackHistograms()
00673   : ptHisto(NULL),
00674     phiHisto(NULL),
00675     etaHisto(NULL),
00676     nHitsHisto(NULL),
00677     nLayersHisto(NULL),
00678     ptVsEtaHisto(NULL),
00679     dzHisto(NULL),
00680     dxyHisto(NULL),
00681     trackDirectionJetDRHisto(NULL),
00682     trackImpactPointJetDRHisto(NULL)
00683 {}
00684 
00685 JPTJetAnalyzer::TrackHistograms::TrackHistograms(MonitorElement* theNTracksHisto,
00686                                                  MonitorElement* thePtHisto, MonitorElement* thePhiHisto, MonitorElement* theEtaHisto,
00687                                                  MonitorElement* theNHitsHisto, MonitorElement* theNLayersHisto, MonitorElement* thePtVsEtaHisto,
00688                                                  MonitorElement* theDzHisto, MonitorElement* theDxyHisto,
00689                                                  MonitorElement* theTrackDirectionJetDRHisto, MonitorElement* theTrackImpactPointJetDRHisto)
00690   : nTracksHisto(theNTracksHisto),
00691     ptHisto(thePtHisto),
00692     phiHisto(thePhiHisto),
00693     etaHisto(theEtaHisto),
00694     nHitsHisto(theNHitsHisto),
00695     nLayersHisto(theNLayersHisto),
00696     ptVsEtaHisto(thePtVsEtaHisto),
00697     dzHisto(theDzHisto),
00698     dxyHisto(theDxyHisto),
00699     trackDirectionJetDRHisto(theTrackDirectionJetDRHisto),
00700     trackImpactPointJetDRHisto(theTrackImpactPointJetDRHisto)
00701 {}
00702 
00703 namespace jptJetAnalysis {
00704   
00705   TrackPropagatorToCalo::TrackPropagatorToCalo()
00706     : magneticField_(NULL),
00707       propagator_(NULL),
00708       magneticFieldCacheId_(0),
00709       propagatorCacheId_(0)
00710     {}
00711   
00712   void TrackPropagatorToCalo::update(const edm::EventSetup& eventSetup)
00713   {
00714     //update magnetic filed if necessary
00715     const IdealMagneticFieldRecord& magneticFieldRecord = eventSetup.get<IdealMagneticFieldRecord>();
00716     const uint32_t newMagneticFieldCacheId = magneticFieldRecord.cacheIdentifier();
00717     if ((newMagneticFieldCacheId != magneticFieldCacheId_) || !magneticField_) {
00718       edm::ESHandle<MagneticField> magneticFieldHandle;
00719       magneticFieldRecord.get(magneticFieldHandle);
00720       magneticField_ = magneticFieldHandle.product();
00721       magneticFieldCacheId_ = newMagneticFieldCacheId;
00722     }
00723     //update propagator if necessary
00724     const TrackingComponentsRecord& trackingComponentsRecord = eventSetup.get<TrackingComponentsRecord>();
00725     const uint32_t newPropagatorCacheId = trackingComponentsRecord.cacheIdentifier();
00726     if ((propagatorCacheId_ != newPropagatorCacheId) || !propagator_) {
00727       edm::ESHandle<Propagator> propagatorHandle;
00728       trackingComponentsRecord.get("SteppingHelixPropagatorAlong",propagatorHandle);
00729       propagator_ = propagatorHandle.product();
00730       propagatorCacheId_ = newPropagatorCacheId;
00731     }
00732   }
00733   
00734   inline math::XYZPoint TrackPropagatorToCalo::impactPoint(const reco::Track& track) const
00735   {
00736     return JetTracksAssociationDRCalo::propagateTrackToCalorimeter(track,*magneticField_,*propagator_);
00737   }
00738   
00739   StripSignalOverNoiseCalculator::StripSignalOverNoiseCalculator(const std::string& theQualityLabel)
00740     : qualityLabel_(theQualityLabel),
00741       quality_(NULL),
00742       noise_(NULL),
00743       gain_(NULL),
00744       qualityCacheId_(0),
00745       noiseCacheId_(0),
00746       gainCacheId_(0)
00747     {}
00748   
00749   void StripSignalOverNoiseCalculator::update(const edm::EventSetup& eventSetup)
00750   {
00751     //update the quality if necessary
00752     const SiStripQualityRcd& qualityRecord = eventSetup.get<SiStripQualityRcd>();
00753     const uint32_t newQualityCacheId = qualityRecord.cacheIdentifier();
00754     if ((newQualityCacheId != qualityCacheId_) || !quality_) {
00755       edm::ESHandle<SiStripQuality> qualityHandle;
00756       qualityRecord.get(qualityLabel_,qualityHandle);
00757       quality_ = qualityHandle.product();
00758       qualityCacheId_ = newQualityCacheId;
00759     }
00760     //update the noise if necessary
00761     const SiStripNoisesRcd& noiseRecord = eventSetup.get<SiStripNoisesRcd>();
00762     const uint32_t newNoiseCacheId = noiseRecord.cacheIdentifier();
00763     if ((newNoiseCacheId != noiseCacheId_) || !noise_) {
00764       edm::ESHandle<SiStripNoises> noiseHandle;
00765       noiseRecord.get(noiseHandle);
00766       noise_ = noiseHandle.product();
00767       noiseCacheId_ = newNoiseCacheId;
00768     }
00769     //update the gain if necessary
00770     const SiStripGainRcd& gainRecord = eventSetup.get<SiStripGainRcd>();
00771     const uint32_t newGainCacheId = gainRecord.cacheIdentifier();
00772     if ((newGainCacheId != gainCacheId_) || !gain_) {
00773       edm::ESHandle<SiStripGain> gainHandle;
00774       gainRecord.get(gainHandle);
00775       gain_ = gainHandle.product();
00776       gainCacheId_ = newGainCacheId;
00777     }
00778   }
00779   
00780   double StripSignalOverNoiseCalculator::signalOverNoise(const SiStripCluster& cluster,
00781                                                          const uint32_t& detId) const
00782   {
00783     //const uint32_t detId = cluster.geographicalId();
00784     
00785     const uint16_t firstStrip = cluster.firstStrip();
00786     const SiStripQuality::Range& qualityRange = quality_->getRange(detId);
00787     const SiStripNoises::Range& noiseRange = noise_->getRange(detId);
00788     const SiStripApvGain::Range& gainRange = gain_->getRange(detId);
00789     double signal = 0;
00790     double noise2 = 0;
00791     unsigned int nNonZeroStrips = 0;
00792     const std::vector<uint8_t>& clusterAmplitudes = cluster.amplitudes();
00793     const std::vector<uint8_t>::const_iterator clusterAmplitudesEnd = clusterAmplitudes.end();
00794     const std::vector<uint8_t>::const_iterator clusterAmplitudesBegin = clusterAmplitudes.begin();
00795     for (std::vector<uint8_t>::const_iterator iAmp = clusterAmplitudesBegin; iAmp != clusterAmplitudesEnd; ++iAmp) {
00796       const uint8_t adc = *iAmp;
00797       const uint16_t strip = iAmp-clusterAmplitudesBegin+firstStrip;
00798       const bool stripBad = quality_->IsStripBad(qualityRange,strip);
00799       const double noise = noise_->getNoise(strip,noiseRange);
00800       const double gain = gain_->getStripGain(strip,gainRange);
00801       signal += adc;
00802       if (adc) ++nNonZeroStrips;
00803       const double noiseContrib = (stripBad ? 0 : noise/gain);
00804       noise2 += noiseContrib*noiseContrib;
00805     }
00806     const double noise = sqrt(noise2/nNonZeroStrips);
00807     if (noise) return signal/noise;
00808     else return 0;
00809   }
00810   
00811 }