CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
GlobalMuonTrackMatcher.cc
Go to the documentation of this file.
1 
14 
15 //---------------
16 // C++ Headers --
17 //---------------
18 
19 //-------------------------------
20 // Collaborating Class Headers --
21 //-------------------------------
22 
26 
32 
34 
37 
40 
42 
43 using namespace std;
44 using namespace reco;
45 
46 //
47 // constructor
48 //
50  : theService(service) {
51  theMinP = par.getParameter<double>("MinP");
52  theMinPt = par.getParameter<double>("MinPt");
53  thePt_threshold1 = par.getParameter<double>("Pt_threshold1");
54  thePt_threshold2 = par.getParameter<double>("Pt_threshold2");
55  theEta_threshold = par.getParameter<double>("Eta_threshold");
56  theChi2_1 = par.getParameter<double>("Chi2Cut_1");
57  theChi2_2 = par.getParameter<double>("Chi2Cut_2");
58  theChi2_3 = par.getParameter<double>("Chi2Cut_3");
59  theLocChi2 = par.getParameter<double>("LocChi2Cut");
60  theDeltaD_1 = par.getParameter<double>("DeltaDCut_1");
61  theDeltaD_2 = par.getParameter<double>("DeltaDCut_2");
62  theDeltaD_3 = par.getParameter<double>("DeltaDCut_3");
63  theDeltaR_1 = par.getParameter<double>("DeltaRCut_1");
64  theDeltaR_2 = par.getParameter<double>("DeltaRCut_2");
65  theDeltaR_3 = par.getParameter<double>("DeltaRCut_3");
66  theQual_1 = par.getParameter<double>("Quality_1");
67  theQual_2 = par.getParameter<double>("Quality_2");
68  theQual_3 = par.getParameter<double>("Quality_3");
69  theOutPropagatorName = par.getParameter<string>("Propagator");
70 }
71 
72 //
73 // destructor
74 //
76 
77 //
78 // check if two tracks are compatible with the *tight* criteria
79 //
81  std::pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface> tsosPair = convertToTSOSMuHit(sta, track);
82 
83  double chi2 = match_Chi2(tsosPair.first, tsosPair.second);
84  if (chi2 > 0. && chi2 < theChi2_2)
85  return true;
86 
87  double distance = match_d(tsosPair.first, tsosPair.second);
88  if (distance > 0. && distance < theDeltaD_2)
89  return true;
90 
91  //double deltaR = match_Rpos(tsosPair.first,tsosPair.second);
92  //if ( deltaR > 0. && deltaR < theDeltaR_3 ) return true;
93 
94  return false;
95 }
96 
97 //
98 // check if two tracks are compatible
99 //
101  const TrackCand& track,
102  int matchOption,
103  int surfaceOption) const {
104  std::pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface> tsosPair;
105  if (surfaceOption == 0)
106  tsosPair = convertToTSOSMuHit(sta, track);
107  if (surfaceOption == 1)
108  tsosPair = convertToTSOSTkHit(sta, track);
109  if (surfaceOption != 0 && surfaceOption != 1)
110  return -1.0;
111 
112  if (matchOption == 0) {
113  // chi^2
114  return match_Chi2(tsosPair.first, tsosPair.second);
115  } else if (matchOption == 1) {
116  // distance
117  return match_d(tsosPair.first, tsosPair.second);
118  } else if (matchOption == 2) {
119  // deltaR
120  return match_Rpos(tsosPair.first, tsosPair.second);
121  } else if (matchOption == 3) {
122  return match_dist(tsosPair.first, tsosPair.second);
123  } else {
124  return -1.0;
125  }
126 }
127 
128 //
129 // choose the track from a TrackCollection which best
130 // matches a given standalone muon track
131 //
132 std::vector<GlobalMuonTrackMatcher::TrackCand>::const_iterator GlobalMuonTrackMatcher::matchOne(
133  const TrackCand& sta, const std::vector<TrackCand>& tracks) const {
134  if (tracks.empty())
135  return tracks.end();
136 
137  double minChi2 = 1000.0;
138  vector<TrackCand>::const_iterator result = tracks.end();
139  for (vector<TrackCand>::const_iterator is = tracks.begin(); is != tracks.end(); ++is) {
140  // propagate to common surface
141  std::pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface> tsosPair = convertToTSOSMuHit(sta, *is);
142 
143  // calculate chi^2 of local track parameters
144  double chi2 = match_Chi2(tsosPair.first, tsosPair.second);
145  if (chi2 > 0. && chi2 <= minChi2) {
146  minChi2 = chi2;
147  result = is;
148  }
149  }
150 
151  return result;
152 }
153 
154 //
155 // choose a vector of tracks from a TrackCollection that are compatible
156 // with a given standalone track. The order of checks for compatability
157 // * for low momentum: use chi2 selection
158 // * high momentum: use direction or local position
159 //
160 vector<GlobalMuonTrackMatcher::TrackCand> GlobalMuonTrackMatcher::match(const TrackCand& sta,
161  const vector<TrackCand>& tracks) const {
162  const string category = "GlobalMuonTrackMatcher";
163 
164  vector<TrackCand> result;
165 
166  if (tracks.empty())
167  return result;
168 
169  typedef std::pair<TrackCand, TrajectoryStateOnSurface> TrackCandWithTSOS;
170  vector<TrackCandWithTSOS> cands;
171  int iiTk = 1;
172  TrajectoryStateOnSurface muonTSOS;
173 
174  LogTrace(category) << " ***" << endl << "STA Muon pT " << sta.second->pt();
175  LogTrace(category) << " Tk in Region " << tracks.size() << endl;
176 
177  for (vector<TrackCand>::const_iterator is = tracks.begin(); is != tracks.end(); ++is, iiTk++) {
178  // propagate to a common surface
179  std::pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface> tsosPair = convertToTSOSMuHit(sta, *is);
180  LogTrace(category) << " Tk " << iiTk << " of " << tracks.size() << " ConvertToMuHitSurface muon isValid "
181  << tsosPair.first.isValid() << " tk isValid " << tsosPair.second.isValid() << endl;
182  if (tsosPair.first.isValid())
183  muonTSOS = tsosPair.first;
184  cands.push_back(TrackCandWithTSOS(*is, tsosPair.second));
185  }
186 
187  // initialize variables
188  double min_chisq = 999999;
189  double min_d = 999999;
190  double min_de = 999999;
191  double min_r_pos = 999999;
192  std::vector<bool> passes(cands.size(), false);
193  int jj = 0;
194 
195  int iTkCand = 1;
196  for (vector<TrackCandWithTSOS>::const_iterator ii = cands.begin(); ii != cands.end(); ++ii, jj++, iTkCand++) {
197  // tracks that are able not able propagate to a common surface
198  if (!muonTSOS.isValid() || !(*ii).second.isValid())
199  continue;
200 
201  // calculate matching variables
202  double distance = match_d(muonTSOS, (*ii).second);
203  double chi2 = match_Chi2(muonTSOS, (*ii).second);
204  double loc_chi2 = match_dist(muonTSOS, (*ii).second);
205  double deltaR = match_Rpos(muonTSOS, (*ii).second);
206 
207  LogTrace(category) << " iTk " << iTkCand << " of " << cands.size() << " eta "
208  << (*ii).second.globalPosition().eta() << " phi " << (*ii).second.globalPosition().phi() << endl;
209  LogTrace(category) << " distance " << distance << " distance cut "
210  << " " << endl;
211  LogTrace(category) << " chi2 " << chi2 << " chi2 cut "
212  << " " << endl;
213  LogTrace(category) << " loc_chi2 " << loc_chi2 << " locChi2 cut "
214  << " " << endl;
215  LogTrace(category) << " deltaR " << deltaR << " deltaR cut "
216  << " " << endl;
217 
218  if ((*ii).second.globalMomentum().perp() < thePt_threshold1) {
219  LogTrace(category) << " Enters a1" << endl;
220 
221  if ((chi2 > 0 && fabs((*ii).second.globalMomentum().eta()) < theEta_threshold && chi2 < theChi2_1) ||
222  (distance > 0 && distance / (*ii).first.second->pt() < theDeltaD_1 && loc_chi2 > 0 &&
223  loc_chi2 < theLocChi2)) {
224  LogTrace(category) << " Passes a1" << endl;
225  result.push_back((*ii).first);
226  passes[jj] = true;
227  }
228  }
229  if ((passes[jj] == false) && (*ii).second.globalMomentum().perp() < thePt_threshold2) {
230  LogTrace(category) << " Enters a2" << endl;
231  if ((chi2 > 0 && chi2 < theChi2_2) || (distance > 0 && distance < theDeltaD_2)) {
232  LogTrace(category) << " Passes a2" << endl;
233  result.push_back((*ii).first);
234  passes[jj] = true;
235  }
236  } else {
237  LogTrace(category) << " Enters a3" << endl;
238  if (distance > 0 && distance < theDeltaD_3 && deltaR > 0 && deltaR < theDeltaR_1) {
239  LogTrace(category) << " Passes a3" << endl;
240  result.push_back((*ii).first);
241  passes[jj] = true;
242  }
243  }
244 
245  if (passes[jj]) {
246  if (distance < min_d)
247  min_d = distance;
248  if (loc_chi2 < min_de)
249  min_de = loc_chi2;
250  if (deltaR < min_r_pos)
251  min_r_pos = deltaR;
252  if (chi2 < min_chisq)
253  min_chisq = chi2;
254  }
255  }
256 
257  // re-initialize mask counter
258  jj = 0;
259 
260  if (result.empty()) {
261  LogTrace(category) << " Stage 1 returned 0 results";
262  for (vector<TrackCandWithTSOS>::const_iterator is = cands.begin(); is != cands.end(); ++is, jj++) {
263  double deltaR = match_Rpos(muonTSOS, (*is).second);
264 
265  if (muonTSOS.isValid() && (*is).second.isValid()) {
266  // check matching between tracker and muon tracks using dEta cut looser then dPhi cut
267  LogTrace(category) << " Stage 2 deltaR " << deltaR << " deltaEta "
268  << fabs((*is).second.globalPosition().eta() - muonTSOS.globalPosition().eta() <
269  1.5 * theDeltaR_2)
270  << " deltaPhi "
271  << (fabs(deltaPhi((*is).second.globalPosition().barePhi(),
272  muonTSOS.globalPosition().barePhi())) < theDeltaR_2)
273  << endl;
274 
275  if (fabs((*is).second.globalPosition().eta() - muonTSOS.globalPosition().eta()) < 1.5 * theDeltaR_2 &&
276  fabs(deltaPhi((*is).second.globalPosition().barePhi(), muonTSOS.globalPosition().barePhi())) <
277  theDeltaR_2) {
278  result.push_back((*is).first);
279  passes[jj] = true;
280  }
281  }
282 
283  if (passes[jj]) {
284  double distance = match_d(muonTSOS, (*is).second);
285  double chi2 = match_Chi2(muonTSOS, (*is).second);
286  double loc_chi2 = match_dist(muonTSOS, (*is).second);
287  if (distance < min_d)
288  min_d = distance;
289  if (loc_chi2 < min_de)
290  min_de = loc_chi2;
291  if (deltaR < min_r_pos)
292  min_r_pos = deltaR;
293  if (chi2 < min_chisq)
294  min_chisq = chi2;
295  }
296  }
297  }
298 
299  for (vector<TrackCand>::const_iterator iTk = result.begin(); iTk != result.end(); ++iTk) {
300  LogTrace(category) << " -----" << endl
301  << "selected pt " << iTk->second->pt() << " eta " << iTk->second->eta() << " phi "
302  << iTk->second->phi() << endl;
303  }
304 
305  if (result.size() < 2)
306  return result;
307  else
308  result.clear();
309 
310  LogTrace(category) << " Cleaning matched candiates" << endl;
311 
312  // re-initialize mask counter
313  jj = 0;
314 
315  for (vector<TrackCandWithTSOS>::const_iterator is = cands.begin(); is != cands.end(); ++is, jj++) {
316  if (!passes[jj])
317  continue;
318 
319  double distance = match_d(muonTSOS, (*is).second);
320  double chi2 = match_Chi2(muonTSOS, (*is).second);
321  //unused double loc_chi2 = match_dist(muonTSOS,(*is).second);
322  double deltaR = match_Rpos(muonTSOS, (*is).second);
323 
324  // compute quality as the relative ratio to the minimum found for each variable
325 
326  int qual = (int)(chi2 / min_chisq + distance / min_d + deltaR / min_r_pos);
327  int n_min =
328  ((chi2 / min_chisq == 1) ? 1 : 0) + ((distance / min_d == 1) ? 1 : 0) + ((deltaR / min_r_pos == 1) ? 1 : 0);
329 
330  if (n_min == 3) {
331  result.push_back((*is).first);
332  }
333 
334  if (n_min == 2 && qual < theQual_1) {
335  result.push_back((*is).first);
336  }
337 
338  if (n_min == 1 && qual < theQual_2) {
339  result.push_back((*is).first);
340  }
341 
342  if (n_min == 0 && qual < theQual_3) {
343  result.push_back((*is).first);
344  }
345  }
346 
347  for (vector<TrackCand>::const_iterator iTk = result.begin(); iTk != result.end(); ++iTk) {
348  LogTrace(category) << " -----" << endl
349  << "selected pt " << iTk->second->pt() << " eta " << iTk->second->eta() << " phi "
350  << iTk->second->phi() << endl;
351  }
352 
353  return result;
354 }
355 
356 //
357 // propagate the two track candidates to the tracker bound surface
358 //
359 std::pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface> GlobalMuonTrackMatcher::convertToTSOSTk(
360  const TrackCand& staCand, const TrackCand& tkCand) const {
361  const string category = "GlobalMuonTrackMatcher";
362 
364 
365  TransientTrack muTT(*staCand.second, &*theService->magneticField(), theService->trackingGeometry());
366  TrajectoryStateOnSurface impactMuTSOS = muTT.impactPointState();
367 
368  TrajectoryStateOnSurface outerTkTsos;
369  if (tkCand.second.isNonnull()) {
370  // make sure the tracker track has enough momentum to reach the muon chambers
371  if (!(tkCand.second->p() < theMinP || tkCand.second->pt() < theMinPt)) {
373  *tkCand.second, *theService->trackingGeometry(), &*theService->magneticField());
374  }
375  }
376 
377  if (!impactMuTSOS.isValid() || !outerTkTsos.isValid())
378  return pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface>(empty, empty);
379 
380  // define StateOnTrackerBound object
381  StateOnTrackerBound fromInside(&*theService->propagator(theOutPropagatorName));
382 
383  // extrapolate to outer tracker surface
384  TrajectoryStateOnSurface tkTsosFromMu = fromInside(impactMuTSOS);
385  TrajectoryStateOnSurface tkTsosFromTk = fromInside(outerTkTsos);
386 
387  if (!samePlane(tkTsosFromMu, tkTsosFromTk)) {
388  // propagate tracker track to same surface as muon
389  bool same1, same2;
390  TrajectoryStateOnSurface newTkTsosFromTk, newTkTsosFromMu;
391  if (tkTsosFromMu.isValid())
392  newTkTsosFromTk = theService->propagator(theOutPropagatorName)->propagate(outerTkTsos, tkTsosFromMu.surface());
393  same1 = samePlane(newTkTsosFromTk, tkTsosFromMu);
394  LogTrace(category) << "Propagating to same tracker surface (Mu):" << same1;
395  if (!same1) {
396  if (tkTsosFromTk.isValid())
397  newTkTsosFromMu = theService->propagator(theOutPropagatorName)->propagate(impactMuTSOS, tkTsosFromTk.surface());
398  same2 = samePlane(newTkTsosFromMu, tkTsosFromTk);
399  LogTrace(category) << "Propagating to same tracker surface (Tk):" << same2;
400  }
401  if (same1)
402  tkTsosFromTk = newTkTsosFromTk;
403  else if (same2)
404  tkTsosFromMu = newTkTsosFromMu;
405  else {
406  LogTrace(category) << "Could not propagate Muon and Tracker track to the same tracker bound!";
407  return pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface>(empty, empty);
408  }
409  }
410 
411  return pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface>(tkTsosFromMu, tkTsosFromTk);
412 }
413 
414 //
415 // propagate the two track candidates to the surface of the innermost muon hit
416 //
417 std::pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface> GlobalMuonTrackMatcher::convertToTSOSMuHit(
418  const TrackCand& staCand, const TrackCand& tkCand) const {
419  const string category = "GlobalMuonTrackMatcher";
421  TransientTrack muTT(*staCand.second, &*theService->magneticField(), theService->trackingGeometry());
422  TrajectoryStateOnSurface innerMuTSOS = muTT.innermostMeasurementState();
423  TrajectoryStateOnSurface outerTkTsos, innerTkTsos;
424  if (tkCand.second.isNonnull()) {
425  // make sure the tracker track has enough momentum to reach the muon chambers
426  if (!(tkCand.second->p() < theMinP || tkCand.second->pt() < theMinPt)) {
427  TrajectoryStateOnSurface innerTkTsos;
428 
430  *tkCand.second, *theService->trackingGeometry(), &*theService->magneticField());
432  *tkCand.second, *theService->trackingGeometry(), &*theService->magneticField());
433  // for cosmics, outer-most referst to last traversed layer
434  if ((innerMuTSOS.globalPosition() - outerTkTsos.globalPosition()).mag() >
435  (innerMuTSOS.globalPosition() - innerTkTsos.globalPosition()).mag())
436  outerTkTsos = innerTkTsos;
437  }
438  }
439 
440  if (!innerMuTSOS.isValid() || !outerTkTsos.isValid()) {
441  LogTrace(category) << "A TSOS validity problem! MuTSOS " << innerMuTSOS.isValid() << " TkTSOS "
442  << outerTkTsos.isValid();
443  return pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface>(empty, empty);
444  }
445 
446  const Surface& refSurface = innerMuTSOS.surface();
447  TrajectoryStateOnSurface tkAtMu =
448  theService->propagator(theOutPropagatorName)->propagate(*outerTkTsos.freeState(), refSurface);
449 
450  if (!tkAtMu.isValid()) {
451  LogTrace(category) << "Could not propagate Muon and Tracker track to the same muon hit surface!";
452  return pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface>(empty, empty);
453  }
454 
455  return pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface>(innerMuTSOS, tkAtMu);
456 }
457 
458 //
459 // propagate the two track candidates to the surface of the outermost tracker hit
460 //
461 std::pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface> GlobalMuonTrackMatcher::convertToTSOSTkHit(
462  const TrackCand& staCand, const TrackCand& tkCand) const {
463  const string category = "GlobalMuonTrackMatcher";
464 
466 
467  TransientTrack muTT(*staCand.second, &*theService->magneticField(), theService->trackingGeometry());
468  TrajectoryStateOnSurface impactMuTSOS = muTT.impactPointState();
469  TrajectoryStateOnSurface innerMuTSOS = muTT.innermostMeasurementState();
470 
471  TrajectoryStateOnSurface outerTkTsos, innerTkTsos;
472  if (tkCand.second.isNonnull()) {
473  // make sure the tracker track has enough momentum to reach the muon chambers
474  if (!(tkCand.second->p() < theMinP || tkCand.second->pt() < theMinPt)) {
476  *tkCand.second, *theService->trackingGeometry(), &*theService->magneticField());
478  *tkCand.second, *theService->trackingGeometry(), &*theService->magneticField());
479 
480  // for cosmics, outer-most referst to last traversed layer
481  if ((innerMuTSOS.globalPosition() - outerTkTsos.globalPosition()).mag() >
482  (innerMuTSOS.globalPosition() - innerTkTsos.globalPosition()).mag())
483  outerTkTsos = innerTkTsos;
484  }
485  }
486 
487  if (!impactMuTSOS.isValid() || !outerTkTsos.isValid()) {
488  LogTrace(category) << "A TSOS validity problem! MuTSOS " << impactMuTSOS.isValid() << " TkTSOS "
489  << outerTkTsos.isValid();
490  return pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface>(empty, empty);
491  }
492 
493  const Surface& refSurface = outerTkTsos.surface();
494  TrajectoryStateOnSurface muAtTk =
495  theService->propagator(theOutPropagatorName)->propagate(*impactMuTSOS.freeState(), refSurface);
496 
497  if (!muAtTk.isValid()) {
498  LogTrace(category) << "Could not propagate Muon and Tracker track to the same tracker hit surface!";
499  return pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface>(empty, empty);
500  }
501 
502  return pair<TrajectoryStateOnSurface, TrajectoryStateOnSurface>(muAtTk, outerTkTsos);
503 }
504 
505 //
506 //
507 //
509  const TrajectoryStateOnSurface& tsos2) const {
510  if (!tsos1.isValid() || !tsos2.isValid())
511  return false;
512 
513  if (fabs(match_D(tsos1, tsos2) - match_d(tsos1, tsos2)) > 0.1)
514  return false;
515 
516  const float maxtilt = 0.999;
517  const float maxdist = 0.01; // in cm
518 
519  auto p1(tsos1.surface().tangentPlane(tsos1.localPosition()));
520  auto p2(tsos2.surface().tangentPlane(tsos2.localPosition()));
521 
522  bool returnValue = ((fabs(p1->normalVector().dot(p2->normalVector())) > maxtilt) ||
523  (fabs((p1->toLocal(p2->position())).z()) < maxdist))
524  ? true
525  : false;
526 
527  return returnValue;
528 }
529 
530 //
531 // calculate Chi^2 of two trajectory states
532 //
534  const TrajectoryStateOnSurface& tsos2) const {
535  const string category = "GlobalMuonTrackMatcher";
536  //LogTrace(category) << "match_Chi2 sanity check: " << tsos1.isValid() << " " << tsos2.isValid();
537  if (!tsos1.isValid() || !tsos2.isValid())
538  return -1.;
539 
541  AlgebraicSymMatrix55 m(tsos1.localError().matrix() + tsos2.localError().matrix());
542 
543  //LogTrace(category) << "match_Chi2 vector v " << v;
544 
545  bool ierr = !m.Invert();
546 
547  if (ierr) {
548  edm::LogInfo(category) << "Error inverting covariance matrix";
549  return -1;
550  }
551 
552  double est = ROOT::Math::Similarity(v, m);
553 
554  //LogTrace(category) << "Chi2 " << est;
555 
556  return est;
557 }
558 
559 //
560 // calculate Delta_R of two track candidates at the IP
561 //
562 double GlobalMuonTrackMatcher::match_R_IP(const TrackCand& staCand, const TrackCand& tkCand) const {
563  double dR = 99.0;
564  if (tkCand.second.isNonnull()) {
565  dR = (deltaR<double>(staCand.second->eta(), staCand.second->phi(), tkCand.second->eta(), tkCand.second->phi()));
566  }
567 
568  return dR;
569 }
570 
571 //
572 // calculate Delta_R of two trajectory states
573 //
575  const TrajectoryStateOnSurface& tk) const {
576  if (!sta.isValid() || !tk.isValid())
577  return -1;
578  return (deltaR<double>(
579  sta.globalMomentum().eta(), sta.globalMomentum().phi(), tk.globalMomentum().eta(), tk.globalMomentum().phi()));
580 }
581 
582 //
583 // calculate Delta_R of two trajectory states
584 //
586  const TrajectoryStateOnSurface& tk) const {
587  if (!sta.isValid() || !tk.isValid())
588  return -1;
589  return (deltaR<double>(
590  sta.globalPosition().eta(), sta.globalPosition().phi(), tk.globalPosition().eta(), tk.globalPosition().phi()));
591 }
592 
593 //
594 // calculate the distance in global position of two trajectory states
595 //
597  if (!sta.isValid() || !tk.isValid())
598  return -1;
599  return (sta.globalPosition() - tk.globalPosition()).mag();
600 }
601 
602 //
603 // calculate the distance in local position of two trajectory states
604 //
606  if (!sta.isValid() || !tk.isValid())
607  return -1;
608  return (sta.localPosition() - tk.localPosition()).mag();
609 }
610 
611 //
612 // calculate the chi2 of the distance in local position of two
613 // trajectory states including local errors
614 //
616  const TrajectoryStateOnSurface& tk) const {
617  const string category = "GlobalMuonTrackMatcher";
618 
619  if (!sta.isValid() || !tk.isValid())
620  return -1;
621 
623  m(0, 0) = tk.localError().positionError().xx() + sta.localError().positionError().xx();
624  m(1, 0) = m(0, 1) = tk.localError().positionError().xy() + sta.localError().positionError().xy();
625  m(1, 1) = tk.localError().positionError().yy() + sta.localError().positionError().yy();
626 
628  v[0] = tk.localPosition().x() - sta.localPosition().x();
629  v[1] = tk.localPosition().y() - sta.localPosition().y();
630 
631  if (!m.Invert()) {
632  LogTrace(category) << "Error inverting local matrix ";
633  return -1;
634  }
635 
636  return ROOT::Math::Similarity(v, m);
637 }
std::vector< TrackCand >::const_iterator matchOne(const TrackCand &sta, const std::vector< TrackCand > &tracks) const
choose the one tracker track which best matches a muon track
std::pair< const Trajectory *, reco::TrackRef > TrackCand
float xx() const
Definition: LocalError.h:22
GlobalMuonTrackMatcher(const edm::ParameterSet &, const MuonServiceProxy *)
constructor
virtual ConstReferenceCountingPointer< TangentPlane > tangentPlane(const GlobalPoint &) const =0
const LocalTrajectoryParameters & localParameters() const
const TString p2
Definition: fwPaths.cc:13
static const char category[]
TrajectoryStateOnSurface outerStateOnSurface(const reco::Track &tk, const TrackingGeometry &geom, const MagneticField *field, bool withErr=true)
T mag() const
The vector magnitude. Equivalent to sqrt(vec.mag2())
bool matchTight(const TrackCand &sta, const TrackCand &track) const
check if two tracks are compatible (less than Chi2Cut, DeltaDCut, DeltaRCut)
Geom::Phi< T > phi() const
Definition: PV3DBase.h:66
T y() const
Definition: PV3DBase.h:60
GlobalPoint globalPosition() const
std::pair< TrajectoryStateOnSurface, TrajectoryStateOnSurface > convertToTSOSTkHit(const TrackCand &, const TrackCand &) const
auto const & tracks
cannot be loose
double match_Rmom(const TrajectoryStateOnSurface &, const TrajectoryStateOnSurface &) const
int ii
Definition: cuy.py:589
double match_R_IP(const TrackCand &, const TrackCand &) const
LocalError positionError() const
#define LogTrace(id)
tuple result
Definition: mps_fire.py:311
std::pair< TrajectoryStateOnSurface, TrajectoryStateOnSurface > convertToTSOSMuHit(const TrackCand &, const TrackCand &) const
T barePhi() const
Definition: PV3DBase.h:65
AlgebraicVector5 vector() const
float xy() const
Definition: LocalError.h:23
const SurfaceType & surface() const
ROOT::Math::SVector< double, 2 > AlgebraicVector2
std::pair< TrajectoryStateOnSurface, TrajectoryStateOnSurface > convertToTSOSTk(const TrackCand &, const TrackCand &) const
float yy() const
Definition: LocalError.h:24
FreeTrajectoryState const * freeState(bool withErrors=true) const
const TString p1
Definition: fwPaths.cc:12
ROOT::Math::SVector< double, 5 > AlgebraicVector5
double match_d(const TrajectoryStateOnSurface &, const TrajectoryStateOnSurface &) const
double match_Chi2(const TrajectoryStateOnSurface &, const TrajectoryStateOnSurface &) const
const AlgebraicSymMatrix55 & matrix() const
const LocalTrajectoryError & localError() const
double match(const TrackCand &sta, const TrackCand &track, int matchOption=0, int surfaceOption=1) const
double match_D(const TrajectoryStateOnSurface &, const TrajectoryStateOnSurface &) const
const MuonServiceProxy * theService
Log< level::Info, false > LogInfo
T getParameter(std::string const &) const
Definition: ParameterSet.h:303
ROOT::Math::SMatrix< double, 5, 5, ROOT::Math::MatRepSym< double, 5 > > AlgebraicSymMatrix55
T eta() const
Definition: PV3DBase.h:73
double match_dist(const TrajectoryStateOnSurface &, const TrajectoryStateOnSurface &) const
double match_Rpos(const TrajectoryStateOnSurface &, const TrajectoryStateOnSurface &) const
GlobalVector globalMomentum() const
ROOT::Math::SMatrix< double, 2, 2, ROOT::Math::MatRepStd< double, 2, 2 > > AlgebraicMatrix22
bool samePlane(const TrajectoryStateOnSurface &, const TrajectoryStateOnSurface &) const
T x() const
Definition: PV3DBase.h:59
virtual ~GlobalMuonTrackMatcher()
destructor
TrajectoryStateOnSurface innerStateOnSurface(const reco::Track &tk, const TrackingGeometry &geom, const MagneticField *field, bool withErr=true)