00001
00002
00003
00004
00005
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include <memory>
00022 #include <iostream>
00023
00024
00025 #include "FWCore/Framework/interface/Frameworkfwd.h"
00026 #include "FWCore/Framework/interface/Event.h"
00027 #include "FWCore/Framework/interface/MakerMacros.h"
00028 #include "FWCore/Framework/interface/EventSetup.h"
00029 #include "FWCore/Framework/interface/ESHandle.h"
00030
00031 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00032
00033 #include "DataFormats/TrackReco/interface/Track.h"
00034 #include "DataFormats/BTauReco/interface/JetTag.h"
00035 #include "DataFormats/BTauReco/interface/TrackIPTagInfo.h"
00036 #include "DataFormats/JetReco/interface/JetTracksAssociation.h"
00037
00038 #include "TrackingTools/TransientTrack/interface/TransientTrackBuilder.h"
00039 #include "TrackingTools/IPTools/interface/IPTools.h"
00040 #include "TrackingTools/Records/interface/TransientTrackRecord.h"
00041
00042 #include "RecoBTag/TrackProbability/interface/HistogramProbabilityEstimator.h"
00043 #include "RecoBTag/ImpactParameter/plugins/TrackIPProducer.h"
00044 #include "TrackingTools/PatternTools/interface/TwoTrackMinimumDistance.h"
00045
00046
00047 using namespace std;
00048 using namespace reco;
00049 using namespace edm;
00050
00051
00052
00053
00054 TrackIPProducer::TrackIPProducer(const edm::ParameterSet& iConfig) :
00055 m_config(iConfig),m_probabilityEstimator(0) {
00056
00057 m_calibrationCacheId3D= 0;
00058 m_calibrationCacheId2D= 0;
00059
00060 m_associator = m_config.getParameter<InputTag>("jetTracks");
00061 m_primaryVertexProducer = m_config.getParameter<InputTag>("primaryVertex");
00062
00063 m_computeProbabilities = m_config.getParameter<bool>("computeProbabilities");
00064
00065 m_cutPixelHits = m_config.getParameter<int>("minimumNumberOfPixelHits");
00066 m_cutTotalHits = m_config.getParameter<int>("minimumNumberOfHits");
00067 m_cutMaxTIP = m_config.getParameter<double>("maximumTransverseImpactParameter");
00068 m_cutMinPt = m_config.getParameter<double>("minimumTransverseMomentum");
00069 m_cutMaxChiSquared = m_config.getParameter<double>("maximumChiSquared");
00070 m_cutMaxLIP = m_config.getParameter<double>("maximumLongitudinalImpactParameter");
00071 m_directionWithTracks = m_config.getParameter<bool>("jetDirectionUsingTracks");
00072 m_useTrackQuality = m_config.getParameter<bool>("useTrackQuality");
00073
00074
00075 produces<reco::TrackIPTagInfoCollection>();
00076
00077 }
00078
00079 TrackIPProducer::~TrackIPProducer()
00080 {
00081 delete m_probabilityEstimator;
00082 }
00083
00084
00085
00086
00087
00088 void
00089 TrackIPProducer::produce(edm::Event& iEvent, const edm::EventSetup& iSetup)
00090 {
00091 using namespace edm;
00092
00093 if(m_computeProbabilities ) checkEventSetup(iSetup);
00094
00095
00096 Handle<reco::JetTracksAssociationCollection> jetTracksAssociation;
00097 iEvent.getByLabel(m_associator,jetTracksAssociation);
00098
00099 Handle<reco::VertexCollection> primaryVertex;
00100 iEvent.getByLabel(m_primaryVertexProducer,primaryVertex);
00101
00102 edm::ESHandle<TransientTrackBuilder> builder;
00103 iSetup.get<TransientTrackRecord>().get("TransientTrackBuilder",builder);
00104
00105
00106
00107
00108 reco::TrackIPTagInfoCollection * outCollection = new reco::TrackIPTagInfoCollection();
00109
00110
00111
00112 const Vertex *pv;
00113 edm::Ref<VertexCollection> * pvRef;
00114 bool pvFound = (primaryVertex->size() != 0);
00115 if(pvFound)
00116 {
00117 pv = &(*primaryVertex->begin());
00118 pvRef = new edm::Ref<VertexCollection>(primaryVertex,0);
00119 }
00120 else
00121 {
00122 Vertex::Error e;
00123 e(0,0)=0.0015*0.0015;
00124 e(1,1)=0.0015*0.0015;
00125 e(2,2)=15.*15.;
00126 Vertex::Point p(0,0,0);
00127 pv= new Vertex(p,e,1,1,1);
00128 pvRef = new edm::Ref<VertexCollection>();
00129 }
00130
00131 double pvZ=pv->z();
00132
00133
00134
00135
00136
00137 int i=0;
00138 JetTracksAssociationCollection::const_iterator it = jetTracksAssociation->begin();
00139 TwoTrackMinimumDistance minDist;
00140 for(; it != jetTracksAssociation->end(); it++, i++)
00141 {
00142 TrackRefVector tracks = it->second;
00143 math::XYZVector jetMomentum=it->first->momentum()/2.;
00144 if(m_directionWithTracks)
00145 {
00146 for (TrackRefVector::const_iterator itTrack = tracks.begin(); itTrack != tracks.end(); ++itTrack) {
00147 if((**itTrack).numberOfValidHits() >= m_cutTotalHits )
00148 jetMomentum+=(**itTrack).momentum();
00149 }
00150 }
00151 else
00152 {
00153 jetMomentum=it->first->momentum();
00154 }
00155 GlobalVector direction(jetMomentum.x(),jetMomentum.y(),jetMomentum.z());
00156 TrackRefVector selectedTracks;
00157 vector<Measurement1D> ip3Dv,ip2Dv,dLenv,jetDistv;
00158 vector<float> prob2D,prob3D;
00159 vector<TrackIPTagInfo::TrackIPData> ipData;
00160
00161 multimap<float,int> significanceMap;
00162 int ind =0;
00163 for (TrackRefVector::const_iterator itTrack = tracks.begin(); itTrack != tracks.end(); ++itTrack) {
00164 const Track & track = **itTrack;
00165 const TransientTrack & transientTrack = builder->build(&(**itTrack));
00166
00167
00168
00169
00170
00171
00172
00173 if( track.pt() > m_cutMinPt &&
00174
00175
00176 fabs(IPTools::signedTransverseImpactParameter(transientTrack, direction, *pv).second.value())
00177 < m_cutMaxTIP &&
00178
00179 track.hitPattern().numberOfValidHits() >= m_cutTotalHits &&
00180 fabs(track.dz()-pvZ) < m_cutMaxLIP &&
00181 track.normalizedChi2() < m_cutMaxChiSquared &&
00182 track.hitPattern().numberOfValidPixelHits() >= m_cutPixelHits
00183 )
00184 {
00185
00186
00187 ip3Dv.push_back(IPTools::signedImpactParameter3D(transientTrack,direction,*pv).second);
00188 ip2Dv.push_back(IPTools::signedTransverseImpactParameter(transientTrack,direction,*pv).second);
00189 dLenv.push_back(IPTools::signedDecayLength3D(transientTrack,direction,*pv).second);
00190 jetDistv.push_back(IPTools::jetTrackDistance(transientTrack,direction,*pv).second);
00191 TrackIPTagInfo::TrackIPData trackIp;
00192 trackIp.ip3d=IPTools::signedImpactParameter3D(transientTrack,direction,*pv).second;
00193 trackIp.ip2d=IPTools::signedTransverseImpactParameter(transientTrack,direction,*pv).second;
00194 TrajectoryStateOnSurface closest = IPTools::closestApproachToJet(transientTrack.impactPointState(), *pv, direction,transientTrack.field());
00195 if(closest.isValid()) trackIp.closestToJetAxis=closest.globalPosition();
00196
00197 trackIp.distanceToJetAxis=IPTools::jetTrackDistance(transientTrack,direction,*pv).second.value();
00198
00199 significanceMap.insert(pair<float,int>(trackIp.ip3d.significance(), ind++) );
00200
00201 ipData.push_back(trackIp);
00202 selectedTracks.push_back(*itTrack);
00203
00204 if(m_computeProbabilities) {
00205
00206 pair<bool,double> probability = m_probabilityEstimator->probability(m_useTrackQuality , 0,ipData.back().ip3d.significance(),track,*(it->first),*pv);
00207 if(probability.first) prob3D.push_back(probability.second); else prob3D.push_back(-1.);
00208
00209
00210 probability = m_probabilityEstimator->probability(m_useTrackQuality ,1,ipData.back().ip2d.significance(),track,*(it->first),*pv);
00211 if(probability.first) prob2D.push_back(probability.second); else prob2D.push_back(-1.);
00212
00213 }
00214
00215 }
00216
00217 }
00218
00219 if(ipData.size() > 1)
00220 {
00221 multimap<float,int>::iterator last=significanceMap.end();
00222 last--;
00223 int first=last->second;
00224 last--;
00225 int second=last->second;
00226
00227 for(int n=0;n< ipData.size();n++)
00228 {
00229 int use;
00230 if(n==first) use = second; else use = first;
00231 TrajectoryStateOnSurface trackState1 = builder->build(selectedTracks[n]).impactPointState();
00232 TrajectoryStateOnSurface trackState2 = builder->build(selectedTracks[use]).impactPointState();
00233 minDist.calculate(trackState1,trackState2);
00234 std::pair<GlobalPoint,GlobalPoint> points = minDist.points();
00235 float distance = ( points.first - points.second ).mag();
00236 ipData[n].closestToFirstTrack=points.first;
00237 ipData[n].distanceToFirstTrack=distance;
00238
00239 }
00240 }
00241 TrackIPTagInfo tagInfo(ipData,prob2D,prob3D,selectedTracks,
00242 edm::Ref<JetTracksAssociationCollection>(jetTracksAssociation,i),
00243 *pvRef);
00244 outCollection->push_back(tagInfo);
00245 }
00246
00247 std::auto_ptr<reco::TrackIPTagInfoCollection> result(outCollection);
00248 iEvent.put(result);
00249
00250 if(!pvFound) delete pv;
00251 delete pvRef;
00252 }
00253
00254
00255 #include "CondFormats/BTauObjects/interface/TrackProbabilityCalibration.h"
00256 #include "RecoBTag/XMLCalibration/interface/CalibrationInterface.h"
00257 #include "CondFormats/DataRecord/interface/BTagTrackProbability2DRcd.h"
00258 #include "CondFormats/DataRecord/interface/BTagTrackProbability3DRcd.h"
00259 #include "FWCore/Framework/interface/EventSetupRecord.h"
00260 #include "FWCore/Framework/interface/EventSetupRecordImplementation.h"
00261 #include "FWCore/Framework/interface/EventSetupRecordKey.h"
00262
00263
00264 void TrackIPProducer::checkEventSetup(const EventSetup & iSetup)
00265 {
00266 using namespace edm;
00267 using namespace edm::eventsetup;
00268 const EventSetupRecord & re2D= iSetup.get<BTagTrackProbability2DRcd>();
00269 const EventSetupRecord & re3D= iSetup.get<BTagTrackProbability3DRcd>();
00270 unsigned long long cacheId2D= re2D.cacheIdentifier();
00271 unsigned long long cacheId3D= re3D.cacheIdentifier();
00272
00273 if(cacheId2D!=m_calibrationCacheId2D || cacheId3D!=m_calibrationCacheId3D )
00274 {
00275
00276 ESHandle<TrackProbabilityCalibration> calib2DHandle;
00277 iSetup.get<BTagTrackProbability2DRcd>().get(calib2DHandle);
00278 ESHandle<TrackProbabilityCalibration> calib3DHandle;
00279 iSetup.get<BTagTrackProbability3DRcd>().get(calib3DHandle);
00280
00281 const TrackProbabilityCalibration * ca2D= calib2DHandle.product();
00282 const TrackProbabilityCalibration * ca3D= calib3DHandle.product();
00283
00284 if(m_probabilityEstimator) delete m_probabilityEstimator;
00285 m_probabilityEstimator=new HistogramProbabilityEstimator(ca3D,ca2D);
00286
00287 }
00288 m_calibrationCacheId3D=cacheId3D;
00289 m_calibrationCacheId2D=cacheId2D;
00290 }
00291
00292
00293