CMS 3D CMS Logo

MultiTrackValidator.cc
Go to the documentation of this file.
3 
7 
25 
31 #include <type_traits>
32 
33 #include "TMath.h"
34 #include <TF1.h>
37 //#include <iostream>
38 
39 using namespace std;
40 using namespace edm;
41 
43 namespace {
44  bool trackSelected(unsigned char mask, unsigned char qual) { return mask & 1 << qual; }
45 
46 } // namespace
47 
49  : tTopoEsToken(esConsumes()),
50  parametersDefinerIsCosmic_(pset.getParameter<std::string>("parametersDefiner") == "CosmicParametersDefinerForTP"),
51  associators(pset.getUntrackedParameter<std::vector<edm::InputTag>>("associators")),
52  label(pset.getParameter<std::vector<edm::InputTag>>("label")),
53  ignoremissingtkcollection_(pset.getUntrackedParameter<bool>("ignoremissingtrackcollection", false)),
54  useAssociators_(pset.getParameter<bool>("UseAssociators")),
55  calculateDrSingleCollection_(pset.getUntrackedParameter<bool>("calculateDrSingleCollection")),
56  doPlotsOnlyForTruePV_(pset.getUntrackedParameter<bool>("doPlotsOnlyForTruePV")),
57  doSummaryPlots_(pset.getUntrackedParameter<bool>("doSummaryPlots")),
58  doSimPlots_(pset.getUntrackedParameter<bool>("doSimPlots")),
59  doSimTrackPlots_(pset.getUntrackedParameter<bool>("doSimTrackPlots")),
60  doRecoTrackPlots_(pset.getUntrackedParameter<bool>("doRecoTrackPlots")),
61  dodEdxPlots_(pset.getUntrackedParameter<bool>("dodEdxPlots")),
62  doPVAssociationPlots_(pset.getUntrackedParameter<bool>("doPVAssociationPlots")),
63  doSeedPlots_(pset.getUntrackedParameter<bool>("doSeedPlots")),
64  doMVAPlots_(pset.getUntrackedParameter<bool>("doMVAPlots")),
65  applyTPSelToSimMatch_(pset.getParameter<bool>("applyTPSelToSimMatch")),
66  simPVMaxZ_(pset.getUntrackedParameter<double>("simPVMaxZ")) {
67  if (not(pset.getParameter<edm::InputTag>("cores").label().empty())) {
68  cores_ = consumes<edm::View<reco::Candidate>>(pset.getParameter<edm::InputTag>("cores"));
69  }
70  if (label.empty()) {
71  // Disable prefetching of everything if there are no track collections
72  return;
73  }
74 
75  const edm::InputTag& label_tp_effic_tag = pset.getParameter<edm::InputTag>("label_tp_effic");
76  const edm::InputTag& label_tp_fake_tag = pset.getParameter<edm::InputTag>("label_tp_fake");
77 
78  if (pset.getParameter<bool>("label_tp_effic_refvector")) {
79  label_tp_effic_refvector = consumes<TrackingParticleRefVector>(label_tp_effic_tag);
80  } else {
81  label_tp_effic = consumes<TrackingParticleCollection>(label_tp_effic_tag);
82  }
83  if (pset.getParameter<bool>("label_tp_fake_refvector")) {
84  label_tp_fake_refvector = consumes<TrackingParticleRefVector>(label_tp_fake_tag);
85  } else {
86  label_tp_fake = consumes<TrackingParticleCollection>(label_tp_fake_tag);
87  }
88  label_pileupinfo = consumes<std::vector<PileupSummaryInfo>>(pset.getParameter<edm::InputTag>("label_pileupinfo"));
89  for (const auto& tag : pset.getParameter<std::vector<edm::InputTag>>("sim")) {
90  simHitTokens_.push_back(consumes<std::vector<PSimHit>>(tag));
91  }
92 
93  std::vector<edm::InputTag> doResolutionPlotsForLabels =
94  pset.getParameter<std::vector<edm::InputTag>>("doResolutionPlotsForLabels");
95  doResolutionPlots_.reserve(label.size());
96  for (auto& itag : label) {
97  labelToken.push_back(consumes<edm::View<reco::Track>>(itag));
98  const bool doResol = doResolutionPlotsForLabels.empty() ||
101  doResolutionPlots_.push_back(doResol);
102  }
103  { // check for duplicates
104  auto labelTmp = edm::vector_transform(label, [&](const edm::InputTag& tag) { return tag.label(); });
105  std::sort(begin(labelTmp), end(labelTmp));
107  const std::string* prev = &empty;
108  for (const std::string& l : labelTmp) {
109  if (l == *prev) {
110  throw cms::Exception("Configuration") << "Duplicate InputTag in labels: " << l;
111  }
112  prev = &l;
113  }
114  }
115 
116  edm::InputTag beamSpotTag = pset.getParameter<edm::InputTag>("beamSpot");
117  bsSrc = consumes<reco::BeamSpot>(beamSpotTag);
118 
120  parametersDefinerTP_ = std::make_unique<CosmicParametersDefinerForTP>(consumesCollector());
121  } else {
122  parametersDefinerTP_ = std::make_unique<ParametersDefinerForTP>(beamSpotTag, consumesCollector());
123  }
124 
125  ParameterSet psetForHistoProducerAlgo = pset.getParameter<ParameterSet>("histoProducerAlgoBlock");
126  histoProducerAlgo_ = std::make_unique<MTVHistoProducerAlgoForTracker>(psetForHistoProducerAlgo, doSeedPlots_);
127 
128  dirName_ = pset.getParameter<std::string>("dirName");
129 
130  tpNLayersToken_ = consumes<edm::ValueMap<unsigned int>>(pset.getParameter<edm::InputTag>("label_tp_nlayers"));
132  consumes<edm::ValueMap<unsigned int>>(pset.getParameter<edm::InputTag>("label_tp_npixellayers"));
134  consumes<edm::ValueMap<unsigned int>>(pset.getParameter<edm::InputTag>("label_tp_nstripstereolayers"));
135 
136  if (dodEdxPlots_) {
137  m_dEdx1Tag = consumes<edm::ValueMap<reco::DeDxData>>(pset.getParameter<edm::InputTag>("dEdx1Tag"));
138  m_dEdx2Tag = consumes<edm::ValueMap<reco::DeDxData>>(pset.getParameter<edm::InputTag>("dEdx2Tag"));
139  }
140 
141  label_tv = consumes<TrackingVertexCollection>(pset.getParameter<edm::InputTag>("label_tv"));
143  recoVertexToken_ = consumes<edm::View<reco::Vertex>>(pset.getUntrackedParameter<edm::InputTag>("label_vertex"));
145  consumes<reco::VertexToTrackingVertexAssociator>(pset.getUntrackedParameter<edm::InputTag>("vertexAssociator"));
146  }
147 
148  if (doMVAPlots_) {
150  auto mvaPSet = pset.getUntrackedParameter<edm::ParameterSet>("mvaLabels");
151  for (size_t iIter = 0; iIter < labelToken.size(); ++iIter) {
154  if (mvaPSet.exists(labels.module)) {
156  mvaPSet.getUntrackedParameter<std::vector<std::string>>(labels.module), [&](const std::string& tag) {
157  return std::make_tuple(consumes<MVACollection>(edm::InputTag(tag, "MVAValues")),
158  consumes<QualityMaskCollection>(edm::InputTag(tag, "QualityMasks")));
159  });
160  }
161  }
162  }
163 
164  tpSelector = TrackingParticleSelector(pset.getParameter<double>("ptMinTP"),
165  pset.getParameter<double>("ptMaxTP"),
166  pset.getParameter<double>("minRapidityTP"),
167  pset.getParameter<double>("maxRapidityTP"),
168  pset.getParameter<double>("tipTP"),
169  pset.getParameter<double>("lipTP"),
170  pset.getParameter<int>("minHitTP"),
171  pset.getParameter<bool>("signalOnlyTP"),
172  pset.getParameter<bool>("intimeOnlyTP"),
173  pset.getParameter<bool>("chargedOnlyTP"),
174  pset.getParameter<bool>("stableOnlyTP"),
175  pset.getParameter<std::vector<int>>("pdgIdTP"),
176  pset.getParameter<bool>("invertRapidityCutTP"),
177  pset.getParameter<double>("minPhi"),
178  pset.getParameter<double>("maxPhi"));
179 
180  cosmictpSelector = CosmicTrackingParticleSelector(pset.getParameter<double>("ptMinTP"),
181  pset.getParameter<double>("minRapidityTP"),
182  pset.getParameter<double>("maxRapidityTP"),
183  pset.getParameter<double>("tipTP"),
184  pset.getParameter<double>("lipTP"),
185  pset.getParameter<int>("minHitTP"),
186  pset.getParameter<bool>("chargedOnlyTP"),
187  pset.getParameter<std::vector<int>>("pdgIdTP"));
188 
189  ParameterSet psetVsPhi = psetForHistoProducerAlgo.getParameter<ParameterSet>("TpSelectorForEfficiencyVsPhi");
190  dRtpSelector = TrackingParticleSelector(psetVsPhi.getParameter<double>("ptMin"),
191  psetVsPhi.getParameter<double>("ptMax"),
192  psetVsPhi.getParameter<double>("minRapidity"),
193  psetVsPhi.getParameter<double>("maxRapidity"),
194  psetVsPhi.getParameter<double>("tip"),
195  psetVsPhi.getParameter<double>("lip"),
196  psetVsPhi.getParameter<int>("minHit"),
197  psetVsPhi.getParameter<bool>("signalOnly"),
198  psetVsPhi.getParameter<bool>("intimeOnly"),
199  psetVsPhi.getParameter<bool>("chargedOnly"),
200  psetVsPhi.getParameter<bool>("stableOnly"),
201  psetVsPhi.getParameter<std::vector<int>>("pdgId"),
202  psetVsPhi.getParameter<bool>("invertRapidityCut"),
203  psetVsPhi.getParameter<double>("minPhi"),
204  psetVsPhi.getParameter<double>("maxPhi"));
205 
207 
208  useGsf = pset.getParameter<bool>("useGsf");
209 
210  _simHitTpMapTag = mayConsume<SimHitTPAssociationProducer::SimHitTPAssociationList>(
211  pset.getParameter<edm::InputTag>("simHitTpMapTag"));
212 
215  consumes<edm::View<reco::Track>>(pset.getParameter<edm::InputTag>("trackCollectionForDrCalculation"));
216  }
217 
218  if (useAssociators_) {
219  for (auto const& src : associators) {
220  associatorTokens.push_back(consumes<reco::TrackToTrackingParticleAssociator>(src));
221  }
222  } else {
223  for (auto const& src : associators) {
224  associatormapStRs.push_back(consumes<reco::SimToRecoCollection>(src));
225  associatormapRtSs.push_back(consumes<reco::RecoToSimCollection>(src));
226  }
227  }
228 }
229 
231 
233  edm::Run const&,
234  edm::EventSetup const& setup,
235  Histograms& histograms) const {
236  if (label.empty()) {
237  // Disable histogram booking if there are no track collections
238  return;
239  }
240 
241  const auto minColl = -0.5;
242  const auto maxColl = label.size() - 0.5;
243  const auto nintColl = label.size();
244 
245  auto binLabels = [&](dqm::reco::MonitorElement* me) {
246  for (size_t i = 0; i < label.size(); ++i) {
247  me->setBinLabel(i + 1, label[i].label());
248  }
249  me->disableAlphanumeric();
250  return me;
251  };
252 
253  //Booking histograms concerning with simulated tracks
254  if (doSimPlots_) {
255  ibook.cd();
256  ibook.setCurrentFolder(dirName_ + "simulation");
257 
258  histoProducerAlgo_->bookSimHistos(ibook, histograms.histoProducerAlgo);
259 
260  ibook.cd();
261  ibook.setCurrentFolder(dirName_);
262  }
263 
264  for (unsigned int ww = 0; ww < associators.size(); ww++) {
265  ibook.cd();
266  // FIXME: these need to be moved to a subdirectory whose name depends on the associator
267  ibook.setCurrentFolder(dirName_);
268 
269  if (doSummaryPlots_) {
270  if (doSimTrackPlots_) {
271  histograms.h_assoc_coll.push_back(
272  binLabels(ibook.book1D("num_assoc(simToReco)_coll",
273  "N of associated (simToReco) tracks vs track collection",
274  nintColl,
275  minColl,
276  maxColl)));
277  histograms.h_simul_coll.push_back(binLabels(
278  ibook.book1D("num_simul_coll", "N of simulated tracks vs track collection", nintColl, minColl, maxColl)));
279  }
280  if (doRecoTrackPlots_) {
281  histograms.h_reco_coll.push_back(binLabels(
282  ibook.book1D("num_reco_coll", "N of reco track vs track collection", nintColl, minColl, maxColl)));
283  histograms.h_assoc2_coll.push_back(
284  binLabels(ibook.book1D("num_assoc(recoToSim)_coll",
285  "N of associated (recoToSim) tracks vs track collection",
286  nintColl,
287  minColl,
288  maxColl)));
289  histograms.h_looper_coll.push_back(
290  binLabels(ibook.book1D("num_duplicate_coll",
291  "N of associated (recoToSim) looper tracks vs track collection",
292  nintColl,
293  minColl,
294  maxColl)));
295  histograms.h_pileup_coll.push_back(
296  binLabels(ibook.book1D("num_pileup_coll",
297  "N of associated (recoToSim) pileup tracks vs track collection",
298  nintColl,
299  minColl,
300  maxColl)));
301  }
302  }
303 
304  for (unsigned int www = 0; www < label.size(); www++) {
305  ibook.cd();
306  InputTag algo = label[www];
307  string dirName = dirName_;
308  if (!algo.process().empty())
309  dirName += algo.process() + "_";
310  if (!algo.label().empty())
311  dirName += algo.label() + "_";
312  if (!algo.instance().empty())
313  dirName += algo.instance() + "_";
314  if (dirName.find("Tracks") < dirName.length()) {
315  dirName.replace(dirName.find("Tracks"), 6, "");
316  }
317  string assoc = associators[ww].label();
318  if (assoc.find("Track") < assoc.length()) {
319  assoc.replace(assoc.find("Track"), 5, "");
320  }
321  dirName += assoc;
322  std::replace(dirName.begin(), dirName.end(), ':', '_');
323 
324  ibook.setCurrentFolder(dirName);
325 
326  const bool doResolutionPlots = doResolutionPlots_[www];
327 
328  if (doSimTrackPlots_) {
329  histoProducerAlgo_->bookSimTrackHistos(ibook, histograms.histoProducerAlgo, doResolutionPlots);
331  histoProducerAlgo_->bookSimTrackPVAssociationHistos(ibook, histograms.histoProducerAlgo);
332  }
333 
334  //Booking histograms concerning with reconstructed tracks
335  if (doRecoTrackPlots_) {
336  histoProducerAlgo_->bookRecoHistos(ibook, histograms.histoProducerAlgo, doResolutionPlots);
337  if (dodEdxPlots_)
338  histoProducerAlgo_->bookRecodEdxHistos(ibook, histograms.histoProducerAlgo);
340  histoProducerAlgo_->bookRecoPVAssociationHistos(ibook, histograms.histoProducerAlgo);
341  if (doMVAPlots_)
342  histoProducerAlgo_->bookMVAHistos(
343  ibook, histograms.histoProducerAlgo, mvaQualityCollectionTokens_[www].size());
344  }
345 
346  if (doSeedPlots_) {
347  histoProducerAlgo_->bookSeedHistos(ibook, histograms.histoProducerAlgo);
348  }
349  } //end loop www
350  } // end loop ww
351 }
352 
353 #ifdef EDM_ML_DEBUG
354 namespace {
355  void ensureEffIsSubsetOfFake(const TrackingParticleRefVector& eff, const TrackingParticleRefVector& fake) {
356  // If efficiency RefVector is empty, don't check the product ids
357  // as it will be 0:0 for empty. This covers also the case where
358  // both are empty. The case of fake being empty and eff not is an
359  // error.
360  if (eff.empty())
361  return;
362 
363  // First ensure product ids
364  if (eff.id() != fake.id()) {
365  throw cms::Exception("Configuration")
366  << "Efficiency and fake TrackingParticle (refs) point to different collections (eff " << eff.id() << " fake "
367  << fake.id()
368  << "). This is not supported. Efficiency TP set must be the same or a subset of the fake TP set.";
369  }
370 
371  // Same technique as in associationMapFilterValues
372  edm::IndexSet fakeKeys;
373  fakeKeys.reserve(fake.size());
374  for (const auto& ref : fake) {
375  fakeKeys.insert(ref.key());
376  }
377 
378  for (const auto& ref : eff) {
379  if (!fakeKeys.has(ref.key())) {
380  throw cms::Exception("Configuration") << "Efficiency TrackingParticle " << ref.key()
381  << " is not found from the set of fake TPs. This is not supported. The "
382  "efficiency TP set must be the same or a subset of the fake TP set.";
383  }
384  }
385  }
386 } // namespace
387 #endif
388 
390  const edm::Handle<TrackingVertexCollection>& htv) const {
391  for (const auto& simV : *htv) {
392  if (simV.eventId().bunchCrossing() != 0)
393  continue; // remove OOTPU
394  if (simV.eventId().event() != 0)
395  continue; // pick the PV of hard scatter
396  return &(simV.position());
397  }
398  return nullptr;
399 }
400 
402  const edm::Event& event, const edm::Handle<TrackingVertexCollection>& htv) const {
404  event.getByToken(recoVertexToken_, hvertex);
405 
407  event.getByToken(vertexAssociatorToken_, hvassociator);
408 
409  auto v_r2s = hvassociator->associateRecoToSim(hvertex, htv);
410  auto pvPtr = hvertex->refAt(0);
411  if (pvPtr->isFake() || pvPtr->ndof() < 0) // skip junk vertices
412  return nullptr;
413 
414  auto pvFound = v_r2s.find(pvPtr);
415  if (pvFound == v_r2s.end())
416  return nullptr;
417 
418  for (const auto& vertexRefQuality : pvFound->val) {
419  const TrackingVertex& tv = *(vertexRefQuality.first);
420  if (tv.eventId().event() == 0 && tv.eventId().bunchCrossing() == 0) {
421  return &(pvPtr->position());
422  }
423  }
424 
425  return nullptr;
426 }
427 
429  const Histograms& histograms,
430  const TrackingParticleRefVector& tPCeff,
431  const edm::Event& event,
432  const edm::EventSetup& setup,
433  const reco::BeamSpot& bs,
434  std::vector<std::tuple<TrackingParticle::Vector, TrackingParticle::Point>>& momVert_tPCeff,
435  std::vector<size_t>& selected_tPCeff) const {
436  selected_tPCeff.reserve(tPCeff.size());
437  momVert_tPCeff.reserve(tPCeff.size());
438  int nIntimeTPs = 0;
440  for (size_t j = 0; j < tPCeff.size(); ++j) {
441  const TrackingParticleRef& tpr = tPCeff[j];
442 
443  auto const& rec = parametersDefinerTP_->momentumAndVertex(event, setup, tpr);
444  TrackingParticle::Vector const& momentum = std::get<0>(rec);
445  TrackingParticle::Point const& vertex = std::get<1>(rec);
446  if (doSimPlots_) {
447  histoProducerAlgo_->fill_generic_simTrack_histos(
448  histograms.histoProducerAlgo, momentum, vertex, tpr->eventId().bunchCrossing());
449  }
450  if (tpr->eventId().bunchCrossing() == 0)
451  ++nIntimeTPs;
452 
453  if (cosmictpSelector(tpr, &bs, event, setup)) {
454  selected_tPCeff.push_back(j);
455  momVert_tPCeff.emplace_back(momentum, vertex);
456  }
457  }
458  } else {
459  size_t j = 0;
460  for (auto const& tpr : tPCeff) {
461  const TrackingParticle& tp = *tpr;
462 
463  // TODO: do we want to fill these from all TPs that include IT
464  // and OOT (as below), or limit to IT+OOT TPs passing tpSelector
465  // (as it was before)? The latter would require another instance
466  // of tpSelector with intimeOnly=False.
467  if (doSimPlots_) {
468  histoProducerAlgo_->fill_generic_simTrack_histos(
469  histograms.histoProducerAlgo, tp.momentum(), tp.vertex(), tp.eventId().bunchCrossing());
470  }
471  if (tp.eventId().bunchCrossing() == 0)
472  ++nIntimeTPs;
473 
474  if (tpSelector(tp)) {
475  selected_tPCeff.push_back(j);
476  momVert_tPCeff.emplace_back(parametersDefinerTP_->momentumAndVertex(event, setup, tpr));
477  }
478  ++j;
479  }
480  }
481  if (doSimPlots_) {
482  histoProducerAlgo_->fill_simTrackBased_histos(histograms.histoProducerAlgo, nIntimeTPs);
483  }
484 }
485 
487  const std::vector<size_t>& selected_tPCeff,
488  DynArray<float>& dR_tPCeff,
489  DynArray<float>& dR_tPCeff_jet,
490  const edm::View<reco::Candidate>* cores) const {
491  if (tPCeff.empty()) {
492  return 0;
493  }
494  float etaL[tPCeff.size()], phiL[tPCeff.size()];
495  size_t n_selTP_dr = 0;
496  for (size_t iTP : selected_tPCeff) {
497  //calculare dR wrt inclusive collection (also with PU, low pT, displaced)
498  auto const& tp2 = *(tPCeff[iTP]);
499  auto&& p = tp2.momentum();
500  etaL[iTP] = etaFromXYZ(p.x(), p.y(), p.z());
501  phiL[iTP] = atan2f(p.y(), p.x());
502  }
503  for (size_t iTP1 : selected_tPCeff) {
504  auto const& tp = *(tPCeff[iTP1]);
506  double dR_jet = std::numeric_limits<double>::max();
507  if (dRtpSelector(tp)) { //only for those needed for efficiency!
508  ++n_selTP_dr;
509  float eta = etaL[iTP1];
510  float phi = phiL[iTP1];
511  for (size_t iTP2 : selected_tPCeff) {
512  //calculare dR wrt inclusive collection (also with PU, low pT, displaced)
513  if (iTP1 == iTP2) {
514  continue;
515  }
516  auto dR_tmp = reco::deltaR2(eta, phi, etaL[iTP2], phiL[iTP2]);
517  if (dR_tmp < dR)
518  dR = dR_tmp;
519  } // ttp2 (iTP)
520  if (cores != nullptr) {
521  for (unsigned int ji = 0; ji < cores->size(); ji++) { //jet loop
522  const reco::Candidate& jet = (*cores)[ji];
523  double jet_eta = jet.eta();
524  double jet_phi = jet.phi();
525  auto dR_jet_tmp = reco::deltaR2(eta, phi, jet_eta, jet_phi);
526  if (dR_jet_tmp < dR_jet)
527  dR_jet = dR_jet_tmp;
528  }
529  }
530  }
531  dR_tPCeff[iTP1] = std::sqrt(dR);
532  dR_tPCeff_jet[iTP1] = std::sqrt(dR_jet);
533 
534  } // tp
535  return n_selTP_dr;
536 }
537 
539  const edm::View<reco::Track>& trackCollectionDr,
540  DynArray<float>& dR_trk,
541  DynArray<float>& dR_trk_jet,
542  const edm::View<reco::Candidate>* cores) const {
543  if (trackCollectionDr.empty()) {
544  return;
545  }
546  int i = 0;
547  float etaL[trackCollectionDr.size()];
548  float phiL[trackCollectionDr.size()];
549  bool validL[trackCollectionDr.size()];
550  for (auto const& track2 : trackCollectionDr) {
551  auto&& p = track2.momentum();
552  etaL[i] = etaFromXYZ(p.x(), p.y(), p.z());
553  phiL[i] = atan2f(p.y(), p.x());
554  validL[i] = !trackFromSeedFitFailed(track2);
555  ++i;
556  }
557  for (View<reco::Track>::size_type i = 0; i < trackCollection.size(); ++i) {
558  auto const& track = trackCollection[i];
560  auto dR_jet = std::numeric_limits<float>::max();
562  auto&& p = track.momentum();
563  float eta = etaFromXYZ(p.x(), p.y(), p.z());
564  float phi = atan2f(p.y(), p.x());
565  for (View<reco::Track>::size_type j = 0; j < trackCollectionDr.size(); ++j) {
566  if (!validL[j])
567  continue;
568  auto dR_tmp = reco::deltaR2(eta, phi, etaL[j], phiL[j]);
569  if ((dR_tmp < dR) & (dR_tmp > std::numeric_limits<float>::min()))
570  dR = dR_tmp;
571  }
572  if (cores != nullptr) {
573  for (unsigned int ji = 0; ji < cores->size(); ji++) { //jet loop
574  const reco::Candidate& jet = (*cores)[ji];
575  double jet_eta = jet.eta();
576  double jet_phi = jet.phi();
577  auto dR_jet_tmp = reco::deltaR2(eta, phi, jet_eta, jet_phi);
578  if (dR_jet_tmp < dR_jet)
579  dR_jet = dR_jet_tmp;
580  }
581  }
582  }
583  dR_trk[i] = std::sqrt(dR);
584  dR_trk_jet[i] = std::sqrt(dR_jet);
585  }
586 }
587 
589  const edm::EventSetup& setup,
590  const Histograms& histograms) const {
591  if (label.empty()) {
592  // Disable if there are no track collections
593  return;
594  }
595 
596  using namespace reco;
597 
598  LogDebug("TrackValidator") << "\n===================================================="
599  << "\n"
600  << "Analyzing new event"
601  << "\n"
602  << "====================================================\n"
603  << "\n";
604 
605  const TrackerTopology& ttopo = setup.getData(tTopoEsToken);
606 
607  // FIXME: we really need to move to edm::View for reading the
608  // TrackingParticles... Unfortunately it has non-trivial
609  // consequences on the associator/association interfaces etc.
610  TrackingParticleRefVector tmpTPeff;
611  TrackingParticleRefVector tmpTPfake;
612  const TrackingParticleRefVector* tmpTPeffPtr = nullptr;
613  const TrackingParticleRefVector* tmpTPfakePtr = nullptr;
614 
616  edm::Handle<TrackingParticleRefVector> TPCollectionHeffRefVector;
617 
618  const bool tp_effic_refvector = label_tp_effic.isUninitialized();
619  if (!tp_effic_refvector) {
620  event.getByToken(label_tp_effic, TPCollectionHeff);
621  tmpTPeff.reserve(TPCollectionHeff->size());
622  for (size_t i = 0, size = TPCollectionHeff->size(); i < size; ++i) {
623  tmpTPeff.push_back(TrackingParticleRef(TPCollectionHeff, i));
624  }
625  tmpTPeffPtr = &tmpTPeff;
626  } else {
627  event.getByToken(label_tp_effic_refvector, TPCollectionHeffRefVector);
628  tmpTPeffPtr = TPCollectionHeffRefVector.product();
629  }
631  edm::Handle<TrackingParticleCollection> TPCollectionHfake;
632  event.getByToken(label_tp_fake, TPCollectionHfake);
633  tmpTPfake.reserve(TPCollectionHfake->size());
634  for (size_t i = 0, size = TPCollectionHfake->size(); i < size; ++i) {
635  tmpTPfake.push_back(TrackingParticleRef(TPCollectionHfake, i));
636  }
637  tmpTPfakePtr = &tmpTPfake;
638  } else {
639  edm::Handle<TrackingParticleRefVector> TPCollectionHfakeRefVector;
640  event.getByToken(label_tp_fake_refvector, TPCollectionHfakeRefVector);
641  tmpTPfakePtr = TPCollectionHfakeRefVector.product();
642  }
643 
644  TrackingParticleRefVector const& tPCeff = *tmpTPeffPtr;
645  TrackingParticleRefVector const& tPCfake = *tmpTPfakePtr;
646 
647 #ifdef EDM_ML_DEBUG
648  ensureEffIsSubsetOfFake(tPCeff, tPCfake);
649 #endif
650 
653  //warning: make sure the TP collection used in the map is the same used in the MTV!
654  event.getByToken(_simHitTpMapTag, simHitsTPAssoc);
655  parametersDefinerTP_->initEvent(simHitsTPAssoc);
656  cosmictpSelector.initEvent(simHitsTPAssoc);
657  }
658 
659  // Find the sim PV and tak its position
661  event.getByToken(label_tv, htv);
662  const TrackingVertex::LorentzVector* theSimPVPosition = getSimPVPosition(htv);
663  if (simPVMaxZ_ >= 0) {
664  if (!theSimPVPosition)
665  return;
666  if (std::abs(theSimPVPosition->z()) > simPVMaxZ_)
667  return;
668  }
669 
670  // Check, when necessary, if reco PV matches to sim PV
671  const reco::Vertex::Point* thePVposition = nullptr;
673  thePVposition = getRecoPVPosition(event, htv);
674  if (doPlotsOnlyForTruePV_ && !thePVposition)
675  return;
676 
677  // Rest of the code assumes that if thePVposition is non-null, the
678  // PV-association histograms get filled. In above, the "nullness"
679  // is used to deliver the information if the reco PV is matched to
680  // the sim PV.
682  thePVposition = nullptr;
683  }
684 
685  edm::Handle<reco::BeamSpot> recoBeamSpotHandle;
686  event.getByToken(bsSrc, recoBeamSpotHandle);
687  reco::BeamSpot const& bs = *recoBeamSpotHandle;
688 
690  event.getByToken(label_pileupinfo, puinfoH);
691  PileupSummaryInfo puinfo;
692 
693  for (unsigned int puinfo_ite = 0; puinfo_ite < (*puinfoH).size(); ++puinfo_ite) {
694  if ((*puinfoH)[puinfo_ite].getBunchCrossing() == 0) {
695  puinfo = (*puinfoH)[puinfo_ite];
696  break;
697  }
698  }
699 
700  // Number of 3D layers for TPs
702  event.getByToken(tpNLayersToken_, tpNLayersH);
703  const auto& nLayers_tPCeff = *tpNLayersH;
704 
705  event.getByToken(tpNPixelLayersToken_, tpNLayersH);
706  const auto& nPixelLayers_tPCeff = *tpNLayersH;
707 
708  event.getByToken(tpNStripStereoLayersToken_, tpNLayersH);
709  const auto& nStripMonoAndStereoLayers_tPCeff = *tpNLayersH;
710 
711  // Precalculate TP selection (for efficiency), and momentum and vertex wrt PCA
712  //
713  // TODO: ParametersDefinerForTP ESProduct needs to be changed to
714  // EDProduct because of consumes.
715  //
716  // In principle, we could just precalculate the momentum and vertex
717  // wrt PCA for all TPs for once and put that to the event. To avoid
718  // repetitive calculations those should be calculated only once for
719  // each TP. That would imply that we should access TPs via Refs
720  // (i.e. View) in here, since, in general, the eff and fake TP
721  // collections can be different (and at least HI seems to use that
722  // feature). This would further imply that the
723  // RecoToSimCollection/SimToRecoCollection should be changed to use
724  // View<TP> instead of vector<TP>, and migrate everything.
725  //
726  // Or we could take only one input TP collection, and do another
727  // TP-selection to obtain the "fake" collection like we already do
728  // for "efficiency" TPs.
729  std::vector<size_t> selected_tPCeff;
730  std::vector<std::tuple<TrackingParticle::Vector, TrackingParticle::Point>> momVert_tPCeff;
731  tpParametersAndSelection(histograms, tPCeff, event, setup, bs, momVert_tPCeff, selected_tPCeff);
732 
733  //calculate dR for TPs
734  declareDynArray(float, tPCeff.size(), dR_tPCeff);
735 
736  //calculate dR_jet for TPs
737  const edm::View<reco::Candidate>* coresVector = nullptr;
738  if (not cores_.isUninitialized()) {
740  event.getByToken(cores_, cores);
741  if (cores.isValid()) {
742  coresVector = cores.product();
743  }
744  }
745  declareDynArray(float, tPCeff.size(), dR_tPCeff_jet);
746 
747  size_t n_selTP_dr = tpDR(tPCeff, selected_tPCeff, dR_tPCeff, dR_tPCeff_jet, coresVector);
748 
752  }
753 
754  // dE/dx
755  // at some point this could be generalized, with a vector of tags and a corresponding vector of Handles
756  // I'm writing the interface such to take vectors of ValueMaps
757  std::vector<const edm::ValueMap<reco::DeDxData>*> v_dEdx;
758  if (dodEdxPlots_) {
761  event.getByToken(m_dEdx1Tag, dEdx1Handle);
762  event.getByToken(m_dEdx2Tag, dEdx2Handle);
763  v_dEdx.push_back(dEdx1Handle.product());
764  v_dEdx.push_back(dEdx2Handle.product());
765  }
766 
767  std::vector<const MVACollection*> mvaCollections;
768  std::vector<const QualityMaskCollection*> qualityMaskCollections;
769  std::vector<float> mvaValues;
770 
771  int w = 0; //counter counting the number of sets of histograms
772  for (unsigned int ww = 0; ww < associators.size(); ww++) {
773  // run value filtering of recoToSim map already here as it depends only on the association, not track collection
774  reco::SimToRecoCollection const* simRecCollPFull = nullptr;
775  reco::RecoToSimCollection const* recSimCollP = nullptr;
776  reco::RecoToSimCollection recSimCollL;
777  if (!useAssociators_) {
778  Handle<reco::SimToRecoCollection> simtorecoCollectionH;
779  event.getByToken(associatormapStRs[ww], simtorecoCollectionH);
780  simRecCollPFull = simtorecoCollectionH.product();
781 
782  Handle<reco::RecoToSimCollection> recotosimCollectionH;
783  event.getByToken(associatormapRtSs[ww], recotosimCollectionH);
784  recSimCollP = recotosimCollectionH.product();
785 
786  // We need to filter the associations of the fake-TrackingParticle
787  // collection only from RecoToSim collection, otherwise the
788  // RecoToSim histograms get false entries
789  recSimCollL = associationMapFilterValues(*recSimCollP, tPCfake);
790  recSimCollP = &recSimCollL;
791  }
792 
793  for (unsigned int www = 0; www < label.size();
794  www++, w++) { // need to increment w here, since there are many continues in the loop body
795  //
796  //get collections from the event
797  //
798  edm::Handle<View<Track>> trackCollectionHandle;
799  if (!event.getByToken(labelToken[www], trackCollectionHandle) && ignoremissingtkcollection_)
800  continue;
801  const edm::View<Track>& trackCollection = *trackCollectionHandle;
802 
803  reco::SimToRecoCollection const* simRecCollP = nullptr;
804  reco::SimToRecoCollection simRecCollL;
805 
806  //associate tracks
807  LogTrace("TrackValidator") << "Analyzing " << label[www] << " with " << associators[ww] << "\n";
808  if (useAssociators_) {
810  event.getByToken(associatorTokens[ww], theAssociator);
811 
812  // The associator interfaces really need to be fixed...
814  // trackRefs.vectorHolder()->reserve(trackCollection.size()); NOT a good idea
815  for (edm::View<Track>::size_type i = 0; i < trackCollection.size(); ++i) {
816  trackRefs.push_back(trackCollection.refAt(i));
817  }
818 
819  LogTrace("TrackValidator") << "Calling associateRecoToSim method"
820  << "\n";
821  recSimCollL = theAssociator->associateRecoToSim(trackRefs, tPCfake);
822  recSimCollP = &recSimCollL;
823  LogTrace("TrackValidator") << "Calling associateSimToReco method"
824  << "\n";
825  // It is necessary to do the association wrt. fake TPs,
826  // because this SimToReco association is used also for
827  // duplicates. Since the set of efficiency TPs are required to
828  // be a subset of the set of fake TPs, for efficiency
829  // histograms it doesn't matter if the association contains
830  // associations of TPs not in the set of efficiency TPs.
831  simRecCollL = theAssociator->associateSimToReco(trackRefs, tPCfake);
832  simRecCollP = &simRecCollL;
833  } else {
834  // We need to filter the associations of the current track
835  // collection only from SimToReco collection, otherwise the
836  // SimToReco histograms get false entries. The filtering must
837  // be done separately for each track collection.
838  simRecCollL = associationMapFilterValues(*simRecCollPFull, trackCollection);
839  simRecCollP = &simRecCollL;
840  }
841 
842  reco::RecoToSimCollection const& recSimColl = *recSimCollP;
843  reco::SimToRecoCollection const& simRecColl = *simRecCollP;
844 
845  // read MVA collections
849  for (const auto& tokenTpl : mvaQualityCollectionTokens_[www]) {
850  event.getByToken(std::get<0>(tokenTpl), hmva);
851  event.getByToken(std::get<1>(tokenTpl), hqual);
852 
853  mvaCollections.push_back(hmva.product());
854  qualityMaskCollections.push_back(hqual.product());
855  if (mvaCollections.back()->size() != trackCollection.size()) {
856  throw cms::Exception("Configuration")
857  << "Inconsistency in track collection and MVA sizes. Track collection " << www << " has "
858  << trackCollection.size() << " tracks, whereas the MVA " << (mvaCollections.size() - 1)
859  << " for it has " << mvaCollections.back()->size() << " entries. Double-check your configuration.";
860  }
861  if (qualityMaskCollections.back()->size() != trackCollection.size()) {
862  throw cms::Exception("Configuration")
863  << "Inconsistency in track collection and quality mask sizes. Track collection " << www << " has "
864  << trackCollection.size() << " tracks, whereas the quality mask " << (qualityMaskCollections.size() - 1)
865  << " for it has " << qualityMaskCollections.back()->size()
866  << " entries. Double-check your configuration.";
867  }
868  }
869  }
870 
871  // ########################################################
872  // fill simulation histograms (LOOP OVER TRACKINGPARTICLES)
873  // ########################################################
874 
875  //compute number of tracks per eta interval
876  //
877  LogTrace("TrackValidator") << "\n# of TrackingParticles: " << tPCeff.size() << "\n";
878  int st(0); //This counter counts the number of simulated tracks passing the MTV selection (i.e. tpSelector(tp) )
879 
880  //loop over already-selected TPs for tracking efficiency
881  for (size_t i = 0; i < selected_tPCeff.size(); ++i) {
882  size_t iTP = selected_tPCeff[i];
883  const TrackingParticleRef& tpr = tPCeff[iTP];
884  const TrackingParticle& tp = *tpr;
885 
886  auto const& momVert = momVert_tPCeff[i];
887  TrackingParticle::Vector momentumTP;
888  TrackingParticle::Point vertexTP;
889 
890  double dxySim(0);
891  double dzSim(0);
892  double dxyPVSim = 0;
893  double dzPVSim = 0;
894  double dR = dR_tPCeff[iTP];
895  double dR_jet = dR_tPCeff_jet[iTP];
896 
897  //---------- THIS PART HAS TO BE CLEANED UP. THE PARAMETER DEFINER WAS NOT MEANT TO BE USED IN THIS WAY ----------
898  //If the TrackingParticle is collison like, get the momentum and vertex at production state
900  momentumTP = tp.momentum();
901  vertexTP = tp.vertex();
902  //Calcualte the impact parameters w.r.t. PCA
903  const TrackingParticle::Vector& momentum = std::get<TrackingParticle::Vector>(momVert);
904  const TrackingParticle::Point& vertex = std::get<TrackingParticle::Point>(momVert);
905  dxySim = TrackingParticleIP::dxy(vertex, momentum, bs.position());
906  dzSim = TrackingParticleIP::dz(vertex, momentum, bs.position());
907 
908  if (theSimPVPosition) {
909  dxyPVSim = TrackingParticleIP::dxy(vertex, momentum, *theSimPVPosition);
910  dzPVSim = TrackingParticleIP::dz(vertex, momentum, *theSimPVPosition);
911  }
912  }
913  //If the TrackingParticle is comics, get the momentum and vertex at PCA
914  else {
915  momentumTP = std::get<TrackingParticle::Vector>(momVert);
916  vertexTP = std::get<TrackingParticle::Point>(momVert);
917  dxySim = TrackingParticleIP::dxy(vertexTP, momentumTP, bs.position());
918  dzSim = TrackingParticleIP::dz(vertexTP, momentumTP, bs.position());
919 
920  // Do dxy and dz vs. PV make any sense for cosmics? I guess not
921  }
922  //---------- THE PART ABOVE HAS TO BE CLEANED UP. THE PARAMETER DEFINER WAS NOT MEANT TO BE USED IN THIS WAY ----------
923 
924  // in the coming lines, histos are filled using as input
925  // - momentumTP
926  // - vertexTP
927  // - dxySim
928  // - dzSim
929  if (!doSimTrackPlots_)
930  continue;
931 
932  // ##############################################
933  // fill RecoAssociated SimTracks' histograms
934  // ##############################################
935  const reco::Track* matchedTrackPointer = nullptr;
936  const reco::Track* matchedSecondTrackPointer = nullptr;
937  unsigned int selectsLoose = mvaCollections.size();
938  unsigned int selectsHP = mvaCollections.size();
939  if (simRecColl.find(tpr) != simRecColl.end()) {
940  auto const& rt = simRecColl[tpr];
941  if (!rt.empty()) {
942  // isRecoMatched = true; // UNUSED
943  matchedTrackPointer = rt.begin()->first.get();
944  if (rt.size() >= 2) {
945  matchedSecondTrackPointer = (rt.begin() + 1)->first.get();
946  }
947  LogTrace("TrackValidator") << "TrackingParticle #" << st << " with pt=" << sqrt(momentumTP.perp2())
948  << " associated with quality:" << rt.begin()->second << "\n";
949 
950  if (doMVAPlots_) {
951  // for each MVA we need to take the value of the track
952  // with largest MVA value (for the cumulative histograms)
953  //
954  // also identify the first MVA that possibly selects any
955  // track matched to this TrackingParticle, separately
956  // for loose and highPurity qualities
957  for (size_t imva = 0; imva < mvaCollections.size(); ++imva) {
958  const auto& mva = *(mvaCollections[imva]);
959  const auto& qual = *(qualityMaskCollections[imva]);
960 
961  auto iMatch = rt.begin();
962  float maxMva = mva[iMatch->first.key()];
963  for (; iMatch != rt.end(); ++iMatch) {
964  auto itrk = iMatch->first.key();
965  maxMva = std::max(maxMva, mva[itrk]);
966 
967  if (selectsLoose >= imva && trackSelected(qual[itrk], reco::TrackBase::loose))
968  selectsLoose = imva;
969  if (selectsHP >= imva && trackSelected(qual[itrk], reco::TrackBase::highPurity))
970  selectsHP = imva;
971  }
972  mvaValues.push_back(maxMva);
973  }
974  }
975  }
976  } else {
977  LogTrace("TrackValidator") << "TrackingParticle #" << st << " with pt,eta,phi: " << sqrt(momentumTP.perp2())
978  << " , " << momentumTP.eta() << " , " << momentumTP.phi() << " , "
979  << " NOT associated to any reco::Track"
980  << "\n";
981  }
982 
983  int nSimHits = tp.numberOfTrackerHits();
984  int nSimLayers = nLayers_tPCeff[tpr];
985  int nSimPixelLayers = nPixelLayers_tPCeff[tpr];
986  int nSimStripMonoAndStereoLayers = nStripMonoAndStereoLayers_tPCeff[tpr];
987  histoProducerAlgo_->fill_recoAssociated_simTrack_histos(histograms.histoProducerAlgo,
988  w,
989  tp,
990  momentumTP,
991  vertexTP,
992  dxySim,
993  dzSim,
994  dxyPVSim,
995  dzPVSim,
996  nSimHits,
997  nSimLayers,
998  nSimPixelLayers,
999  nSimStripMonoAndStereoLayers,
1000  matchedTrackPointer,
1001  puinfo.getPU_NumInteractions(),
1002  dR,
1003  dR_jet,
1004  thePVposition,
1005  theSimPVPosition,
1006  bs.position(),
1007  mvaValues,
1008  selectsLoose,
1009  selectsHP);
1010  mvaValues.clear();
1011 
1012  if (matchedTrackPointer && matchedSecondTrackPointer) {
1013  histoProducerAlgo_->fill_duplicate_histos(
1014  histograms.histoProducerAlgo, w, *matchedTrackPointer, *matchedSecondTrackPointer);
1015  }
1016 
1017  if (doSummaryPlots_) {
1018  if (dRtpSelector(tp)) {
1019  histograms.h_simul_coll[ww]->Fill(www);
1020  if (matchedTrackPointer) {
1021  histograms.h_assoc_coll[ww]->Fill(www);
1022  }
1023  }
1024  }
1025 
1026  } // End for (TrackingParticleCollection::size_type i=0; i<tPCeff.size(); i++){
1027 
1028  // ##############################################
1029  // fill recoTracks histograms (LOOP OVER TRACKS)
1030  // ##############################################
1031  if (!doRecoTrackPlots_)
1032  continue;
1033  LogTrace("TrackValidator") << "\n# of reco::Tracks with " << label[www].process() << ":" << label[www].label()
1034  << ":" << label[www].instance() << ": " << trackCollection.size() << "\n";
1035 
1036  int at(0); //This counter counts the number of recoTracks that are associated to SimTracks
1037  int rT(0); //This counter counts the number of recoTracks in general
1038  int seed_fit_failed = 0;
1039  size_t n_selTrack_dr = 0;
1040 
1041  //calculate dR for tracks
1042  declareDynArray(float, trackCollection.size(), dR_trk);
1043  declareDynArray(float, trackCollection.size(), dR_trk_jet);
1044 #ifndef NO_TRACK_DR
1045  // this accounts for most of the time spent in MTV and it is used to fill just one histo that is of doubtful usefulness but (maybe) for the whole collection
1046  const edm::View<Track>* trackCollectionDr = &trackCollection;
1048  trackCollectionDr = trackCollectionForDrCalculation.product();
1049  }
1050  trackDR(trackCollection, *trackCollectionDr, dR_trk, dR_trk_jet, coresVector);
1051 #endif
1052 
1053  for (View<Track>::size_type i = 0; i < trackCollection.size(); ++i) {
1054  auto track = trackCollection.refAt(i);
1055  rT++;
1057  ++seed_fit_failed;
1058  if ((*dRTrackSelector)(*track, bs.position()))
1059  ++n_selTrack_dr;
1060 
1061  bool isSigSimMatched(false);
1062  bool isSimMatched(false);
1063  bool isChargeMatched(true);
1064  int numAssocRecoTracks = 0;
1065  int nSimHits = 0;
1066  double sharedFraction = 0.;
1067 
1068  auto tpFound = recSimColl.find(track);
1069  isSimMatched = tpFound != recSimColl.end();
1070  if (applyTPSelToSimMatch_ && isSimMatched)
1071  isSimMatched = tpSelector(*tpFound->val[0].first);
1072  if (isSimMatched) {
1073  const auto& tp = tpFound->val;
1074  nSimHits = tp[0].first->numberOfTrackerHits();
1075  sharedFraction = tp[0].second;
1076  if (tp[0].first->charge() != track->charge())
1077  isChargeMatched = false;
1078  if (simRecColl.find(tp[0].first) != simRecColl.end())
1079  numAssocRecoTracks = simRecColl[tp[0].first].size();
1080  at++;
1081  for (unsigned int tp_ite = 0; tp_ite < tp.size(); ++tp_ite) {
1082  TrackingParticle trackpart = *(tp[tp_ite].first);
1083  if ((trackpart.eventId().event() == 0) && (trackpart.eventId().bunchCrossing() == 0)) {
1084  isSigSimMatched = true;
1085  break;
1086  }
1087  }
1088  LogTrace("TrackValidator") << "reco::Track #" << rT << " with pt=" << track->pt()
1089  << " associated with quality:" << tp.begin()->second << "\n";
1090  } else {
1091  LogTrace("TrackValidator") << "reco::Track #" << rT << " with pt=" << track->pt()
1092  << " NOT associated to any TrackingParticle"
1093  << "\n";
1094  }
1095 
1096  // set MVA values for this track
1097  // take also the indices of first MVAs to select by loose and
1098  // HP quality
1099  unsigned int selectsLoose = mvaCollections.size();
1100  unsigned int selectsHP = mvaCollections.size();
1101  if (doMVAPlots_) {
1102  for (size_t imva = 0; imva < mvaCollections.size(); ++imva) {
1103  const auto& mva = *(mvaCollections[imva]);
1104  const auto& qual = *(qualityMaskCollections[imva]);
1105  mvaValues.push_back(mva[i]);
1106 
1107  if (selectsLoose >= imva && trackSelected(qual[i], reco::TrackBase::loose))
1108  selectsLoose = imva;
1109  if (selectsHP >= imva && trackSelected(qual[i], reco::TrackBase::highPurity))
1110  selectsHP = imva;
1111  }
1112  }
1113 
1114  double dR = dR_trk[i];
1115  double dR_jet = dR_trk_jet[i];
1116  histoProducerAlgo_->fill_generic_recoTrack_histos(histograms.histoProducerAlgo,
1117  w,
1118  *track,
1119  ttopo,
1120  bs.position(),
1121  thePVposition,
1122  theSimPVPosition,
1123  isSimMatched,
1124  isSigSimMatched,
1125  isChargeMatched,
1126  numAssocRecoTracks,
1127  puinfo.getPU_NumInteractions(),
1128  nSimHits,
1129  sharedFraction,
1130  dR,
1131  dR_jet,
1132  mvaValues,
1133  selectsLoose,
1134  selectsHP);
1135  mvaValues.clear();
1136 
1137  if (doSummaryPlots_) {
1138  histograms.h_reco_coll[ww]->Fill(www);
1139  if (isSimMatched) {
1140  histograms.h_assoc2_coll[ww]->Fill(www);
1141  if (numAssocRecoTracks > 1) {
1142  histograms.h_looper_coll[ww]->Fill(www);
1143  }
1144  if (!isSigSimMatched) {
1145  histograms.h_pileup_coll[ww]->Fill(www);
1146  }
1147  }
1148  }
1149 
1150  // dE/dx
1151  if (dodEdxPlots_)
1152  histoProducerAlgo_->fill_dedx_recoTrack_histos(histograms.histoProducerAlgo, w, track, v_dEdx);
1153 
1154  //Fill other histos
1155  if (!isSimMatched)
1156  continue;
1157 
1158  histoProducerAlgo_->fill_simAssociated_recoTrack_histos(histograms.histoProducerAlgo, w, *track);
1159 
1160  /* TO BE FIXED LATER
1161  if (associators[ww]=="trackAssociatorByChi2"){
1162  //association chi2
1163  double assocChi2 = -tp.begin()->second;//in association map is stored -chi2
1164  h_assochi2[www]->Fill(assocChi2);
1165  h_assochi2_prob[www]->Fill(TMath::Prob((assocChi2)*5,5));
1166  }
1167  else if (associators[ww]=="quickTrackAssociatorByHits"){
1168  double fraction = tp.begin()->second;
1169  h_assocFraction[www]->Fill(fraction);
1170  h_assocSharedHit[www]->Fill(fraction*track->numberOfValidHits());
1171  }
1172  */
1173 
1174  if (doResolutionPlots_[www]) {
1175  //Get tracking particle parameters at point of closest approach to the beamline
1176  TrackingParticleRef tpr = tpFound->val.begin()->first;
1177  TrackingParticle::Vector momentumTP = parametersDefinerTP_->momentum(event, setup, tpr);
1178  TrackingParticle::Point vertexTP = parametersDefinerTP_->vertex(event, setup, tpr);
1179  int chargeTP = tpr->charge();
1180 
1181  histoProducerAlgo_->fill_ResoAndPull_recoTrack_histos(
1182  histograms.histoProducerAlgo, w, momentumTP, vertexTP, chargeTP, *track, bs.position());
1183  }
1184 
1185  //TO BE FIXED
1186  //std::vector<PSimHit> simhits=tpr.get()->trackPSimHit(DetId::Tracker);
1187  //nrecHit_vs_nsimHit_rec2sim[w]->Fill(track->numberOfValidHits(), (int)(simhits.end()-simhits.begin() ));
1188 
1189  } // End of for(View<Track>::size_type i=0; i<trackCollection.size(); ++i){
1190  mvaCollections.clear();
1191  qualityMaskCollections.clear();
1192 
1193  histoProducerAlgo_->fill_trackBased_histos(histograms.histoProducerAlgo, w, at, rT, n_selTrack_dr, n_selTP_dr);
1194  // Fill seed-specific histograms
1195  if (doSeedPlots_) {
1196  histoProducerAlgo_->fill_seed_histos(
1197  histograms.histoProducerAlgo, www, seed_fit_failed, trackCollection.size());
1198  }
1199 
1200  LogTrace("TrackValidator") << "Collection " << www << "\n"
1201  << "Total Simulated (selected): " << n_selTP_dr << "\n"
1202  << "Total Reconstructed (selected): " << n_selTrack_dr << "\n"
1203  << "Total Reconstructed: " << rT << "\n"
1204  << "Total Associated (recoToSim): " << at << "\n"
1205  << "Total Fakes: " << rT - at << "\n";
1206  } // End of for (unsigned int www=0;www<label.size();www++){
1207  } //END of for (unsigned int ww=0;ww<associators.size();ww++){
1208 }
reco::SimToRecoCollection associateSimToReco(const edm::Handle< edm::View< reco::Track >> &tCH, const edm::Handle< TrackingParticleCollection > &tPCH) const
size
Write out results.
const edm::ESGetToken< TrackerTopology, TrackerTopologyRcd > tTopoEsToken
unsigned int size_type
Definition: View.h:92
bool empty() const
Is the RefVector empty.
Definition: RefVector.h:99
ESGetTokenH3DDVariant esConsumes(std::string const &Record, edm::ConsumesCollector &)
Definition: DeDxTools.cc:283
T getParameter(std::string const &) const
Definition: ParameterSet.h:307
EncodedEventId eventId() const
Signal source, crossing number.
edm::EDGetTokenT< SimHitTPAssociationProducer::SimHitTPAssociationList > _simHitTpMapTag
edm::EDGetTokenT< edm::ValueMap< reco::DeDxData > > m_dEdx2Tag
int event() const
get the contents of the subdetector field (should be protected?)
bool trackFromSeedFitFailed(const reco::Track &track)
std::vector< edm::EDGetTokenT< reco::SimToRecoCollection > > associatormapStRs
reco::RecoToSimCollection associateRecoToSim(const edm::Handle< edm::View< reco::Track >> &tCH, const edm::Handle< TrackingParticleCollection > &tPCH) const
CosmicTrackingParticleSelector cosmictpSelector
virtual void setCurrentFolder(std::string const &fullpath)
Definition: DQMStore.cc:36
bool empty() const
T w() const
T const * product() const
Definition: Handle.h:70
std::vector< std::vector< std::tuple< edm::EDGetTokenT< MVACollection >, edm::EDGetTokenT< QualityMaskCollection > > > > mvaQualityCollectionTokens_
constexpr bool isUninitialized() const noexcept
Definition: EDGetToken.h:98
edm::EDGetTokenT< edm::ValueMap< unsigned int > > tpNStripStereoLayersToken_
def replace(string, replacements)
edm::EDGetTokenT< edm::ValueMap< unsigned int > > tpNLayersToken_
void trackDR(const edm::View< reco::Track > &trackCollection, const edm::View< reco::Track > &trackCollectionDr, DynArray< float > &dR_trk, DynArray< float > &dR_trk_jet, const edm::View< reco::Candidate > *cores) const
bool has(unsigned int index) const
Check if an element (=index) is in the set.
Definition: IndexSet.h:54
T_AssociationMap associationMapFilterValues(const T_AssociationMap &map, const T_RefVector &valueRefs)
TrackingParticleSelector dRtpSelector
std::string const & label() const
Definition: InputTag.h:36
auto vector_transform(std::vector< InputType > const &input, Function predicate) -> std::vector< typename std::remove_cv< typename std::remove_reference< decltype(predicate(input.front()))>::type >::type >
Definition: transform.h:11
void find(edm::Handle< EcalRecHitCollection > &hits, DetId thisDet, std::vector< EcalRecHitCollection::const_iterator > &hit, bool debug=false)
Definition: FindCaloHit.cc:19
std::vector< edm::EDGetTokenT< reco::TrackToTrackingParticleAssociator > > associatorTokens
const bool doPlotsOnlyForTruePV_
edm::EDGetTokenT< reco::BeamSpot > bsSrc
const_iterator find(const key_type &k) const
find element with specified reference key
#define LogTrace(id)
size_type size() const
EDGetTokenT< ProductType > consumes(edm::InputTag const &tag)
const_iterator end() const
last iterator over the map (read only)
~MultiTrackValidator() override
Destructor.
math::XYZPointD Point
point in the space
edm::EDGetTokenT< edm::ValueMap< unsigned int > > tpNPixelLayersToken_
math::XYZTLorentzVectorD LorentzVector
std::vector< edm::InputTag > associators
char const * label
void bookHistograms(DQMStore::IBooker &, edm::Run const &, edm::EventSetup const &, Histograms &) const override
Method called to book the DQM histograms.
ProductID id() const
Accessor for product ID.
Definition: RefVector.h:117
std::vector< edm::EDGetTokenT< edm::View< reco::Track > > > labelToken
edm::EDGetTokenT< edm::ValueMap< reco::DeDxData > > m_dEdx1Tag
const reco::Vertex::Point * getRecoPVPosition(const edm::Event &event, const edm::Handle< TrackingVertexCollection > &htv) const
std::vector< edm::EDGetTokenT< reco::RecoToSimCollection > > associatormapRtSs
void tpParametersAndSelection(const Histograms &histograms, const TrackingParticleRefVector &tPCeff, const edm::Event &event, const edm::EventSetup &setup, const reco::BeamSpot &bs, std::vector< std::tuple< TrackingParticle::Vector, TrackingParticle::Point >> &momVert_tPCeff, std::vector< size_t > &selected_tPCeff) const
auto dz(const T_Vertex &vertex, const T_Momentum &momentum, const T_Point &point)
ConsumesCollector consumesCollector()
Use a ConsumesCollector to gather consumes information from helper functions.
const EncodedEventId & eventId() const
T sqrt(T t)
Definition: SSEVec.h:23
int bunchCrossing() const
get the detector field from this detid
TrackingParticleSelector tpSelector
std::vector< bool > doResolutionPlots_
Abs< T >::type abs(const T &t)
Definition: Abs.h:22
edm::EDGetTokenT< edm::View< reco::Track > > labelTokenForDrCalculation
math::XYZPoint Point
point in the space
Definition: Vertex.h:40
edm::EDGetTokenT< std::vector< PileupSummaryInfo > > label_pileupinfo
std::vector< edm::InputTag > label
std::unique_ptr< ParametersDefinerForTP > parametersDefinerTP_
void reserve(size_type n)
Reserve space for RefVector.
Definition: RefVector.h:108
trackCollection
Definition: JetHT_cfg.py:51
MultiTrackValidator(const edm::ParameterSet &pset)
Constructor.
ObjectSelector< CosmicTrackingParticleSelector > CosmicTrackingParticleSelector
edm::EDGetTokenT< TrackingParticleRefVector > label_tp_fake_refvector
std::unique_ptr< MTVHistoProducerAlgoForTracker > histoProducerAlgo_
const bool applyTPSelToSimMatch_
constexpr auto deltaR2(const T1 &t1, const T2 &t2) -> decltype(t1.eta())
Definition: deltaR.h:16
size_type size() const
Size of the RefVector.
Definition: RefVector.h:102
edm::EDGetTokenT< TrackingVertexCollection > label_tv
edm::EDGetTokenT< reco::VertexToTrackingVertexAssociator > vertexAssociatorToken_
std::unique_ptr< RecoTrackSelectorBase > dRTrackSelector
edm::Ref< edm::HepMCProduct, HepMC::GenParticle > GenParticleRef
const bool ignoremissingtkcollection_
const bool doPVAssociationPlots_
edm::EDGetTokenT< edm::View< reco::Vertex > > recoVertexToken_
std::vector< edm::EDGetTokenT< std::vector< PSimHit > > > simHitTokens_
const bool calculateDrSingleCollection_
fixed size matrix
HLT enums.
auto dxy(const T_Vertex &vertex, const T_Momentum &momentum, const T_Point &point)
void push_back(const RefToBase< T > &)
void push_back(value_type const &ref)
Add a Ref<C, T> to the RefVector.
Definition: RefVector.h:67
edm::EDGetTokenT< TrackingParticleCollection > label_tp_fake
void initEvent(edm::Handle< SimHitTPAssociationProducer::SimHitTPAssociationList > simHitsTPAssocToSet) const
Monte Carlo truth information used for tracking validation.
void insert(unsigned int index)
Insert an element (=index) to the set.
Definition: IndexSet.h:47
#define declareDynArray(T, n, x)
Definition: DynArray.h:91
reco::VertexRecoToSimCollection associateRecoToSim(const edm::Handle< edm::View< reco::Vertex >> &vCH, const edm::Handle< TrackingVertexCollection > &tVCH) const
edm::EDGetTokenT< edm::View< reco::Candidate > > cores_
size_t tpDR(const TrackingParticleRefVector &tPCeff, const std::vector< size_t > &selected_tPCeff, DynArray< float > &dR_tPCeff, DynArray< float > &dR_tPCeff_jet, const edm::View< reco::Candidate > *cores) const
const TrackingVertex::LorentzVector * getSimPVPosition(const edm::Handle< TrackingVertexCollection > &htv) const
math::XYZVectorD Vector
point in the space
MonitorElement * book1D(TString const &name, TString const &title, int const nchX, double const lowX, double const highX, FUNC onbooking=NOOP())
Definition: DQMStore.h:98
edm::EDGetTokenT< TrackingParticleRefVector > label_tp_effic_refvector
doResolutionPlotsForLabels
do resolution plots only for these labels (or all if empty)
static std::unique_ptr< RecoTrackSelectorBase > makeRecoTrackSelectorFromTPSelectorParameters(const edm::ParameterSet &pset)
void dqmAnalyze(const edm::Event &, const edm::EventSetup &, const Histograms &) const override
Method called once per event.
void reserve(unsigned int size)
Reserve memory for the set.
Definition: IndexSet.h:34
SingleObjectSelector< TrackingParticleCollection, ::TrackingParticleSelector > TrackingParticleSelector
edm::EDGetTokenT< TrackingParticleCollection > label_tp_effic
const int getPU_NumInteractions() const
edm::Ref< TrackingParticleCollection > TrackingParticleRef
Definition: event.py:1
Definition: Run.h:45
void labelsForToken(EDGetToken iToken, Labels &oLabels) const
#define LogDebug(id)
const bool parametersDefinerIsCosmic_