CMS 3D CMS Logo

TrackerOfflineValidationSummary.cc
Go to the documentation of this file.
1 // -*- C++ -*-
2 //
3 // Package: TrackerOfflineValidationSummary
4 // Class: TrackerOfflineValidationSummary
5 //
13 //
14 // Original Author: Johannes Hauk
15 // Created: Sat Aug 22 10:31:34 CEST 2009
16 // $Id: TrackerOfflineValidationSummary.cc,v 1.7 2012/06/30 09:09:47 eulisse Exp $
17 //
18 //
19 
20 // system include files
21 #include <memory>
22 
23 // user include files
26 
29 
31 
36 
37 #include "TTree.h"
38 //#include "Alignment/OfflineValidation/interface/TrackerValidationVariables.h"
40 
48 #include "TH1.h"
49 #include "TMath.h"
50 
53 
54 //
55 // class decleration
56 //
57 
58 class TrackerOfflineValidationSummary : public edm::one::EDAnalyzer<edm::one::WatchRuns> {
59 public:
63 
64 private:
67 
68  struct ModuleHistos {
71  TH1* ResHisto;
77  };
78 
82  TH1* DmrXprime;
83  TH1* DmrYprime;
84  };
85 
88  HarvestingHierarchy(const std::string& name, const std::string& component, const std::vector<unsigned int>& entries)
89  : hierarchyName(name), componentName(component), treeEntries(entries) {}
90  // Needed for naming of histogram according to residual histograms
92  // "Pixel" or "Strip"
94  // Modules belonging to selected hierarchy
95  std::vector<unsigned int> treeEntries;
97  };
98 
99  void beginRun(const edm::Run&, const edm::EventSetup& iSetup) override{};
100  void analyze(const edm::Event& evt, const edm::EventSetup&) override;
101  void endRun(const edm::Run&, const edm::EventSetup& iSetup) override;
102  void endJob() override;
103 
104  void fillTree(TTree& tree,
105  std::map<int, TrackerOfflineValidationSummary::ModuleHistos>& moduleHist,
106  TkOffTreeVariables& treeMem,
107  const TrackerGeometry& tkgeom,
108  std::map<std::string, std::string>& substructureName,
109  const TrackerTopology* tTopo);
110 
111  std::pair<float, float> fitResiduals(TH1* hist) const;
112  float getMedian(const TH1* hist) const;
113 
116  std::map<std::string, std::string>& substructureName);
117 
118  void collateHarvestingHists(TTree& tree);
119  void applyHarvestingHierarchy(TTree& treeMem);
120  void bookHarvestingHists();
121  void getBinning(const std::string& binningPSetName, int& nBinsX, double& lowerBoundX, double& upperBoundX) const;
122  void fillHarvestingHists(TTree& tree);
123 
124  // ----------member data ---------------------------
125 
128  std::unique_ptr<TrackerTopology> tTopo_;
129 
130  // parameters from cfg to steer
132  const bool useFit_;
133 
135 
137 
138  std::map<int, TrackerOfflineValidationSummary::ModuleHistos> mPxbResiduals_;
139  std::map<int, TrackerOfflineValidationSummary::ModuleHistos> mPxeResiduals_;
140  std::map<int, TrackerOfflineValidationSummary::ModuleHistos> mTibResiduals_;
141  std::map<int, TrackerOfflineValidationSummary::ModuleHistos> mTidResiduals_;
142  std::map<int, TrackerOfflineValidationSummary::ModuleHistos> mTobResiduals_;
143  std::map<int, TrackerOfflineValidationSummary::ModuleHistos> mTecResiduals_;
144 
145  std::vector<HarvestingHierarchy> vHarvestingHierarchy_;
146 };
147 
148 //
149 // constructors and destructor
150 //
152  : geomToken_(esConsumes()),
153  tTopoToken_(esConsumes<edm::Transition::EndRun>()),
154  parSet_(iConfig),
155  tTopo_(nullptr),
156  moduleDirectory_(parSet_.getParameter<std::string>("moduleDirectoryInOutput")),
157  useFit_(parSet_.getParameter<bool>("useFit")),
158  dbe_(nullptr),
159  moduleMapsInitialized(false) {
160  //now do what ever initialization is needed
162 }
163 
165 //
166 // member functions
167 //
168 
169 // ------------ method called to for each event ------------
171  // Access of EventSetup is needed to get the list of silicon-modules and their IDs
172  // Since they do not change, it is accessed only once
174  return;
175  tkGeom_ = iSetup.getHandle(geomToken_);
176  const TrackerGeometry* bareTkGeomPtr = &(*tkGeom_);
177 
178  const TrackingGeometry::DetIdContainer& detIdContainer = bareTkGeomPtr->detIds();
179  std::vector<DetId>::const_iterator iDet;
180  for (iDet = detIdContainer.begin(); iDet != detIdContainer.end(); ++iDet) {
181  const DetId& detId = *iDet;
182  const uint32_t rawId = detId.rawId();
183  const unsigned int subdetId = detId.subdetId();
184  if (subdetId == PixelSubdetector::PixelBarrel)
185  mPxbResiduals_[rawId];
186  else if (subdetId == PixelSubdetector::PixelEndcap)
187  mPxeResiduals_[rawId];
188  else if (subdetId == StripSubdetector::TIB)
189  mTibResiduals_[rawId];
190  else if (subdetId == StripSubdetector::TID)
191  mTidResiduals_[rawId];
192  else if (subdetId == StripSubdetector::TOB)
193  mTobResiduals_[rawId];
194  else if (subdetId == StripSubdetector::TEC)
195  mTecResiduals_[rawId];
196  else {
197  throw cms::Exception("Geometry Error")
198  << "[TrackerOfflineValidationSummary] Error, tried to get reference for non-tracker subdet " << subdetId
199  << " from detector " << detId.det();
200  }
201  }
202  moduleMapsInitialized = true;
203 }
204 
205 // ------------ method called at each end of Run ------------
207  if (!tTopo_) {
208  tTopo_ = std::make_unique<TrackerTopology>(iSetup.getData(tTopoToken_));
209  }
210 }
211 
212 // ------------ method called once each job just after ending the event loop ------------
214  AlignableTracker aliTracker(&(*tkGeom_), tTopo_.get());
215 
216  TTree* tree = new TTree("TkOffVal", "TkOffVal");
217 
218  TkOffTreeVariables* treeMemPtr = new TkOffTreeVariables;
219  // We create branches for all members of 'TkOffTreeVariables' (even if not needed).
220  // This works because we have a dictionary for 'TkOffTreeVariables'
221  // (see src/classes_def.xml and src/classes.h):
222  tree->Branch("TkOffTreeVariables", &treeMemPtr); // address of pointer!
223  // second branch needed for assigning names and titles to harvesting histograms consistent to others
224  std::map<std::string, std::string>* substructureName = new std::map<std::string, std::string>;
225  tree->Branch("SubstructureName", &substructureName, 32000, 00); // SplitLevel must be set to zero
226 
227  this->fillTree(*tree, mPxbResiduals_, *treeMemPtr, *tkGeom_, *substructureName, tTopo_.get());
228  this->fillTree(*tree, mPxeResiduals_, *treeMemPtr, *tkGeom_, *substructureName, tTopo_.get());
229  this->fillTree(*tree, mTibResiduals_, *treeMemPtr, *tkGeom_, *substructureName, tTopo_.get());
230  this->fillTree(*tree, mTidResiduals_, *treeMemPtr, *tkGeom_, *substructureName, tTopo_.get());
231  this->fillTree(*tree, mTobResiduals_, *treeMemPtr, *tkGeom_, *substructureName, tTopo_.get());
232  this->fillTree(*tree, mTecResiduals_, *treeMemPtr, *tkGeom_, *substructureName, tTopo_.get());
233 
234  //dbe_->save("dqmOut.root");
235 
236  // Method for filling histograms which show summarized values (mean, rms, median ...)
237  // of the module-based histograms from TrackerOfflineValidation
238  this->collateHarvestingHists(*tree);
239 
240  delete tree;
241  tree = nullptr;
242  delete treeMemPtr;
243  treeMemPtr = nullptr;
244  delete substructureName;
245  substructureName = nullptr;
246 }
247 
249  std::map<int, TrackerOfflineValidationSummary::ModuleHistos>& moduleHist,
250  TkOffTreeVariables& treeMem,
251  const TrackerGeometry& tkgeom,
252  std::map<std::string, std::string>& substructureName,
253  const TrackerTopology* tTopo) {
254  for (std::map<int, TrackerOfflineValidationSummary::ModuleHistos>::iterator it = moduleHist.begin(),
255  itEnd = moduleHist.end();
256  it != itEnd;
257  ++it) {
258  treeMem.clear(); // make empty/default
259 
260  //variables concerning the tracker components/hierarchy levels
261  const DetId detId = it->first;
262  treeMem.moduleId = detId;
263  treeMem.subDetId = detId.subdetId();
264 
265  if (treeMem.subDetId == PixelSubdetector::PixelBarrel) {
266  unsigned int whichHalfBarrel(1), rawId(detId.rawId()); //DetId does not know about halfBarrels is PXB ...
267  if ((rawId >= 302056964 && rawId < 302059300) || (rawId >= 302123268 && rawId < 302127140) ||
268  (rawId >= 302189572 && rawId < 302194980))
269  whichHalfBarrel = 2;
270  treeMem.layer = tTopo->pxbLayer(detId);
271  treeMem.half = whichHalfBarrel;
272  treeMem.rod = tTopo->pxbLadder(
273  detId); // ... so, ladder is not per halfBarrel-Layer, but per barrel-layer! Needs complicated calculation in associateModuleHistsWithTree()
274  treeMem.module = tTopo->pxbModule(detId);
275  } else if (treeMem.subDetId == PixelSubdetector::PixelEndcap) {
276  unsigned int whichHalfCylinder(1), rawId(detId.rawId()); //DetId does not kmow about halfCylinders in PXF
277  if ((rawId >= 352394500 && rawId < 352406032) || (rawId >= 352460036 && rawId < 352471568) ||
278  (rawId >= 344005892 && rawId < 344017424) || (rawId >= 344071428 && rawId < 344082960))
279  whichHalfCylinder = 2;
280  treeMem.layer = tTopo->pxfDisk(detId);
281  treeMem.side = tTopo->pxfSide(detId);
282  treeMem.half = whichHalfCylinder;
283  treeMem.blade = tTopo->pxfBlade(detId);
284  treeMem.panel = tTopo->pxfPanel(detId);
285  treeMem.module = tTopo->pxfModule(detId);
286  } else if (treeMem.subDetId == StripSubdetector::TIB) {
287  unsigned int whichHalfShell(1), rawId(detId.rawId()); //DetId does not kmow about halfShells in TIB
288  if ((rawId >= 369120484 && rawId < 369120688) || (rawId >= 369121540 && rawId < 369121776) ||
289  (rawId >= 369136932 && rawId < 369137200) || (rawId >= 369137988 && rawId < 369138288) ||
290  (rawId >= 369153396 && rawId < 369153744) || (rawId >= 369154436 && rawId < 369154800) ||
291  (rawId >= 369169844 && rawId < 369170256) || (rawId >= 369170900 && rawId < 369171344) ||
292  (rawId >= 369124580 && rawId < 369124784) || (rawId >= 369125636 && rawId < 369125872) ||
293  (rawId >= 369141028 && rawId < 369141296) || (rawId >= 369142084 && rawId < 369142384) ||
294  (rawId >= 369157492 && rawId < 369157840) || (rawId >= 369158532 && rawId < 369158896) ||
295  (rawId >= 369173940 && rawId < 369174352) || (rawId >= 369174996 && rawId < 369175440))
296  whichHalfShell = 2;
297  treeMem.layer = tTopo->tibLayer(detId);
298  treeMem.side = tTopo->tibStringInfo(detId)[0];
299  treeMem.half = whichHalfShell;
300  treeMem.rod = tTopo->tibStringInfo(detId)[2];
301  treeMem.outerInner = tTopo->tibStringInfo(detId)[1];
302  treeMem.module = tTopo->tibModule(detId);
303  treeMem.isStereo = tTopo->tibStereo(detId);
304  treeMem.isDoubleSide = tTopo->tibIsDoubleSide(detId);
305  } else if (treeMem.subDetId == StripSubdetector::TID) {
306  treeMem.layer = tTopo->tidWheel(detId);
307  treeMem.side = tTopo->tidSide(detId);
308  treeMem.ring = tTopo->tidRing(detId);
309  treeMem.outerInner = tTopo->tidModuleInfo(detId)[0];
310  treeMem.module = tTopo->tidModuleInfo(detId)[1];
311  treeMem.isStereo = tTopo->tidStereo(detId);
312  treeMem.isDoubleSide = tTopo->tidIsDoubleSide(detId);
313  } else if (treeMem.subDetId == StripSubdetector::TOB) {
314  treeMem.layer = tTopo->tobLayer(detId);
315  treeMem.side = tTopo->tobRodInfo(detId)[0];
316  treeMem.rod = tTopo->tobRodInfo(detId)[1];
317  treeMem.module = tTopo->tobModule(detId);
318  treeMem.isStereo = tTopo->tobStereo(detId);
319  treeMem.isDoubleSide = tTopo->tobIsDoubleSide(detId);
320  } else if (treeMem.subDetId == StripSubdetector::TEC) {
321  treeMem.layer = tTopo->tecWheel(detId);
322  treeMem.side = tTopo->tecSide(detId);
323  treeMem.ring = tTopo->tecRing(detId);
324  treeMem.petal = tTopo->tecPetalInfo(detId)[1];
325  treeMem.outerInner = tTopo->tecPetalInfo(detId)[0];
326  treeMem.module = tTopo->tecModule(detId);
327  treeMem.isStereo = tTopo->tecStereo(detId);
328  treeMem.isDoubleSide = tTopo->tecIsDoubleSide(detId);
329  }
330 
331  //variables concerning the tracker geometry
332 
333  const Surface::PositionType& gPModule = tkgeom.idToDet(detId)->position();
334  treeMem.posPhi = gPModule.phi();
335  treeMem.posEta = gPModule.eta();
336  treeMem.posR = gPModule.perp();
337  treeMem.posX = gPModule.x();
338  treeMem.posY = gPModule.y();
339  treeMem.posZ = gPModule.z();
340 
341  const Surface& surface = tkgeom.idToDet(detId)->surface();
342 
343  //global Orientation of local coordinate system of dets/detUnits
344  LocalPoint lUDirection(1., 0., 0.), lVDirection(0., 1., 0.), lWDirection(0., 0., 1.);
345  GlobalPoint gUDirection = surface.toGlobal(lUDirection), gVDirection = surface.toGlobal(lVDirection),
346  gWDirection = surface.toGlobal(lWDirection);
347  double dR(999.), dPhi(999.), dZ(999.);
349  treeMem.subDetId == StripSubdetector::TOB) {
350  dR = gWDirection.perp() - gPModule.perp();
351  dPhi = deltaPhi(gUDirection.barePhi(), gPModule.barePhi());
352  dZ = gVDirection.z() - gPModule.z();
353  if (dZ >= 0.)
354  treeMem.rOrZDirection = 1;
355  else
356  treeMem.rOrZDirection = -1;
357  } else if (treeMem.subDetId == PixelSubdetector::PixelEndcap) {
358  dR = gUDirection.perp() - gPModule.perp();
359  dPhi = deltaPhi(gVDirection.barePhi(), gPModule.barePhi());
360  dZ = gWDirection.z() - gPModule.z();
361  if (dR >= 0.)
362  treeMem.rOrZDirection = 1;
363  else
364  treeMem.rOrZDirection = -1;
365  } else if (treeMem.subDetId == StripSubdetector::TID || treeMem.subDetId == StripSubdetector::TEC) {
366  dR = gVDirection.perp() - gPModule.perp();
367  dPhi = deltaPhi(gUDirection.barePhi(), gPModule.barePhi());
368  dZ = gWDirection.z() - gPModule.z();
369  if (dR >= 0.)
370  treeMem.rOrZDirection = 1;
371  else
372  treeMem.rOrZDirection = -1;
373  }
374  if (dR >= 0.)
375  treeMem.rDirection = 1;
376  else
377  treeMem.rDirection = -1;
378  if (dPhi >= 0.)
379  treeMem.phiDirection = 1;
380  else
381  treeMem.phiDirection = -1;
382  if (dZ >= 0.)
383  treeMem.zDirection = 1;
384  else
385  treeMem.zDirection = -1;
386 
387  // Assign histos from first step (TrackerOfflineValidation) to the module's entry in the TTree for retrieving mean, rms, median ...
388  const std::string histDir = associateModuleHistsWithTree(treeMem, it->second, substructureName);
389 
390  //mean and RMS values (extracted from histograms Xprime on module level)
391  treeMem.entries = static_cast<UInt_t>(it->second.ResXprimeHisto->GetEntries());
392  treeMem.meanX = it->second.ResXprimeHisto->GetMean();
393  treeMem.rmsX = it->second.ResXprimeHisto->GetRMS();
394  //treeMem.sigmaX = Fwhm(it->second.ResXprimeHisto)/2.355;
395  if (useFit_) {
396  //call fit function which returns mean and sigma from the fit
397  //for absolute residuals
398  std::pair<float, float> fitResult1 = this->fitResiduals(it->second.ResXprimeHisto);
399  treeMem.fitMeanX = fitResult1.first;
400  treeMem.fitSigmaX = fitResult1.second;
401  //for normalized residuals
402  std::pair<float, float> fitResult2 = this->fitResiduals(it->second.NormResXprimeHisto);
403  treeMem.fitMeanNormX = fitResult2.first;
404  treeMem.fitSigmaNormX = fitResult2.second;
405  }
406 
407  //get median for absolute residuals
408  treeMem.medianX = this->getMedian(it->second.ResXprimeHisto);
409 
410  int numberOfBins = it->second.ResXprimeHisto->GetNbinsX();
411  treeMem.numberOfUnderflows = it->second.ResXprimeHisto->GetBinContent(0);
412  treeMem.numberOfOverflows = it->second.ResXprimeHisto->GetBinContent(numberOfBins + 1);
413  treeMem.numberOfOutliers =
414  it->second.ResXprimeHisto->GetBinContent(0) + it->second.ResXprimeHisto->GetBinContent(numberOfBins + 1);
415  //mean and RMS values (extracted from histograms(normalized Xprime on module level)
416  treeMem.meanNormX = it->second.NormResXprimeHisto->GetMean();
417  treeMem.rmsNormX = it->second.NormResXprimeHisto->GetRMS();
418 
419  double stats[20];
420  it->second.NormResXprimeHisto->GetStats(stats);
421  // GF treeMem.chi2PerDofX = stats[3]/(stats[0]-1);
422  if (stats[0])
423  treeMem.chi2PerDofX = stats[3] / stats[0];
424 
425  //treeMem.sigmaNormX = Fwhm(it->second.NormResXprimeHisto)/2.355;
426  treeMem.histNameX = it->second.ResXprimeHisto->GetName();
427  treeMem.histNameNormX = it->second.NormResXprimeHisto->GetName();
428 
429  // fill tree variables in local coordinates if set in cfg of TrackerOfllineValidation
430  if (it->second.ResHisto && it->second.NormResHisto) { // if(lCoorHistOn_) {
431  treeMem.meanLocalX = it->second.ResHisto->GetMean();
432  treeMem.rmsLocalX = it->second.ResHisto->GetRMS();
433  treeMem.meanNormLocalX = it->second.NormResHisto->GetMean();
434  treeMem.rmsNormLocalX = it->second.NormResHisto->GetRMS();
435  treeMem.histNameLocalX = it->second.ResHisto->GetName();
436  treeMem.histNameNormLocalX = it->second.NormResHisto->GetName();
437  }
438 
439  // mean and RMS values in local y (extracted from histograms Yprime on module level)
440  // might exist in pixel only
441  if (it->second.ResYprimeHisto) { //(stripYResiduals_){
442  TH1* h = it->second.ResYprimeHisto;
443  treeMem.meanY = h->GetMean();
444  treeMem.rmsY = h->GetRMS();
445 
446  if (useFit_) { // fit function which returns mean and sigma from the fit
447  std::pair<float, float> fitMeanSigma = this->fitResiduals(h);
448  treeMem.fitMeanY = fitMeanSigma.first;
449  treeMem.fitSigmaY = fitMeanSigma.second;
450  }
451 
452  //get median for absolute residuals
453  treeMem.medianY = this->getMedian(h);
454 
455  treeMem.histNameY = h->GetName();
456  }
457 
458  if (it->second.NormResYprimeHisto) {
459  TH1* h = it->second.NormResYprimeHisto;
460  treeMem.meanNormY = h->GetMean();
461  treeMem.rmsNormY = h->GetRMS();
462  h->GetStats(stats); // stats buffer defined above
463  if (stats[0])
464  treeMem.chi2PerDofY = stats[3] / stats[0];
465 
466  if (useFit_) { // fit function which returns mean and sigma from the fit
467  std::pair<float, float> fitMeanSigma = this->fitResiduals(h);
468  treeMem.fitMeanNormY = fitMeanSigma.first;
469  treeMem.fitSigmaNormY = fitMeanSigma.second;
470  }
471  treeMem.histNameNormY = h->GetName();
472  }
473 
474  tree.Fill();
475  }
476 }
477 
479  const TkOffTreeVariables& treeMem,
481  std::map<std::string, std::string>& substructureName) {
482  std::stringstream histDir, sSubdetName;
483  std::string componentName;
484  if (moduleDirectory_.length() != 0)
485  histDir << moduleDirectory_ << "/";
486  std::string wheelOrLayer("_layer_");
487  if (treeMem.subDetId == PixelSubdetector::PixelBarrel) {
488  unsigned int half(treeMem.half), layer(treeMem.layer), ladder(0);
489  if (layer == 1) {
490  if (half == 2)
491  ladder = treeMem.rod - 5;
492  else if (treeMem.rod > 15)
493  ladder = treeMem.rod - 10;
494  else
495  ladder = treeMem.rod;
496  } else if (layer == 2) {
497  if (half == 2)
498  ladder = treeMem.rod - 8;
499  else if (treeMem.rod > 24)
500  ladder = treeMem.rod - 16;
501  else
502  ladder = treeMem.rod;
503  } else if (layer == 3) {
504  if (half == 2)
505  ladder = treeMem.rod - 11;
506  else if (treeMem.rod > 33)
507  ladder = treeMem.rod - 22;
508  else
509  ladder = treeMem.rod;
510  }
511  componentName = "Pixel";
512  sSubdetName << "TPBBarrel_1";
513  histDir << componentName << "/" << sSubdetName.str() << "/TPBHalfBarrel_" << treeMem.half << "/TPBLayer_"
514  << treeMem.layer << "/TPBLadder_" << ladder;
515  } else if (treeMem.subDetId == PixelSubdetector::PixelEndcap) {
516  unsigned int side(treeMem.side), half(treeMem.half), blade(0);
517  if (side == 1)
518  side = 3;
519  if (half == 2)
520  blade = treeMem.blade - 6;
521  else if (treeMem.blade > 18)
522  blade = treeMem.blade - 12;
523  else
524  blade = treeMem.blade;
525  componentName = "Pixel";
526  sSubdetName << "TPEEndcap_" << side;
527  histDir << componentName << "/" << sSubdetName.str() << "/TPEHalfCylinder_" << treeMem.half << "/TPEHalfDisk_"
528  << treeMem.layer << "/TPEBlade_" << blade << "/TPEPanel_" << treeMem.panel;
529  wheelOrLayer = "_wheel_";
530  } else if (treeMem.subDetId == StripSubdetector::TIB) {
531  unsigned int half(treeMem.half), layer(treeMem.layer), surface(treeMem.outerInner), string(0);
532  if (half == 2) {
533  if (layer == 1) {
534  if (surface == 1)
535  string = treeMem.rod - 13;
536  else if (surface == 2)
537  string = treeMem.rod - 15;
538  }
539  if (layer == 2) {
540  if (surface == 1)
541  string = treeMem.rod - 17;
542  else if (surface == 2)
543  string = treeMem.rod - 19;
544  }
545  if (layer == 3) {
546  if (surface == 1)
547  string = treeMem.rod - 22;
548  else if (surface == 2)
549  string = treeMem.rod - 23;
550  }
551  if (layer == 4) {
552  if (surface == 1)
553  string = treeMem.rod - 26;
554  else if (surface == 2)
555  string = treeMem.rod - 28;
556  }
557  } else
558  string = treeMem.rod;
559  std::stringstream detString;
560  if (treeMem.layer < 3 && !treeMem.isDoubleSide)
561  detString << "/Det_" << treeMem.module;
562  else
563  detString << "";
564  componentName = "Strip";
565  sSubdetName << "TIBBarrel_1";
566  histDir << componentName << "/" << sSubdetName.str() << "/TIBHalfBarrel_" << treeMem.side << "/TIBLayer_"
567  << treeMem.layer << "/TIBHalfShell_" << treeMem.half << "/TIBSurface_" << treeMem.outerInner
568  << "/TIBString_" << string << detString.str();
569  } else if (treeMem.subDetId == StripSubdetector::TID) {
570  unsigned int side(treeMem.side), outerInner(0);
571  if (side == 1)
572  side = 3;
573  if (treeMem.outerInner == 1)
574  outerInner = 2;
575  else if (treeMem.outerInner == 2)
576  outerInner = 1;
577  std::stringstream detString;
578  if (treeMem.ring < 3 && !treeMem.isDoubleSide)
579  detString << "/Det_" << treeMem.module;
580  else
581  detString << "";
582  componentName = "Strip";
583  sSubdetName << "TIDEndcap_" << side;
584  histDir << componentName << "/" << sSubdetName.str() << "/TIDDisk_" << treeMem.layer << "/TIDRing_" << treeMem.ring
585  << "/TIDSide_" << outerInner << detString.str();
586  wheelOrLayer = "_wheel_";
587  } else if (treeMem.subDetId == StripSubdetector::TOB) {
588  std::stringstream detString;
589  if (treeMem.layer < 3 && !treeMem.isDoubleSide)
590  detString << "/Det_" << treeMem.module;
591  else
592  detString << "";
593  componentName = "Strip";
594  sSubdetName << "TOBBarrel_4";
595  histDir << componentName << "/" << sSubdetName.str() << "/TOBHalfBarrel_" << treeMem.side << "/TOBLayer_"
596  << treeMem.layer << "/TOBRod_" << treeMem.rod << detString.str();
597  } else if (treeMem.subDetId == StripSubdetector::TEC) {
598  unsigned int side(0), outerInner(0), ring(0);
599  if (treeMem.side == 1)
600  side = 6;
601  else if (treeMem.side == 2)
602  side = 5;
603  if (treeMem.outerInner == 1)
604  outerInner = 2;
605  else if (treeMem.outerInner == 2)
606  outerInner = 1;
607  if (treeMem.layer > 3 && treeMem.layer < 7)
608  ring = treeMem.ring - 1;
609  else if (treeMem.layer == 7 || treeMem.layer == 8)
610  ring = treeMem.ring - 2;
611  else if (treeMem.layer == 9)
612  ring = treeMem.ring - 3;
613  else
614  ring = treeMem.ring;
615  std::stringstream detString;
616  if ((treeMem.ring < 3 || treeMem.ring == 5) && !treeMem.isDoubleSide)
617  detString << "/Det_" << treeMem.module;
618  else
619  detString << "";
620  componentName = "Strip";
621  sSubdetName << "TECEndcap_" << side;
622  histDir << componentName << "/" << sSubdetName.str() << "/TECDisk_" << treeMem.layer << "/TECSide_" << outerInner
623  << "/TECPetal_" << treeMem.petal << "/TECRing_" << ring << detString.str();
624  wheelOrLayer = "_wheel_";
625  }
626 
627  substructureName["component"] = componentName;
628  substructureName["subdet"] = sSubdetName.str();
629 
630  std::stringstream histName;
631  histName << "residuals_subdet_" << treeMem.subDetId << wheelOrLayer << treeMem.layer << "_module_"
632  << treeMem.moduleId;
633 
635  fullPath = histDir.str() + "/h_xprime_" + histName.str();
636  if (dbe_->get(fullPath))
637  moduleHists.ResXprimeHisto = dbe_->get(fullPath)->getTH1();
638  else {
639  edm::LogError("TrackerOfflineValidationSummary")
640  << "Problem with names in input file produced in TrackerOfflineValidation ...\n"
641  << "This histogram should exist in every configuration, "
642  << "but no histogram with name " << fullPath << " is found!";
643  return "";
644  }
645  fullPath = histDir.str() + "/h_normxprime" + histName.str();
646  if (dbe_->get(fullPath))
647  moduleHists.NormResXprimeHisto = dbe_->get(fullPath)->getTH1();
648  fullPath = histDir.str() + "/h_yprime_" + histName.str();
649  if (dbe_->get(fullPath))
650  moduleHists.ResYprimeHisto = dbe_->get(fullPath)->getTH1();
651  fullPath = histDir.str() + "/h_normyprime" + histName.str();
652  if (dbe_->get(fullPath))
653  moduleHists.NormResYprimeHisto = dbe_->get(fullPath)->getTH1();
654  fullPath = histDir.str() + "/h_" + histName.str();
655  if (dbe_->get(fullPath))
656  moduleHists.ResHisto = dbe_->get(fullPath)->getTH1();
657  fullPath = histDir.str() + "/h_norm" + histName.str();
658  if (dbe_->get(fullPath))
659  moduleHists.NormResHisto = dbe_->get(fullPath)->getTH1();
660 
661  return histDir.str();
662 }
663 
664 std::pair<float, float> TrackerOfflineValidationSummary::fitResiduals(TH1* hist) const {
665  std::pair<float, float> fitResult(9999., 9999.);
666  if (!hist || hist->GetEntries() < 20)
667  return fitResult;
668 
669  float mean = hist->GetMean();
670  float sigma = hist->GetRMS();
671 
672  try { // for < CMSSW_2_2_0 since ROOT warnings from fit are converted to exceptions
673  // Remove the try/catch for more recent CMSSW!
674  // first fit: two RMS around mean
675  TF1 func("tmp", "gaus", mean - 2. * sigma, mean + 2. * sigma);
676  if (0 == hist->Fit(&func, "QNR")) { // N: do not blow up file by storing fit!
677  mean = func.GetParameter(1);
678  sigma = func.GetParameter(2);
679  // second fit: three sigma of first fit around mean of first fit
680  func.SetRange(mean - 3. * sigma, mean + 3. * sigma);
681  // I: integral gives more correct results if binning is too wide
682  // L: Likelihood can treat empty bins correctly (if hist not weighted...)
683  if (0 == hist->Fit(&func, "Q0LR")) {
684  if (hist->GetFunction(func.GetName())) { // Take care that it is later on drawn:
685  hist->GetFunction(func.GetName())->ResetBit(TF1::kNotDraw);
686  }
687  fitResult.first = func.GetParameter(1);
688  fitResult.second = func.GetParameter(2);
689  }
690  }
691  } catch (cms::Exception const& e) {
692  edm::LogWarning("Alignment") << "@SUB=TrackerOfflineValidation::fitResiduals"
693  << "Caught this exception during ROOT fit: " << e.what();
694  }
695  return fitResult;
696 }
697 
699  float median = 999;
700  const int nbins = histo->GetNbinsX();
701 
702  //extract median from histogram
703  double* x = new double[nbins];
704  double* y = new double[nbins];
705  for (int j = 0; j < nbins; j++) {
706  x[j] = histo->GetBinCenter(j + 1);
707  y[j] = histo->GetBinContent(j + 1);
708  }
709  median = TMath::Median(nbins, x, y);
710 
711  delete[] x;
712  x = nullptr;
713  delete[] y;
714  y = nullptr;
715 
716  return median;
717 }
718 
720  this->applyHarvestingHierarchy(tree);
721  this->fillHarvestingHists(tree);
722 }
723 
725  TkOffTreeVariables* treeMemPtr = nullptr;
726  std::map<std::string, std::string>* substructureName = nullptr;
727  tree.SetBranchAddress("TkOffTreeVariables", &treeMemPtr);
728  tree.SetBranchAddress("SubstructureName", &substructureName);
729 
730  // Loop over modules to select accumulation criteria for harvesting plots
731  for (unsigned int iSubdet = 1; iSubdet < 7; ++iSubdet) {
732  std::string hierarchyName("");
733  std::string componentName("");
734  std::vector<unsigned int> treeEntries;
735  for (unsigned int iSide = 1; iSide < 3; ++iSide) {
736  // Set up only one collection for Barrels, not separated for side
737  if (iSide == 1 && (iSubdet == PixelSubdetector::PixelBarrel || iSubdet == StripSubdetector::TIB ||
738  iSubdet == StripSubdetector::TOB))
739  continue;
740  for (int iTree = 0; iTree < tree.GetEntries(); ++iTree) {
741  tree.GetEntry(iTree);
742  // Do not use glued Dets
743  if (treeMemPtr->isDoubleSide)
744  continue;
745  if (treeMemPtr->subDetId == iSubdet) {
746  if (iSide != treeMemPtr->side && (iSubdet == PixelSubdetector::PixelEndcap ||
747  iSubdet == StripSubdetector::TID || iSubdet == StripSubdetector::TEC))
748  continue;
749  treeEntries.push_back(iTree);
750  if (hierarchyName.length() == 0) {
751  hierarchyName = (*substructureName)["subdet"];
752  componentName = (*substructureName)["component"];
753  }
754  }
755  }
756  HarvestingHierarchy harvestingHierarchy(hierarchyName, componentName, treeEntries);
757  vHarvestingHierarchy_.push_back(harvestingHierarchy);
758  hierarchyName = "";
759  componentName = "";
760  treeEntries.clear();
761  }
762  }
763  // Here could be a further separation of the HarvestingHierarchy.
764  // E.g. separate the existing ones by layer and add them to the vector without deleting any element from the vector.
765  // The existing hists will stay and the new ones are added
766 
767  // Now, book the corresponding histos
768  this->bookHarvestingHists();
769 }
770 
772  edm::LogInfo("TrackerOfflineValidationSummary") << "Harvesting histograms will be booked for "
773  << vHarvestingHierarchy_.size() << " different hierarchy selections";
774  for (std::vector<HarvestingHierarchy>::iterator iHier = vHarvestingHierarchy_.begin();
775  iHier != vHarvestingHierarchy_.end();
776  ++iHier) {
777  std::stringstream dmrXprimeHistoName, dmrYprimeHistoName, dmrXprimeHistoTitle, dmrYprimeHistoTitle;
778  dmrXprimeHistoName << "h_DmrXprime_" << iHier->hierarchyName;
779  dmrYprimeHistoName << "h_DmrYprime_" << iHier->hierarchyName;
780  dmrXprimeHistoTitle << "DMR for " << iHier->hierarchyName << ";<#DeltaX> [cm];# modules";
781  dmrYprimeHistoTitle << "DMR for " << iHier->hierarchyName << ";<#DeltaY> [cm];# modules";
782 
783  std::string directoryString(moduleDirectory_);
784  if (directoryString.length() != 0)
785  directoryString += "/";
786  directoryString += iHier->componentName;
787  dbe_->setCurrentFolder(directoryString);
788 
789  int nBinsX(0);
790  double xMin(0.), xMax(0.);
791  if (iHier->componentName == "Pixel") {
792  this->getBinning("TH1DmrXprimePixelModules", nBinsX, xMin, xMax);
793  iHier->harvestingHistos.DmrXprime =
794  dbe_->book1D(dmrXprimeHistoName.str(), dmrXprimeHistoTitle.str(), nBinsX, xMin, xMax)->getTH1();
795  this->getBinning("TH1DmrYprimePixelModules", nBinsX, xMin, xMax);
796  iHier->harvestingHistos.DmrYprime =
797  dbe_->book1D(dmrYprimeHistoName.str(), dmrYprimeHistoTitle.str(), nBinsX, xMin, xMax)->getTH1();
798  } else if (iHier->componentName == "Strip") {
799  this->getBinning("TH1DmrXprimeStripModules", nBinsX, xMin, xMax);
800  iHier->harvestingHistos.DmrXprime =
801  dbe_->book1D(dmrXprimeHistoName.str(), dmrXprimeHistoTitle.str(), nBinsX, xMin, xMax)->getTH1();
802  if (!parSet_.getParameter<bool>("stripYDmrs"))
803  continue;
804  this->getBinning("TH1DmrYprimeStripModules", nBinsX, xMin, xMax);
805  iHier->harvestingHistos.DmrYprime =
806  dbe_->book1D(dmrYprimeHistoName.str(), dmrYprimeHistoTitle.str(), nBinsX, xMin, xMax)->getTH1();
807  }
808  }
809 }
810 
812  int& nBinsX,
813  double& lowerBoundX,
814  double& upperBoundX) const {
815  const edm::ParameterSet& binningPSet = parSet_.getParameter<edm::ParameterSet>(binningPSetName);
816  nBinsX = binningPSet.getParameter<int>("Nbinx");
817  lowerBoundX = binningPSet.getParameter<double>("xmin");
818  upperBoundX = binningPSet.getParameter<double>("xmax");
819 }
820 
822  TkOffTreeVariables* treeMemPtr = nullptr;
823  std::map<std::string, std::string>* substructureName = nullptr;
824  tree.SetBranchAddress("TkOffTreeVariables", &treeMemPtr);
825  tree.SetBranchAddress("SubstructureName", &substructureName);
826 
827  const unsigned int minEntriesPerModule(parSet_.getParameter<unsigned int>("minEntriesPerModuleForDmr"));
828  edm::LogInfo("TrackerOfflineValidationSummary")
829  << "Median of a module is added to DMR plots if it contains at least " << minEntriesPerModule << " hits";
830 
831  for (std::vector<HarvestingHierarchy>::iterator iHier = vHarvestingHierarchy_.begin();
832  iHier != vHarvestingHierarchy_.end();
833  ++iHier) {
834  for (std::vector<unsigned int>::const_iterator iTreeEntries = iHier->treeEntries.begin();
835  iTreeEntries != iHier->treeEntries.end();
836  ++iTreeEntries) {
837  tree.GetEntry(*iTreeEntries);
838  if (treeMemPtr->entries < minEntriesPerModule)
839  continue;
840  iHier->harvestingHistos.DmrXprime->Fill(treeMemPtr->medianX);
841  if (iHier->harvestingHistos.DmrYprime)
842  iHier->harvestingHistos.DmrYprime->Fill(treeMemPtr->medianY);
843  }
844  }
845 }
846 
847 //define this as a plug-in
std::map< int, TrackerOfflineValidationSummary::ModuleHistos > mTobResiduals_
static constexpr auto TEC
bool tibIsDoubleSide(const DetId &id) const
bool tecIsDoubleSide(const DetId &id) const
bool tidIsDoubleSide(const DetId &id) const
ESGetTokenH3DDVariant esConsumes(std::string const &Record, edm::ConsumesCollector &)
Definition: DeDxTools.cc:283
T getParameter(std::string const &) const
Definition: ParameterSet.h:303
unsigned int tobLayer(const DetId &id) const
unsigned int pxbLayer(const DetId &id) const
T perp() const
Definition: PV3DBase.h:69
std::vector< unsigned int > tidModuleInfo(const DetId &id) const
unsigned int pxfBlade(const DetId &id) const
T z() const
Definition: PV3DBase.h:61
Put here the histograms created during harvesting.
const DetIdContainer & detIds() const override
Returm a vector of all GeomDet DetIds (including those of GeomDetUnits)
uint32_t tidStereo(const DetId &id) const
unsigned int tibModule(const DetId &id) const
unsigned int tidSide(const DetId &id) const
#define DEFINE_FWK_MODULE(type)
Definition: MakerMacros.h:16
container to hold data to be written into TTree
Geom::Phi< T > phi() const
Definition: PV3DBase.h:66
unsigned int pxfModule(const DetId &id) const
std::vector< unsigned int > tecPetalInfo(const DetId &id) const
unsigned int tidWheel(const DetId &id) const
unsigned int tecWheel(const DetId &id) const
T eta() const
Definition: PV3DBase.h:73
void setCurrentFolder(std::string const &fullpath) override
Definition: DQMStore.h:646
dqm::legacy::DQMStore * dbe_
std::vector< HarvestingHierarchy > vHarvestingHierarchy_
void getBinning(const std::string &binningPSetName, int &nBinsX, double &lowerBoundX, double &upperBoundX) const
edm::ESHandle< TrackerGeometry > tkGeom_
unsigned int pxbLadder(const DetId &id) const
Log< level::Error, false > LogError
constexpr Detector det() const
get the detector field from this detid
Definition: DetId.h:46
unsigned int tecRing(const DetId &id) const
ring id
std::map< int, TrackerOfflineValidationSummary::ModuleHistos > mTibResiduals_
bool tobIsDoubleSide(const DetId &id) const
constexpr std::array< uint8_t, layerIndexSize > layer
T barePhi() const
Definition: PV3DBase.h:65
T x() const
Definition: PV3DBase.h:59
T y() const
Definition: PV3DBase.h:60
unsigned int tecModule(const DetId &id) const
int iEvent
Definition: GenABIO.cc:224
uint32_t tobStereo(const DetId &id) const
unsigned int tecSide(const DetId &id) const
const std::string associateModuleHistsWithTree(const TkOffTreeVariables &treeMem, TrackerOfflineValidationSummary::ModuleHistos &moduleHists, std::map< std::string, std::string > &substructureName)
unsigned int pxfDisk(const DetId &id) const
Transition
Definition: Transition.h:12
constexpr int subdetId() const
get the contents of the subdetector field (not cast into any detector&#39;s numbering enum) ...
Definition: DetId.h:48
bool getData(T &iHolder) const
Definition: EventSetup.h:122
static constexpr auto TOB
histDir
Location of output EventInfo/reportSummaryContents.
TrackerOfflineValidationSummary(const edm::ParameterSet &)
ESHandle< T > getHandle(const ESGetToken< T, R > &iToken) const
Definition: EventSetup.h:151
void analyze(const edm::Event &evt, const edm::EventSetup &) override
std::pair< float, float > fitResiduals(TH1 *hist) const
const TrackerGeomDet * idToDet(DetId) const override
std::string histNameNormLocalX
std::map< int, TrackerOfflineValidationSummary::ModuleHistos > mTecResiduals_
GlobalPoint toGlobal(const Point2DBase< Scalar, LocalTag > lp) const
Definition: Surface.h:79
__shared__ Hist hist
unsigned int pxfPanel(const DetId &id) const
std::map< int, TrackerOfflineValidationSummary::ModuleHistos > mPxbResiduals_
Log< level::Info, false > LogInfo
Definition: DetId.h:17
HarvestingHierarchy(const std::string &name, const std::string &component, const std::vector< unsigned int > &entries)
unsigned int pxfSide(const DetId &id) const
std::vector< unsigned int > tibStringInfo(const DetId &id) const
static constexpr auto TIB
const Plane & surface() const
The nominal surface of the GeomDet.
Definition: GeomDet.h:37
void beginRun(const edm::Run &, const edm::EventSetup &iSetup) override
constexpr uint32_t rawId() const
get the raw id
Definition: DetId.h:57
std::string histNameLocalX
virtual MonitorElement * get(std::string const &fullpath) const
Definition: DQMStore.cc:680
void endRun(const edm::Run &, const edm::EventSetup &iSetup) override
const Surface::PositionType & position() const
The position (origin of the R.F.)
Definition: GeomDet.h:43
std::vector< DetId > DetIdContainer
virtual TH1 * getTH1() const
T median(std::vector< T > values)
Definition: median.h:16
std::vector< unsigned int > tobRodInfo(const DetId &id) const
void clear()
set to empty values
HLT enums.
const edm::ESGetToken< TrackerTopology, TrackerTopologyRcd > tTopoToken_
unsigned int tidRing(const DetId &id) const
std::unique_ptr< TrackerTopology > tTopo_
std::map< int, TrackerOfflineValidationSummary::ModuleHistos > mPxeResiduals_
uint32_t tecStereo(const DetId &id) const
const edm::ESGetToken< TrackerGeometry, TrackerDigiGeometryRecord > geomToken_
unsigned int tibLayer(const DetId &id) const
std::map< int, TrackerOfflineValidationSummary::ModuleHistos > mTidResiduals_
unsigned int tobModule(const DetId &id) const
Definition: tree.py:1
unsigned int pxbModule(const DetId &id) const
Log< level::Warning, false > LogWarning
MonitorElement * book1D(TString const &name, TString const &title, int const nchX, double const lowX, double const highX, FUNC onbooking=NOOP())
Definition: DQMStore.h:98
The Signals That Services Can Subscribe To This is based on ActivityRegistry h
Helper function to determine trigger accepts.
Definition: Activities.doc:4
void fillTree(TTree &tree, std::map< int, TrackerOfflineValidationSummary::ModuleHistos > &moduleHist, TkOffTreeVariables &treeMem, const TrackerGeometry &tkgeom, std::map< std::string, std::string > &substructureName, const TrackerTopology *tTopo)
static constexpr auto TID
uint32_t tibStereo(const DetId &id) const
Definition: Run.h:45