CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
MuonTrackLoader.cc
Go to the documentation of this file.
1 
11 
15 
25 
27 
31 
36 
39 
41 
42 
43 using namespace edm;
44 using namespace std;
45 using namespace reco;
46 
47 std::vector<const TrackingRecHit*> MuonTrackLoader::unpackHit(const TrackingRecHit &hit)
48 {
49  // get rec hit det id and rec hit type
50  DetId id = hit.geographicalId();
51  uint16_t detid = id.det();
52 
53  std::vector<const TrackingRecHit*> hits;
54 
55  if (detid == DetId::Tracker) {
56  hits.push_back(&hit);
57  } else if (detid == DetId::Muon) {
58  uint16_t subdet = id.subdetId();
59  if (subdet == (uint16_t) MuonSubdetId::DT) {
60  if (hit.dimension() == 1) { // DT rechit (granularity 2)
61  hits.push_back(&hit);
62  } else if (hit.dimension() > 1) { // 4D segment (granularity 0).
63  // Both 2 and 4 dim cases. MB4s have 2D, but formatted in 4D segment
64  // 4D --> 2D
65  std::vector<const TrackingRecHit*> seg2D = hit.recHits();
66  // load 1D hits (2D --> 1D)
67  for (std::vector<const TrackingRecHit*>::const_iterator it = seg2D.begin(); it != seg2D.end(); ++it) {
68  std::vector<const TrackingRecHit*> hits1D = (*it)->recHits();
69  copy(hits1D.begin(), hits1D.end(), back_inserter(hits));
70  }
71  }
72  } else if (subdet == (uint16_t) MuonSubdetId::CSC) {
73  if (hit.dimension() == 2) { // CSC rechit (granularity 2)
74  hits.push_back(&hit);
75  } else if (hit.dimension() == 4) { // 4D segment (granularity 0)
76  // load 2D hits (4D --> 1D)
77  hits = hit.recHits();
78  }
79  } else if (subdet == (uint16_t) MuonSubdetId::RPC) {
80  hits.push_back(&hit);
81  }
82  }
83  return hits;
84 }
85 
86 // constructor (obsolete, should use eventSetUp not service..)
88  theService(service){
89 
90 
91  // option to do or not the smoothing step.
92  // the trajectories which are passed to the track loader are supposed to be non-smoothed
93  theSmoothingStep = parameterSet.getParameter<bool>("DoSmoothing");
95  theSmootherName = parameterSet.getParameter<string>("Smoother");
96 
97  theTrackerRecHitBuilderName = parameterSet.getParameter<std::string>("TTRHBuilder");
98 
99  // update at vertex
100  theUpdatingAtVtx = parameterSet.getParameter<bool>("VertexConstraint");
101 
102  // beam spot input tag
103  theBeamSpotInputTag = parameterSet.getParameter<edm::InputTag>("beamSpot");
105 
106 
107  // Flag to put the trajectory into the event
108  theTrajectoryFlag = parameterSet.getUntrackedParameter<bool>("PutTrajectoryIntoEvent",true);
109 
110  theL2SeededTkLabel = parameterSet.getUntrackedParameter<string>("MuonSeededTracksInstance",string());
111 
112  ParameterSet updatorPar = parameterSet.getParameter<ParameterSet>("MuonUpdatorAtVertexParameters");
113  theUpdatorAtVtx = new MuonUpdatorAtVertex(updatorPar,service);
114 
115  thePutTkTrackFlag = parameterSet.getUntrackedParameter<bool>("PutTkTrackIntoEvent",false);
116  theSmoothTkTrackFlag = parameterSet.getUntrackedParameter<bool>("SmoothTkTrack",false);
117  theAllowNoVtxFlag = parameterSet.getUntrackedParameter<bool>("AllowNoVertex",false);
118 }
119 
121  if(theUpdatorAtVtx) delete theUpdatorAtVtx;
122 }
123 
125 MuonTrackLoader::loadTracks(const TrajectoryContainer& trajectories,
126  Event& event, const string& instance, bool reallyDoSmoothing) {
127  std::vector<bool> dummyVecBool;
128  return loadTracks(trajectories, event, dummyVecBool, instance, reallyDoSmoothing);
129 }
130 
132 MuonTrackLoader::loadTracks(const TrajectoryContainer& trajectories,
133  Event& event, std::vector<bool>& tkBoolVec,
134  const string& instance, bool reallyDoSmoothing) {
135 
136  const bool doSmoothing = theSmoothingStep && reallyDoSmoothing;
137 
138  const string metname = "Muon|RecoMuon|MuonTrackLoader";
139 
140  // the track collectios; they will be loaded in the event
141  auto_ptr<reco::TrackCollection> trackCollection(new reco::TrackCollection());
142  // ... and its reference into the event
143  reco::TrackRefProd trackCollectionRefProd = event.getRefBeforePut<reco::TrackCollection>(instance);
144 
145  // track collection for the tracks updated at vertex
146  auto_ptr<reco::TrackCollection> updatedAtVtxTrackCollection(new reco::TrackCollection());
147  // ... and its (eventually) reference into the event
148  reco::TrackRefProd trackUpdatedCollectionRefProd;
149  if(theUpdatingAtVtx) trackUpdatedCollectionRefProd = event.getRefBeforePut<reco::TrackCollection>(instance+"UpdatedAtVtx");
150 
151  // Association map between updated and non updated at vtx tracks
152  auto_ptr<reco:: TrackToTrackMap> trackToTrackmap(new reco::TrackToTrackMap(trackCollectionRefProd, trackUpdatedCollectionRefProd));
153 
154  // the track extra collection, it will be loaded in the event
155  auto_ptr<reco::TrackExtraCollection> trackExtraCollection(new reco::TrackExtraCollection() );
156  // ... and its reference into the event
157  reco::TrackExtraRefProd trackExtraCollectionRefProd = event.getRefBeforePut<reco::TrackExtraCollection>(instance);
158 
159  // the rechit collection, it will be loaded in the event
160  auto_ptr<TrackingRecHitCollection> recHitCollection(new TrackingRecHitCollection() );
161  // ... and its reference into the event
162  TrackingRecHitRefProd recHitCollectionRefProd = event.getRefBeforePut<TrackingRecHitCollection>(instance);
163 
164  // Collection of Trajectory
165  auto_ptr<vector<Trajectory> > trajectoryCollection(new vector<Trajectory>);
166 
167  // don't waste any time...
168  if ( trajectories.empty() ) {
169  event.put(recHitCollection,instance);
170  event.put(trackExtraCollection,instance);
171  if(theTrajectoryFlag) {
172  event.put(trajectoryCollection,instance);
173 
174  // Association map between track and trajectory
175  std::auto_ptr<TrajTrackAssociationCollection> trajTrackMap( new TrajTrackAssociationCollection() );
176  event.put( trajTrackMap, instance );
177  }
178  if(theUpdatingAtVtx){
179  event.put(trackToTrackmap);
180  event.put(updatedAtVtxTrackCollection,instance+"UpdatedAtVtx");
181  }
182  return event.put(trackCollection,instance);
183  }
184 
186  event.getByToken(theBeamSpotToken, beamSpot);
187 
188  LogTrace(metname) << "Create the collection of Tracks";
189 
190  reco::TrackRef::key_type trackIndex = 0;
191  reco::TrackRef::key_type trackUpdatedIndex = 0;
192 
193  reco::TrackExtraRef::key_type trackExtraIndex = 0;
194  TrackingRecHitRef::key_type recHitsIndex = 0;
195 
197  edm::Ref< std::vector<Trajectory> >::key_type iTjRef = 0;
198  std::map<unsigned int, unsigned int> tjTkMap;
199 
200  if(doSmoothing) {
202  theService->eventSetup().get<TrajectoryFitter::Record>().get(theSmootherName,aSmoother);
203  theSmoother.reset(aSmoother->clone());
204  edm::ESHandle<TransientTrackingRecHitBuilder> theTrackerRecHitBuilder;
205  theService->eventSetup().get<TransientRecHitRecord>().get(theTrackerRecHitBuilderName,theTrackerRecHitBuilder);
206  theTrackerRecHitBuilder.product();
207  hitCloner = static_cast<TkTransientTrackingRecHitBuilder const *>(theTrackerRecHitBuilder.product())->cloner();
208  theSmoother->setHitCloner(&hitCloner);
209  }
210 
211 
212  unsigned int tjCnt = 0;
213  for(TrajectoryContainer::const_iterator rawTrajectory = trajectories.begin();
214  rawTrajectory != trajectories.end(); ++rawTrajectory, ++tjCnt){
215 
216  Trajectory &trajectory = **rawTrajectory;
217 
218  if(doSmoothing){
219  vector<Trajectory> trajectoriesSM = theSmoother->trajectories(**rawTrajectory);
220 
221  if(!trajectoriesSM.empty()) {
222  const edm::RefToBase<TrajectorySeed> tmpSeedRef = (**rawTrajectory).seedRef();
223  trajectory = trajectoriesSM.front();
224  trajectory.setSeedRef(tmpSeedRef);
225  LogDebug(metname) << "theSeedRef.isNonnull " << trajectory.seedRef().isNonnull();
226  } else
227  LogInfo(metname)<<"The trajectory has not been smoothed!"<<endl;
228  }
229 
230  if(theTrajectoryFlag) {
231  trajectoryCollection->push_back(trajectory);
232  iTjRef++;
233  }
234 
235  // get the transient rechit from the trajectory
236  Trajectory::RecHitContainer transHits = trajectory.recHits();
237 
238  if ( trajectory.direction() == oppositeToMomentum)
239  reverse(transHits.begin(),transHits.end());
240 
241  // build the "bare" track from the trajectory.
242  // This track has the parameters defined at PCA (no update)
243  pair<bool,reco::Track> resultOfTrackExtrapAtPCA = buildTrackAtPCA(trajectory, *beamSpot);
244 
245  // Check if the extrapolation went well
246  if(!resultOfTrackExtrapAtPCA.first) {
247  delete *rawTrajectory;
248  continue;
249  }
250 
251  // take the "bare" track at PCA
252  reco::Track &track = resultOfTrackExtrapAtPCA.second;
253 
254  // build the "bare" track extra from the trajectory
255  reco::TrackExtra trackExtra = buildTrackExtra( trajectory );
256 
257  // get the TrackExtraRef (persitent reference of the track extra)
258  reco::TrackExtraRef trackExtraRef(trackExtraCollectionRefProd, trackExtraIndex++ );
259 
260  // set the persistent track-extra reference to the Track
261  track.setExtra(trackExtraRef);
262 
263  // build the updated-at-vertex track, starting from the previous track
264  pair<bool,reco::Track> updateResult(false,reco::Track());
265 
266  if(theUpdatingAtVtx){
267  // build the "bare" track UPDATED at vtx
268  updateResult = buildTrackUpdatedAtPCA(track, *beamSpot);
269 
270  if(!updateResult.first) ++trackIndex;
271  else{
272 
273  // set the persistent track-extra reference to the Track
274  updateResult.second.setExtra(trackExtraRef);
275 
276  // Fill the map
277  trackToTrackmap->insert(reco::TrackRef(trackCollectionRefProd,trackIndex++),
278  reco::TrackRef(trackUpdatedCollectionRefProd,trackUpdatedIndex++));
279  }
280  }
281 
282  // Fill the track extra with the rec hit (persistent-)reference
283  unsigned int nHitsAdded = 0;
284  for (Trajectory::RecHitContainer::const_iterator recHit = transHits.begin(); recHit != transHits.end(); ++recHit) {
285  TrackingRecHit *singleHit = (**recHit).hit()->clone();
286  std::vector<const TrackingRecHit*> hits = MuonTrackLoader::unpackHit(*singleHit);
287  for (std::vector<const TrackingRecHit*>::const_iterator it = hits.begin(); it != hits.end(); ++it) {
288  if unlikely(!track.appendHitPattern(**it)){
289  break;
290  }
291  }
292 
293  if(theUpdatingAtVtx && updateResult.first){
294  std::vector<const TrackingRecHit*> hits = MuonTrackLoader::unpackHit(*singleHit);
295  for (std::vector<const TrackingRecHit*>::const_iterator it = hits.begin(); it != hits.end(); ++it) {
296  if unlikely(!updateResult.second.appendHitPattern(**it)){
297  break;
298  }
299  }
300  }
301  recHitCollection->push_back( singleHit );
302  ++nHitsAdded;
303  }
304  // set the TrackingRecHitRef (persitent reference of the tracking rec hits)
305  trackExtra.setHits(recHitCollectionRefProd, recHitsIndex, nHitsAdded);
306  recHitsIndex +=nHitsAdded;
307 
308  // fill the TrackExtraCollection
309  trackExtraCollection->push_back(trackExtra);
310 
311  // fill the TrackCollection
312  trackCollection->push_back(track);
313  iTkRef++;
314  LogTrace(metname) << "Debug Track being loaded pt "<< track.pt();
315  // fill the TrackCollection updated at vtx
316  if(theUpdatingAtVtx && updateResult.first)
317  updatedAtVtxTrackCollection->push_back(updateResult.second);
318 
319  // We don't need the original trajectory anymore.
320  // It has been copied by value in the trajectoryCollection, if
321  // it is required to put it into the event.
322  delete *rawTrajectory;
323 
324  if(tkBoolVec.size()>tjCnt) tkBoolVec[tjCnt] = true;
325  if(theTrajectoryFlag) tjTkMap[iTjRef-1] = iTkRef-1;
326  }
327 
328 
329 
330  // Put the Collections in the event
331  LogTrace(metname) << "put the Collections in the event";
332  event.put(recHitCollection,instance);
333  event.put(trackExtraCollection,instance);
334 
335  OrphanHandle<reco::TrackCollection> returnTrackHandle;
336  OrphanHandle<reco::TrackCollection> nonUpdatedHandle;
337  if(theUpdatingAtVtx){
338  nonUpdatedHandle = event.put(trackCollection,instance);
339  event.put(trackToTrackmap);
340  returnTrackHandle = event.put(updatedAtVtxTrackCollection,instance+"UpdatedAtVtx");
341  }
342  else {
343  returnTrackHandle = event.put(trackCollection,instance);
344  nonUpdatedHandle = returnTrackHandle;
345  }
346 
347  if ( theTrajectoryFlag ) {
348  OrphanHandle<std::vector<Trajectory> > rTrajs = event.put(trajectoryCollection,instance);
349 
350  // Association map between track and trajectory
351  std::auto_ptr<TrajTrackAssociationCollection> trajTrackMap( new TrajTrackAssociationCollection(rTrajs, nonUpdatedHandle) );
352 
353  // Now Create traj<->tracks association map
354  for ( std::map<unsigned int, unsigned int>::iterator i = tjTkMap.begin();
355  i != tjTkMap.end(); i++ ) {
356  trajTrackMap->insert( edm::Ref<std::vector<Trajectory> >( rTrajs, (*i).first ),
357  edm::Ref<reco::TrackCollection>( nonUpdatedHandle, (*i).second ) );
358  }
359  event.put( trajTrackMap, instance );
360  }
361 
362  return returnTrackHandle;
363 }
364 
367  Event& event) {
368 
369  const string metname = "Muon|RecoMuon|MuonTrackLoader";
370 
371  // the muon collection, it will be loaded in the event
372  auto_ptr<reco::MuonTrackLinksCollection> trackLinksCollection(new reco::MuonTrackLinksCollection());
373 
374  // don't waste any time...
375  if ( muonCands.empty() ) {
376  auto_ptr<reco::TrackExtraCollection> trackExtraCollection(new reco::TrackExtraCollection() );
377  auto_ptr<TrackingRecHitCollection> recHitCollection(new TrackingRecHitCollection() );
378  auto_ptr<reco::TrackCollection> trackCollection( new reco::TrackCollection() );
379 
380  event.put(recHitCollection);
381  event.put(trackExtraCollection);
382  event.put(trackCollection);
383 
384  //need to also put the tracker tracks collection if requested
385  if(thePutTkTrackFlag){
386  //will take care of putting nothing in the event but the empty collection
387  TrajectoryContainer trackerTrajs;
388  loadTracks(trackerTrajs, event, theL2SeededTkLabel, theSmoothTkTrackFlag);
389  }
390 
391  return event.put(trackLinksCollection);
392  }
393 
394  // get combined Trajectories
395  TrajectoryContainer combinedTrajs;
396  TrajectoryContainer trackerTrajs;
397  for (CandidateContainer::const_iterator it = muonCands.begin(); it != muonCands.end(); ++it) {
398  LogDebug(metname) << "Loader glbSeedRef " << (*it)->trajectory()->seedRef().isNonnull();
399  if ((*it)->trackerTrajectory() ) LogDebug(metname) << " " << "tkSeedRef " << (*it)->trackerTrajectory()->seedRef().isNonnull();
400 
401  combinedTrajs.push_back((*it)->trajectory());
402  if ( thePutTkTrackFlag ) trackerTrajs.push_back((*it)->trackerTrajectory());
403 
404  else {
405  if ((*it)->trackerTrajectory()) delete ((*it)->trackerTrajectory());
406  }
407 
408  // // Create the links between sta and tracker tracks
409  // reco::MuonTrackLinks links;
410  // links.setStandAloneTrack((*it)->muonTrack());
411  // links.setTrackerTrack((*it)->trackerTrack());
412  // trackLinksCollection->push_back(links);
413  // delete *it;
414  }
415 
416  // create the TrackCollection of combined Trajectories
417  // FIXME: could this be done one track at a time in the previous loop?
418  LogTrace(metname) << "Build combinedTracks";
419  std::vector<bool> combTksVec(combinedTrajs.size(), false);
420  OrphanHandle<reco::TrackCollection> combinedTracks = loadTracks(combinedTrajs, event, combTksVec);
421 
423  std::vector<bool> trackerTksVec(trackerTrajs.size(), false);
424  if(thePutTkTrackFlag) {
425  LogTrace(metname) << "Build trackerTracks: "
426  << trackerTrajs.size();
427  trackerTracks = loadTracks(trackerTrajs, event, trackerTksVec, theL2SeededTkLabel, theSmoothTkTrackFlag);
428  } else {
429  for (TrajectoryContainer::iterator it = trackerTrajs.begin(); it != trackerTrajs.end(); ++it) {
430  if(*it) delete *it;
431  }
432  }
433 
434  LogTrace(metname) << "Set the final links in the MuonTrackLinks collection";
435 
436  unsigned int candposition(0), position(0), tkposition(0);
437  //reco::TrackCollection::const_iterator glIt = combinedTracks->begin(),
438  // glEnd = combinedTracks->end();
439 
440  for (CandidateContainer::const_iterator it = muonCands.begin(); it != muonCands.end(); ++it, ++candposition) {
441 
442  // The presence of the global track determines whether to fill the MuonTrackLinks or not
443  // N.B. We are assuming here that the global tracks in "combinedTracks"
444  // have the same order as the muon candidates in "muonCands"
445  // (except for possible missing tracks), which should always be the case...
446  //if( glIt == glEnd ) break;
447  if(combTksVec[candposition]) {
448  reco::TrackRef combinedTR(combinedTracks, position++);
449  //++glIt;
450 
451  // Create the links between sta and tracker tracks
453  links.setStandAloneTrack((*it)->muonTrack());
454  links.setTrackerTrack((*it)->trackerTrack());
455  links.setGlobalTrack(combinedTR);
456 
457  if(thePutTkTrackFlag && trackerTksVec[candposition]) {
458  reco::TrackRef trackerTR(trackerTracks, tkposition++);
459  links.setTrackerTrack(trackerTR);
460  }
461 
462  trackLinksCollection->push_back(links);
463  }
464 
465  else { // if no global track, still increment the tracker-track counter when appropriate
466  if(thePutTkTrackFlag && trackerTksVec[candposition]) tkposition++;
467  }
468 
469  delete *it;
470  }
471 
472  if( thePutTkTrackFlag && trackerTracks.isValid() && !(combinedTracks->size() > 0 && trackerTracks->size() > 0 ) )
473  LogWarning(metname)<<"The MuonTrackLinkCollection is incomplete";
474 
475  // put the MuonCollection in the event
476  LogTrace(metname) << "put the MuonCollection in the event" << "\n";
477 
478  return event.put(trackLinksCollection);
479 }
480 
482 MuonTrackLoader::loadTracks(const TrajectoryContainer& trajectories,
483  Event& event, const std::vector<std::pair<Trajectory*,reco::TrackRef> >& miniMap, Handle<reco::TrackCollection> const& trackHandle, const string& instance, bool reallyDoSmoothing) {
484 
485  const bool doSmoothing = theSmoothingStep && reallyDoSmoothing;
486 
487  const string metname = "Muon|RecoMuon|MuonTrackLoader|TevMuonTrackLoader";
488 
489  LogDebug(metname)<<"TeV LoadTracks instance: " << instance;
490 
491  // the track collectios; they will be loaded in the event
492  auto_ptr<reco::TrackCollection> trackCollection(new reco::TrackCollection());
493  // ... and its reference into the event
494  reco::TrackRefProd trackCollectionRefProd = event.getRefBeforePut<reco::TrackCollection>(instance);
495 
496  // Association map between GlobalMuons and TeVMuons
497  auto_ptr<reco:: TrackToTrackMap> trackToTrackmap(new reco::TrackToTrackMap(trackHandle,trackCollectionRefProd ));
498 
499  // the track extra collection, it will be loaded in the event
500  auto_ptr<reco::TrackExtraCollection> trackExtraCollection(new reco::TrackExtraCollection() );
501  // ... and its reference into the event
502  reco::TrackExtraRefProd trackExtraCollectionRefProd = event.getRefBeforePut<reco::TrackExtraCollection>(instance);
503 
504  // the rechit collection, it will be loaded in the event
505  auto_ptr<TrackingRecHitCollection> recHitCollection(new TrackingRecHitCollection() );
506  // ... and its reference into the event
507  TrackingRecHitRefProd recHitCollectionRefProd = event.getRefBeforePut<TrackingRecHitCollection>(instance);
508 
509  // Collection of Trajectory
510  auto_ptr<vector<Trajectory> > trajectoryCollection(new vector<Trajectory>);
511 
512  // don't waste any time...
513  if ( trajectories.empty() ) {
514  event.put(recHitCollection,instance);
515  event.put(trackExtraCollection,instance);
516  if(theTrajectoryFlag) {
517  event.put(trajectoryCollection,instance);
518 
519  // Association map between track and trajectory
520  std::auto_ptr<TrajTrackAssociationCollection> trajTrackMap( new TrajTrackAssociationCollection() );
521  event.put( trajTrackMap, instance );
522  }
523  event.put(trackToTrackmap, instance);
524  return event.put(trackCollection,instance);
525  }
526 
527  LogTrace(metname) << "Create the collection of Tracks";
528 
530  event.getByToken(theBeamSpotToken,beamSpot);
531 
532  reco::TrackRef::key_type trackIndex = 0;
533  // reco::TrackRef::key_type trackUpdatedIndex = 0;
534 
535  reco::TrackExtraRef::key_type trackExtraIndex = 0;
536  TrackingRecHitRef::key_type recHitsIndex = 0;
537 
539  edm::Ref< std::vector<Trajectory> >::key_type iTjRef = 0;
540  std::map<unsigned int, unsigned int> tjTkMap;
541 
542  if(doSmoothing) {
544  theService->eventSetup().get<TrajectoryFitter::Record>().get(theSmootherName,aSmoother);
545  theSmoother.reset(aSmoother->clone());
546  edm::ESHandle<TransientTrackingRecHitBuilder> theTrackerRecHitBuilder;
547  try {
548  std::string theTrackerRecHitBuilderName("WithAngleAndTemplate"); // to be moved to cfg in another PR
549  theService->eventSetup().get<TransientRecHitRecord>().get(theTrackerRecHitBuilderName,theTrackerRecHitBuilder);
550  theTrackerRecHitBuilder.product();
551  } catch(...) {
552  std::string theTrackerRecHitBuilderName("hltESPTTRHBWithTrackAngle"); // FIXME FIXME
553  theService->eventSetup().get<TransientRecHitRecord>().get(theTrackerRecHitBuilderName,theTrackerRecHitBuilder);
554  }
555  hitCloner = static_cast<TkTransientTrackingRecHitBuilder const *>(theTrackerRecHitBuilder.product())->cloner();
556  theSmoother->setHitCloner(&hitCloner);
557  }
558 
559  for(TrajectoryContainer::const_iterator rawTrajectory = trajectories.begin();
560  rawTrajectory != trajectories.end(); ++rawTrajectory){
561 
562  reco::TrackRef glbRef;
563  std::vector<std::pair<Trajectory*,reco::TrackRef> >::const_iterator mmit;
564  for(mmit = miniMap.begin();mmit!=miniMap.end();++mmit){
565  if(mmit->first == *rawTrajectory) glbRef = mmit->second;
566  }
567 
568  Trajectory &trajectory = **rawTrajectory;
569 
570  if(doSmoothing){
571  vector<Trajectory> trajectoriesSM = theSmoother->trajectories(**rawTrajectory);
572 
573  if(!trajectoriesSM.empty()) {
574  const edm::RefToBase<TrajectorySeed> tmpSeedRef = (**rawTrajectory).seedRef();
575  trajectory = trajectoriesSM.front();
576  trajectory.setSeedRef(tmpSeedRef);
577  } else
578  LogInfo(metname)<<"The trajectory has not been smoothed!"<<endl;
579  }
580 
581  if(theTrajectoryFlag) {
582  trajectoryCollection->push_back(trajectory);
583  iTjRef++;
584  }
585 
586  // get the transient rechit from the trajectory
587  Trajectory::RecHitContainer transHits = trajectory.recHits();
588 
589  if ( trajectory.direction() == oppositeToMomentum)
590  reverse(transHits.begin(),transHits.end());
591 
592  // build the "bare" track from the trajectory.
593  // This track has the parameters defined at PCA (no update)
594  pair<bool,reco::Track> resultOfTrackExtrapAtPCA = buildTrackAtPCA(trajectory, *beamSpot);
595 
596  // Check if the extrapolation went well
597  if(!resultOfTrackExtrapAtPCA.first) {
598  // ++trackIndex;//ADAM
599  delete *rawTrajectory;
600  continue;
601  }
602 
603  // take the "bare" track at PCA
604  reco::Track &track = resultOfTrackExtrapAtPCA.second;
605 
606  // build the "bare" track extra from the trajectory
607  reco::TrackExtra trackExtra = buildTrackExtra( trajectory );
608 
609  // get the TrackExtraRef (persitent reference of the track extra)
610  reco::TrackExtraRef trackExtraRef(trackExtraCollectionRefProd, trackExtraIndex++ );
611 
612  // set the persistent track-extra reference to the Track
613  track.setExtra(trackExtraRef);
614 
615  // Fill the map
616  trackToTrackmap->insert(glbRef,
617  reco::TrackRef(trackCollectionRefProd,trackIndex++));
618 
619  // build the updated-at-vertex track, starting from the previous track
620  pair<bool,reco::Track> updateResult(false,reco::Track());
621 
622  // Fill the track extra with the rec hit (persistent-)reference
623  unsigned int nHitsAdded = 0;
624  for (Trajectory::RecHitContainer::const_iterator recHit = transHits.begin();
625  recHit != transHits.end(); ++recHit) {
626  TrackingRecHit *singleHit = (**recHit).hit()->clone();
627 
628  std::vector<const TrackingRecHit*> hits = MuonTrackLoader::unpackHit(*singleHit);
629  for (std::vector<const TrackingRecHit*>::const_iterator it = hits.begin(); it != hits.end(); ++it) {
630  if unlikely(!track.appendHitPattern(**it)){
631  break;
632  }
633  }
634 
635  if(theUpdatingAtVtx && updateResult.first){
636  std::vector<const TrackingRecHit*> hits = MuonTrackLoader::unpackHit(*singleHit);
637  for (std::vector<const TrackingRecHit*>::const_iterator it = hits.begin(); it != hits.end(); ++it) {
638  if unlikely(!updateResult.second.appendHitPattern(**it)){
639  break;
640  }
641  }
642  }
643  recHitCollection->push_back( singleHit );
644  ++nHitsAdded;
645  }
646  // set the TrackingRecHitRef (persitent reference of the tracking rec hits)
647  trackExtra.setHits(recHitCollectionRefProd, recHitsIndex, nHitsAdded);
648  recHitsIndex += nHitsAdded;
649 
650  // fill the TrackExtraCollection
651  trackExtraCollection->push_back(trackExtra);
652 
653  // fill the TrackCollection
654  trackCollection->push_back(track);
655  iTkRef++;
656  LogTrace(metname) << "Debug Track being loaded pt "<< track.pt();
657 
658  // We don't need the original trajectory anymore.
659  // It has been copied by value in the trajectoryCollection, if
660  // it is required to put it into the event.
661  delete *rawTrajectory;
662 
663  if(theTrajectoryFlag) tjTkMap[iTjRef-1] = iTkRef-1;
664  }
665 
666 
667 
668  // Put the Collections in the event
669  LogTrace(metname) << "put the Collections in the event";
670  event.put(recHitCollection,instance);
671  event.put(trackExtraCollection,instance);
672 
673  OrphanHandle<reco::TrackCollection> returnTrackHandle;
674  OrphanHandle<reco::TrackCollection> nonUpdatedHandle;
675  if(theUpdatingAtVtx){
676  }
677  else {
678  event.put(trackToTrackmap,instance);
679  returnTrackHandle = event.put(trackCollection,instance);
680  nonUpdatedHandle = returnTrackHandle;
681  }
682 
683  if ( theTrajectoryFlag ) {
684  OrphanHandle<std::vector<Trajectory> > rTrajs = event.put(trajectoryCollection,instance);
685 
686  // Association map between track and trajectory
687  std::auto_ptr<TrajTrackAssociationCollection> trajTrackMap( new TrajTrackAssociationCollection(rTrajs, nonUpdatedHandle) );
688 
689  // Now Create traj<->tracks association map
690  for ( std::map<unsigned int, unsigned int>::iterator i = tjTkMap.begin();
691  i != tjTkMap.end(); i++ ) {
692  trajTrackMap->insert( edm::Ref<std::vector<Trajectory> >( rTrajs, (*i).first ),
693  edm::Ref<reco::TrackCollection>( nonUpdatedHandle, (*i).second ) );
694  }
695  event.put( trajTrackMap, instance );
696  }
697 
698  return returnTrackHandle;
699 }
700 
701 
702 pair<bool,reco::Track> MuonTrackLoader::buildTrackAtPCA(const Trajectory& trajectory, const reco::BeamSpot &beamSpot) const {
703 
704  const string metname = "Muon|RecoMuon|MuonTrackLoader";
705 
707 
708  // FIXME: check the prop direction
709  TrajectoryStateOnSurface innerTSOS = trajectory.geometricalInnermostState();
710 
711  // This is needed to extrapolate the tsos at vertex
712  LogTrace(metname) << "Propagate to PCA...";
713  pair<bool,FreeTrajectoryState>
714  extrapolationResult = theUpdatorAtVtx->propagate(innerTSOS, beamSpot);
715  FreeTrajectoryState ftsAtVtx;
716 
717  if(extrapolationResult.first)
718  ftsAtVtx = extrapolationResult.second;
719  else{
720  if(TrackerBounds::isInside(innerTSOS.globalPosition())){
721  LogInfo(metname) << "Track in the Tracker: taking the innermost state instead of the state at PCA";
722  ftsAtVtx = *innerTSOS.freeState();
723  }
724  else{
725  if ( theAllowNoVtxFlag ) {
726  LogInfo(metname) << "Propagation to PCA failed, taking the innermost state instead of the state at PCA";
727  ftsAtVtx = *innerTSOS.freeState();
728  } else {
729  LogInfo(metname) << "Stand Alone track: this track will be rejected";
730  return pair<bool,reco::Track>(false,reco::Track());
731  }
732  }
733  }
734 
735  LogTrace(metname) << "TSOS after the extrapolation at vtx";
736  LogTrace(metname) << debug.dumpFTS(ftsAtVtx);
737 
738  GlobalPoint pca = ftsAtVtx.position();
739  math::XYZPoint persistentPCA(pca.x(),pca.y(),pca.z());
740  GlobalVector p = ftsAtVtx.momentum();
741  math::XYZVector persistentMomentum(p.x(),p.y(),p.z());
742 
743  bool bon = true;
744  if(fabs(theService->magneticField()->inTesla(GlobalPoint(0,0,0)).z()) < 0.01) bon=false;
745  double ndof = trajectory.ndof(bon);
746 
747  reco::Track track(trajectory.chiSquared(),
748  ndof,
749  persistentPCA,
750  persistentMomentum,
751  ftsAtVtx.charge(),
752  ftsAtVtx.curvilinearError());
753 
754  return pair<bool,reco::Track>(true,track);
755 }
756 
757 
758 pair<bool,reco::Track> MuonTrackLoader::buildTrackUpdatedAtPCA(const reco::Track &track, const reco::BeamSpot &beamSpot) const {
759 
760  const string metname = "Muon|RecoMuon|MuonTrackLoader";
762 
763  // build the transient track
764  reco::TransientTrack transientTrack(track,
765  &*theService->magneticField(),
766  theService->trackingGeometry());
767 
768  LogTrace(metname) << "Apply the vertex constraint";
769  pair<bool,FreeTrajectoryState> updateResult = theUpdatorAtVtx->update(transientTrack,beamSpot);
770 
771  if(!updateResult.first){
772  return pair<bool,reco::Track>(false,reco::Track());
773  }
774 
775  LogTrace(metname) << "FTS after the vertex constraint";
776  FreeTrajectoryState &ftsAtVtx = updateResult.second;
777 
778  LogTrace(metname) << debug.dumpFTS(ftsAtVtx);
779 
780  GlobalPoint pca = ftsAtVtx.position();
781  math::XYZPoint persistentPCA(pca.x(),pca.y(),pca.z());
782  GlobalVector p = ftsAtVtx.momentum();
783  math::XYZVector persistentMomentum(p.x(),p.y(),p.z());
784 
785  reco::Track updatedTrack(track.chi2(),
786  track.ndof(),
787  persistentPCA,
788  persistentMomentum,
789  ftsAtVtx.charge(),
790  ftsAtVtx.curvilinearError());
791 
792  return pair<bool,reco::Track>(true,updatedTrack);
793 }
794 
795 
797 
798  const string metname = "Muon|RecoMuon|MuonTrackLoader";
799 
800  const Trajectory::RecHitContainer transRecHits = trajectory.recHits();
801 
802  // put the collection of TrackingRecHit in the event
803 
804  // sets the outermost and innermost TSOSs
805  // FIXME: check it!
806  TrajectoryStateOnSurface outerTSOS;
807  TrajectoryStateOnSurface innerTSOS;
808  unsigned int innerId=0, outerId=0;
810  DetId outerDetId;
811 
812  if (trajectory.direction() == alongMomentum) {
813  LogTrace(metname)<<"alongMomentum";
814  outerTSOS = trajectory.lastMeasurement().updatedState();
815  innerTSOS = trajectory.firstMeasurement().updatedState();
816  outerId = trajectory.lastMeasurement().recHit()->geographicalId().rawId();
817  innerId = trajectory.firstMeasurement().recHit()->geographicalId().rawId();
818  outerRecHit = trajectory.lastMeasurement().recHit();
819  outerDetId = trajectory.lastMeasurement().recHit()->geographicalId();
820  }
821  else if (trajectory.direction() == oppositeToMomentum) {
822  LogTrace(metname)<<"oppositeToMomentum";
823  outerTSOS = trajectory.firstMeasurement().updatedState();
824  innerTSOS = trajectory.lastMeasurement().updatedState();
825  outerId = trajectory.firstMeasurement().recHit()->geographicalId().rawId();
826  innerId = trajectory.lastMeasurement().recHit()->geographicalId().rawId();
827  outerRecHit = trajectory.firstMeasurement().recHit();
828  outerDetId = trajectory.firstMeasurement().recHit()->geographicalId();
829  }
830  else LogError(metname)<<"Wrong propagation direction!";
831 
832  const GeomDet *outerDet = theService->trackingGeometry()->idToDet(outerDetId);
833  GlobalPoint outerTSOSPos = outerTSOS.globalParameters().position();
834  bool inside = outerDet->surface().bounds().inside(outerDet->toLocal(outerTSOSPos));
835 
836 
837  GlobalPoint hitPos = (outerRecHit->isValid()) ? outerRecHit->globalPosition() : outerTSOS.globalParameters().position() ;
838 
839  if(!inside) {
840  LogTrace(metname)<<"The Global Muon outerMostMeasurementState is not compatible with the recHit detector! Setting outerMost postition to recHit position if recHit isValid: " << outerRecHit->isValid();
841  LogTrace(metname)<<"From " << outerTSOSPos << " to " << hitPos;
842  }
843 
844 
845  //build the TrackExtra
846  GlobalPoint v = (inside) ? outerTSOSPos : hitPos ;
847  GlobalVector p = outerTSOS.globalParameters().momentum();
848  math::XYZPoint outpos( v.x(), v.y(), v.z() );
849  math::XYZVector outmom( p.x(), p.y(), p.z() );
850 
851  v = innerTSOS.globalParameters().position();
852  p = innerTSOS.globalParameters().momentum();
853  math::XYZPoint inpos( v.x(), v.y(), v.z() );
854  math::XYZVector inmom( p.x(), p.y(), p.z() );
855 
856  reco::TrackExtra trackExtra(outpos, outmom, true, inpos, inmom, true,
857  outerTSOS.curvilinearError(), outerId,
858  innerTSOS.curvilinearError(), innerId,
859  trajectory.direction(),trajectory.seedRef());
860 
861  return trackExtra;
862 
863 }
864 
#define LogDebug(id)
EDGetTokenT< ProductType > consumes(edm::InputTag const &tag)
T getParameter(std::string const &) const
edm::EDGetTokenT< reco::BeamSpot > theBeamSpotToken
std::unique_ptr< TrajectorySmoother > theSmoother
T getUntrackedParameter(std::string const &, T const &) const
MuonTrackLoader(edm::ParameterSet &parameterSet, edm::ConsumesCollector &iC, const MuonServiceProxy *service=0)
Constructor for the STA reco the args must be specify!
int i
Definition: DBlmapReader.cc:9
virtual int dimension() const =0
static bool isInside(const GlobalPoint &)
ConstRecHitPointer const & recHit() const
virtual bool inside(const Local3DPoint &) const =0
Determine if the point is inside the bounds.
static PFTauRenderPlugin instance
const std::string metname
void setHits(TrackingRecHitRefProd const &prod, unsigned firstH, unsigned int nH)
TkClonerImpl hitCloner
const CurvilinearTrajectoryError & curvilinearError() const
Global3DPoint GlobalPoint
Definition: GlobalPoint.h:10
std::vector< Track > TrackCollection
collection of Tracks
Definition: TrackFwd.h:13
T y() const
Definition: PV3DBase.h:63
std::string theSmootherName
std::pair< bool, FreeTrajectoryState > propagate(const TrajectoryStateOnSurface &tsos, const reco::BeamSpot &beamSpot) const
Propagate the state to the 2D-PCA.
GlobalPoint globalPosition() const
LocalPoint toLocal(const GlobalPoint &gp) const
Conversion to the R.F. of the GeomDet.
Definition: GeomDet.h:67
static std::vector< const TrackingRecHit * > unpackHit(const TrackingRecHit &hit)
const Bounds & bounds() const
Definition: Surface.h:128
bool isNonnull() const
Checks for non-null.
Definition: RefToBase.h:330
TrackCharge charge() const
TrajectoryStateOnSurface geometricalInnermostState() const
Definition: Trajectory.cc:155
const Plane & surface() const
The nominal surface of the GeomDet.
Definition: GeomDet.h:40
const CurvilinearTrajectoryError & curvilinearError() const
std::vector< MuonTrackLinks > MuonTrackLinksCollection
collection of MuonTrackLinks
Definition: MuonFwd.h:22
MuonCandidate::CandidateContainer CandidateContainer
const MuonServiceProxy * theService
std::string dumpFTS(const FreeTrajectoryState &fts) const
PropagationDirection const & direction() const
Definition: Trajectory.cc:118
#define unlikely(x)
static const int CSC
Definition: MuonSubdetId.h:13
edm::InputTag theBeamSpotInputTag
double chi2() const
chi-squared of the fit
Definition: TrackBase.h:512
std::string theTrackerRecHitBuilderName
std::pair< bool, FreeTrajectoryState > update(const reco::TransientTrack &track, const reco::BeamSpot &beamSpot) const
Applies the vertex constraint.
double ndof() const
number of degrees of freedom of the fit
Definition: TrackBase.h:518
virtual ~MuonTrackLoader()
Destructor.
TrajectoryMeasurement const & lastMeasurement() const
Definition: Trajectory.h:181
double pt() const
track transverse momentum
Definition: TrackBase.h:584
FreeTrajectoryState const * freeState(bool withErrors=true) const
T z() const
Definition: PV3DBase.h:64
TrackingRecHit::ConstRecHitPointer ConstRecHitPointer
virtual std::vector< const TrackingRecHit * > recHits() const =0
Access to component RecHits (if any)
bool appendHitPattern(const TrackingRecHit &hit)
append a single hit to the HitPattern
Definition: TrackBase.h:431
edm::RefToBase< TrajectorySeed > seedRef(void) const
Definition: Trajectory.h:306
How EventSelector::AcceptEvent() decides whether to accept an event for output otherwise it is excluding the probing of A single or multiple positive and the trigger will pass if any such matching triggers are PASS or EXCEPTION[A criterion thatmatches no triggers at all is detected and causes a throw.] A single negative with an expectation of appropriate bit checking in the decision and the trigger will pass if any such matching triggers are FAIL or EXCEPTION A wildcarded negative criterion that matches more than one trigger in the trigger but the state exists so we define the behavior If all triggers are the negative crieriion will lead to accepting the event(this again matches the behavior of"!*"before the partial wildcard feature was incorporated).The per-event"cost"of each negative criterion with multiple relevant triggers is about the same as!*was in the past
edm::AssociationMap< edm::OneToOne< std::vector< Trajectory >, reco::TrackCollection, unsigned short > > TrajTrackAssociationCollection
MuonUpdatorAtVertex * theUpdatorAtVtx
GlobalVector momentum() const
#define LogTrace(id)
MuonCandidate::TrajectoryContainer TrajectoryContainer
virtual TrackingRecHit * clone() const =0
Definition: DetId.h:18
GlobalPoint position() const
int ndof(bool bon=true) const
Definition: Trajectory.cc:78
edm::OrphanHandle< reco::TrackCollection > loadTracks(const TrajectoryContainer &, edm::Event &, const std::string &="", bool=true)
Convert the trajectories into tracks and load the tracks in the event.
virtual TrackingRecHit const * hit() const
std::vector< TrackExtra > TrackExtraCollection
collection of TrackExtra objects
Definition: TrackExtraFwd.h:11
edm::OwnVector< TrackingRecHit > TrackingRecHitCollection
collection of TrackingRecHits
void setExtra(const TrackExtraRef &ref)
set reference to &quot;extra&quot; object
Definition: Track.h:184
TrajectoryMeasurement const & firstMeasurement() const
Definition: Trajectory.h:194
#define debug
Definition: HDRShower.cc:19
const GlobalTrajectoryParameters & globalParameters() const
std::string theL2SeededTkLabel
Label for L2SeededTracks.
XYZVectorD XYZVector
spatial vector with cartesian internal representation
Definition: Vector3D.h:30
ConstRecHitContainer RecHitContainer
Definition: Trajectory.h:48
XYZPointD XYZPoint
point in space with cartesian internal representation
Definition: Point3D.h:12
T const * product() const
Definition: ESHandle.h:86
reco::TrackExtra buildTrackExtra(const Trajectory &) const
void setSeedRef(const edm::RefToBase< TrajectorySeed > &seedRef)
Definition: Trajectory.h:308
float chiSquared() const
Definition: Trajectory.h:252
std::pair< bool, reco::Track > buildTrackAtPCA(const Trajectory &trajectory, const reco::BeamSpot &) const
Build a track at the PCA WITHOUT any vertex constriant.
static const int RPC
Definition: MuonSubdetId.h:14
static int position[264][3]
Definition: ReadPGInfo.cc:509
static const int DT
Definition: MuonSubdetId.h:12
const MuonServiceProxy * theService
TrajectoryStateOnSurface const & updatedState() const
DetId geographicalId() const
T x() const
Definition: PV3DBase.h:62
std::pair< bool, reco::Track > buildTrackUpdatedAtPCA(const reco::Track &trackAtPCA, const reco::BeamSpot &) const
Takes a track at the PCA and applies the vertex constriant.
ParameterSet const & parameterSet(Provenance const &provenance)
Definition: Provenance.cc:11
boost::remove_cv< typename boost::remove_reference< argument_type >::type >::type key_type
Definition: Ref.h:168