CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
TrackerOfflineValidation.cc
Go to the documentation of this file.
1 // -*- C++ -*-
2 //
3 // Package: TrackerOfflineValidation
4 // Class: TrackerOfflineValidation
5 //
13 //
14 // Original Author: Erik Butz
15 // Created: Tue Dec 11 14:03:05 CET 2007
16 // $Id: TrackerOfflineValidation.cc,v 1.55 2012/09/28 20:48:06 flucke Exp $
17 //
18 //
19 
20 // system include files
21 #include <memory>
22 #include <map>
23 #include <sstream>
24 #include <math.h>
25 #include <tuple>
26 #include <utility>
27 #include <vector>
28 #include <iostream>
29 
30 // ROOT includes
31 #include "TH1.h"
32 #include "TH2.h"
33 #include "TProfile.h"
34 #include "TFile.h"
35 #include "TTree.h"
36 #include "TF1.h"
37 #include "TMath.h"
38 
39 // user include files
49 
55 
58 
63 
66 
72 
75 
76 //
77 // class declaration
78 //
80 public:
83 
85  YResidual, /*NormYResidual, */
89 
90 private:
91 
92  struct ModuleHistos{
93  ModuleHistos() : ResHisto(), NormResHisto(), ResYHisto(), /*NormResYHisto(),*/
98  LocalX(), LocalY() {}
99  TH1* ResHisto;
101  TH1* ResYHisto;
102  /* TH1* NormResYHisto; */
107 
108  TProfile* ResXvsXProfile;
109  TProfile* ResXvsYProfile;
110  TProfile* ResYvsXProfile;
111  TProfile* ResYvsYProfile;
112 
113  TH1* LocalX;
114  TH1* LocalY;
115  };
116 
117  // container struct to organize collection of histograms during endJob
125 
134 
139  };
140 
141 
143  DirectoryWrapper(const DirectoryWrapper& upDir,const std::string& newDir,
144  const std::string& basedir,bool useDqmMode)
145  : tfd(0),
146  dqmMode(useDqmMode),
147  theDbe(0) {
148  if (newDir.length()!=0){
149  if(upDir.directoryString.length()!=0)directoryString=upDir.directoryString+"/"+newDir;
150  else directoryString = newDir;
151  }
152  else
154 
155  if (!dqmMode){
156  if (newDir.length()==0) tfd.reset(&(*upDir.tfd));
157  else
158  tfd.reset(new TFileDirectory(upDir.tfd->mkdir(newDir)));
159  }
160  else {
162  }
163  }
164 
165  DirectoryWrapper(const std::string& newDir,const std::string& basedir,bool useDqmMode)
166  : tfd(0),
167  dqmMode(useDqmMode),
168  theDbe(0) {
169  if (!dqmMode){
171  if (newDir.length()==0){
172  tfd.reset(new TFileDirectory(fs->tFileDirectory()));
173  }
174  else {
175  tfd.reset(new TFileDirectory(fs->mkdir(newDir)));
176  directoryString=newDir;
177  }
178  }
179  else {
180  if (newDir.length()!=0){
181  if(basedir.length()!=0)directoryString=basedir+"/"+newDir;
182  else directoryString = newDir;
183  }
184  else directoryString=basedir;
186  }
187  }
188  // Generalization of Histogram Booking; allows switch between TFileService and DQMStore
189  template <typename T> TH1* make(const char* name,const char* title,int nBinX,double minBinX,double maxBinX);
190  template <typename T> TH1* make(const char* name,const char* title,int nBinX,double *xBins);//variable bin size in x for profile histo
191  template <typename T> TH1* make(const char* name,const char* title,int nBinX,double minBinX,double maxBinX,int nBinY,double minBinY,double maxBinY);
192  template <typename T> TH1* make(const char* name,const char* title,int nBinX,double minBinX,double maxBinX,double minBinY,double maxBinY); // at present not used
193 
194  std::auto_ptr<TFileDirectory> tfd;
196  const bool dqmMode;
198  };
199 
200 
201  //
202  // ------------- private member function -------------
203  //
204  virtual void analyze(const edm::Event&, const edm::EventSetup&) override;
205  virtual void endJob() override;
206 
207  virtual void checkBookHists(const edm::EventSetup& setup);
208 
210  void bookDirHists(DirectoryWrapper& tfd, const Alignable& ali, const TrackerTopology* tTopo);
211  void bookHists(DirectoryWrapper& tfd, const Alignable& ali, const TrackerTopology* tTopo, align::StructureType type, int i);
212 
213  void prepareSummaryHists( DirectoryWrapper& tfd, const Alignable& ali,
214  std::vector<TrackerOfflineValidation::SummaryContainer>& vLevelProfiles);
215  void collateSummaryHists();
216 
217  void setUpTreeMembers(const std::map<int, TrackerOfflineValidation::ModuleHistos>& moduleHist_,
218  const TrackerGeometry& tkgeom, const TrackerTopology* tTopo);
219  void fillTree(TTree& tree, TkOffTreeVariables &treeMem, const std::map<int, TrackerOfflineValidation::ModuleHistos>& moduleHist_);
220 
222  const Alignable& ali,
223  align::StructureType type, int i);
224 
226 
227  bool isBarrel(uint32_t subDetId);
228  bool isEndCap(uint32_t subDetId);
229  bool isPixel(uint32_t subDetId);
231 
232  TH1* bookTH1F(bool isTransient, DirectoryWrapper& tfd, const char* histName, const char* histTitle,
233  int nBinsX, double lowX, double highX);
234 
235  TProfile* bookTProfile(bool isTransient, DirectoryWrapper& tfd, const char* histName, const char* histTitle,
236  int nBinsX, double lowX, double highX);
237 
238  TProfile* bookTProfile(bool isTransient, DirectoryWrapper& tfd, const char* histName, const char* histTitle,
239  int nBinsX, double lowX, double highX, double lowY, double highY);
240 
241  void getBinning(uint32_t subDetId, TrackerOfflineValidation::HistogramType residualtype,
242  int& nBinsX, double& lowerBoundX, double& upperBoundX);
243 
244  void summarizeBinInContainer(int bin, SummaryContainer& targetContainer,
245  SummaryContainer& sourceContainer);
246 
247  void summarizeBinInContainer(int bin, uint32_t subDetId, SummaryContainer& targetContainer,
248  ModuleHistos& sourceContainer);
249 
250  void setSummaryBin(int bin, TH1* targetHist, TH1* sourceHist);
251 
252  float Fwhm(const TH1* hist) const;
253  std::pair<float,float> fitResiduals(TH1* hist) const; //, float meantmp, float rmstmp);
254  float getMedian( const TH1* hist) const;
255 
256  // From MillePedeAlignmentMonitor: Get Index for Arbitary vector<class> by name
257  template <class OBJECT_TYPE> int GetIndex(const std::vector<OBJECT_TYPE*>& vec, const TString& name);
258 
259 
260  // ---------- member data ---------------------------
261 
264  const TrackerGeometry *bareTkGeomPtr_; // ugly hack to book hists only once, but check
265 
266  // parameters from cfg to steer
267  const bool lCoorHistOn_;
270  const bool stripYResiduals_;
271  const bool useFwhm_;
272  const bool useFit_;
273  const bool useOverflowForRMS_;
274  const bool dqmMode_;
276 
277  // a vector to keep track which pointers should be deleted at the very end
278  std::vector<TH1*> vDeleteObjects_;
279 
280  std::vector<TH1*> vTrackHistos_;
281  std::vector<TH1*> vTrackProfiles_;
282  std::vector<TH1*> vTrack2DHistos_;
283 
284  std::map<int,TrackerOfflineValidation::ModuleHistos> mPxbResiduals_;
285  std::map<int,TrackerOfflineValidation::ModuleHistos> mPxeResiduals_;
286  std::map<int,TrackerOfflineValidation::ModuleHistos> mTibResiduals_;
287  std::map<int,TrackerOfflineValidation::ModuleHistos> mTidResiduals_;
288  std::map<int,TrackerOfflineValidation::ModuleHistos> mTobResiduals_;
289  std::map<int,TrackerOfflineValidation::ModuleHistos> mTecResiduals_;
290 
291  std::map<int,TkOffTreeVariables> mTreeMembers_;
292 
293  //There are two types of summary histograms. The first contains, for each component, a bin per subcomponent.
294  //These are set up through summarizeBinInContainer(). The second type is just the sum of the lower level histograms.
295  //Prepare the filling of both types at the beginning, when the tracker topology is available through the eventsetup.
296  //They are not actually filled until the end, but at that time eventsetup is no longer accessible.
297 
298  //To fill the summary hists, store the arguments of setSummaryBin()
299  //At the end, call the function
300  std::vector<std::tuple<int,TH1*,TH1*> > summaryBins_;
301  //To fill the sum hists, just store pairs of TH1*. At the end, first->Add(second).
302  std::vector<std::pair<TH1*,TH1*> > sumHistStructure_;
303  //sum hists are fit at the end using fitResiduals()
304  std::vector<TH1*> toFit_;
305 
307 };
308 
309 
310 //
311 // constants, enums and typedefs
312 //
313 
314 //
315 // static data member definitions
316 //
317 
318 template <class OBJECT_TYPE>
319 int TrackerOfflineValidation::GetIndex(const std::vector<OBJECT_TYPE*> &vec, const TString &name)
320 {
321  int result = 0;
322  for (typename std::vector<OBJECT_TYPE*>::const_iterator iter = vec.begin(), iterEnd = vec.end();
323  iter != iterEnd; ++iter, ++result) {
324  if (*iter && (*iter)->GetName() == name) return result;
325  }
326  edm::LogError("Alignment") << "@SUB=TrackerOfflineValidation::GetIndex" << " could not find " << name;
327  return -1;
328 }
329 
330 
331 template <> TH1* TrackerOfflineValidation::DirectoryWrapper::make<TH1F>(const char* name,const char* title,int nBinX,double minBinX,double maxBinX){
332  if(dqmMode){theDbe->setCurrentFolder(directoryString); return theDbe->book1D(name,title,nBinX,minBinX,maxBinX)->getTH1();}
333  else{return tfd->make<TH1F>(name,title,nBinX,minBinX,maxBinX);}
334 }
335 
336 template <> TH1* TrackerOfflineValidation::DirectoryWrapper::make<TProfile>(const char* name,const char* title,int nBinX,double *xBins){
337  if(dqmMode){
338  theDbe->setCurrentFolder(directoryString);
339  //DQM profile requires y-bins for construction... using TProfile creator by hand...
340  TProfile *tmpProfile=new TProfile(name,title,nBinX,xBins);
341  tmpProfile->SetDirectory(0);
342  return theDbe->bookProfile(name,tmpProfile)->getTH1();
343  }
344  else{return tfd->make<TProfile>(name,title,nBinX,xBins);}
345 }
346 
347 template <> TH1* TrackerOfflineValidation::DirectoryWrapper::make<TProfile>(const char* name,const char* title,int nBinX,double minBinX,double maxBinX){
348  if(dqmMode){
349  theDbe->setCurrentFolder(directoryString);
350  //DQM profile requires y-bins for construction... using TProfile creator by hand...
351  TProfile *tmpProfile=new TProfile(name,title,nBinX,minBinX,maxBinX);
352  tmpProfile->SetDirectory(0);
353  return theDbe->bookProfile(name,tmpProfile)->getTH1();
354  }
355  else{return tfd->make<TProfile>(name,title,nBinX,minBinX,maxBinX);}
356 }
357 
358 template <> TH1* TrackerOfflineValidation::DirectoryWrapper::make<TProfile>(const char* name ,const char* title,int nbinX,double minX ,double maxX,double minY,double maxY){
359  if(dqmMode){
360  theDbe->setCurrentFolder(directoryString);
361  int dummy(0); // DQMProfile wants Y channels... does not use them!
362  return (theDbe->bookProfile(name,title,nbinX,minX,maxX,dummy,minY,maxY)->getTH1());
363  }
364  else{
365  return tfd->make<TProfile>(name,title,nbinX,minX,maxX,minY,maxY);
366  }
367 }
368 
369 template <> TH1* TrackerOfflineValidation::DirectoryWrapper::make<TH2F>(const char* name,const char* title,int nBinX,double minBinX,double maxBinX,int nBinY,double minBinY,double maxBinY){
370  if(dqmMode){theDbe->setCurrentFolder(directoryString); return theDbe->book2D(name,title,nBinX,minBinX,maxBinX,nBinY,minBinY,maxBinY)->getTH1();}
371  else{return tfd->make<TH2F>(name,title,nBinX,minBinX,maxBinX,nBinY,minBinY,maxBinY);}
372 }
373 
374 
375 //
376 // constructors and destructor
377 //
379  : parSet_(iConfig), bareTkGeomPtr_(0), lCoorHistOn_(parSet_.getParameter<bool>("localCoorHistosOn")),
380  moduleLevelHistsTransient_(parSet_.getParameter<bool>("moduleLevelHistsTransient")),
381  moduleLevelProfiles_(parSet_.getParameter<bool>("moduleLevelProfiles")),
382  stripYResiduals_(parSet_.getParameter<bool>("stripYResiduals")),
383  useFwhm_(parSet_.getParameter<bool>("useFwhm")),
384  useFit_(parSet_.getParameter<bool>("useFit")),
385  useOverflowForRMS_(parSet_.getParameter<bool>("useOverflowForRMS")),
386  dqmMode_(parSet_.getParameter<bool>("useInDqmMode")),
387  moduleDirectory_(parSet_.getParameter<std::string>("moduleDirectoryInOutput")),
388  avalidator_(iConfig, consumesCollector())
389 {
390 }
391 
392 
394 {
395  // do anything here that needs to be done at desctruction time
396  // (e.g. close files, deallocate resources etc.)
397  for( std::vector<TH1*>::const_iterator it = vDeleteObjects_.begin(), itEnd = vDeleteObjects_.end();
398  it != itEnd;
399  ++it) delete *it;
400 }
401 
402 
403 //
404 // member functions
405 //
406 
407 
408 // ------------ method called once each job just before starting event loop ------------
409 void
411 {
413  const TrackerGeometry *newBareTkGeomPtr = &(*tkGeom_);
414  if (newBareTkGeomPtr == bareTkGeomPtr_) return; // already booked hists, nothing changed
415 
416  if (!bareTkGeomPtr_) { // pointer not yet set: called the first time => book hists
417 
418  //Retrieve tracker topology from geometry
419  edm::ESHandle<TrackerTopology> tTopoHandle;
420  es.get<TrackerTopologyRcd>().get(tTopoHandle);
421  const TrackerTopology* const tTopo = tTopoHandle.product();
422 
423  // construct alignable tracker to get access to alignable hierarchy
424  AlignableTracker aliTracker(&(*tkGeom_), tTopo);
425 
426  edm::LogInfo("TrackerOfflineValidation") << "There are " << newBareTkGeomPtr->detIds().size()
427  << " dets in the Geometry record.\n"
428  << "Out of these "<<newBareTkGeomPtr->detUnitIds().size()
429  <<" are detUnits";
430 
431  // Book histograms for global track quantities
432  std::string globDir("GlobalTrackVariables");
433  DirectoryWrapper trackglobal(globDir,moduleDirectory_,dqmMode_);
434  this->bookGlobalHists(trackglobal);
435 
436  // recursively book histograms on lowest level
438  this->bookDirHists(tfdw, aliTracker, tTopo);
439  // and prepare the higher level histograms
440  std::vector<TrackerOfflineValidation::SummaryContainer> vTrackerprofiles;
441  this->prepareSummaryHists(tfdw, (aliTracker), vTrackerprofiles);
442 
443  setUpTreeMembers(mPxbResiduals_, *newBareTkGeomPtr, tTopo);
444  setUpTreeMembers(mPxeResiduals_, *newBareTkGeomPtr, tTopo);
445  setUpTreeMembers(mTibResiduals_, *newBareTkGeomPtr, tTopo);
446  setUpTreeMembers(mTidResiduals_, *newBareTkGeomPtr, tTopo);
447  setUpTreeMembers(mTobResiduals_, *newBareTkGeomPtr, tTopo);
448  setUpTreeMembers(mTecResiduals_, *newBareTkGeomPtr, tTopo);
449  }
450  else { // histograms booked, but changed TrackerGeometry?
451  edm::LogWarning("GeometryChange") << "@SUB=checkBookHists"
452  << "TrackerGeometry changed, but will not re-book hists!";
453  }
454  bareTkGeomPtr_ = newBareTkGeomPtr;
455 }
456 
457 
458 void
460 {
461 
462  vTrackHistos_.push_back(tfd.make<TH1F>("h_tracketa",
463  "Track #eta;#eta_{Track};Number of Tracks",
464  90,-3.,3.));
465  vTrackHistos_.push_back(tfd.make<TH1F>("h_trackphi",
466  "Track #phi;#phi_{Track};Number of Tracks",
467  90,-3.15,3.15));
468  vTrackHistos_.push_back(tfd.make<TH1F>("h_trackNumberOfValidHits",
469  "Track # of valid hits;# of valid hits _{Track};Number of Tracks",
470  40,0.,40.));
471  vTrackHistos_.push_back(tfd.make<TH1F>("h_trackNumberOfLostHits",
472  "Track # of lost hits;# of lost hits _{Track};Number of Tracks",
473  10,0.,10.));
474  vTrackHistos_.push_back(tfd.make<TH1F>("h_curvature",
475  "Curvature #kappa;#kappa_{Track};Number of Tracks",
476  100,-.05,.05));
477  vTrackHistos_.push_back(tfd.make<TH1F>("h_curvature_pos",
478  "Curvature |#kappa| Positive Tracks;|#kappa_{pos Track}|;Number of Tracks",
479  100,.0,.05));
480  vTrackHistos_.push_back(tfd.make<TH1F>("h_curvature_neg",
481  "Curvature |#kappa| Negative Tracks;|#kappa_{neg Track}|;Number of Tracks",
482  100,.0,.05));
483  vTrackHistos_.push_back(tfd.make<TH1F>("h_diff_curvature",
484  "Curvature |#kappa| Tracks Difference;|#kappa_{Track}|;# Pos Tracks - # Neg Tracks",
485  100,.0,.05));
486  vTrackHistos_.push_back(tfd.make<TH1F>("h_chi2",
487  "#chi^{2};#chi^{2}_{Track};Number of Tracks",
488  500,-0.01,500.));
489  vTrackHistos_.push_back(tfd.make<TH1F>("h_chi2Prob",
490  "#chi^{2} probability;#chi^{2}prob_{Track};Number of Tracks",
491  100,0.0,1.));
492  vTrackHistos_.push_back(tfd.make<TH1F>("h_normchi2",
493  "#chi^{2}/ndof;#chi^{2}/ndof;Number of Tracks",
494  100,-0.01,10.));
495  vTrackHistos_.push_back(tfd.make<TH1F>("h_pt",
496  "p_{T}^{track};p_{T}^{track} [GeV];Number of Tracks",
497  250,0.,250));
498  vTrackHistos_.push_back(tfd.make<TH1F>("h_ptResolution",
499  "#delta_{p_{T}}/p_{T}^{track};#delta_{p_{T}}/p_{T}^{track};Number of Tracks",
500  100,0.,0.5));
501  vTrackProfiles_.push_back(tfd.make<TProfile>("p_d0_vs_phi",
502  "Transverse Impact Parameter vs. #phi;#phi_{Track};#LT d_{0} #GT [cm]",
503  100,-3.15,3.15));
504  vTrackProfiles_.push_back(tfd.make<TProfile>("p_dz_vs_phi",
505  "Longitudinal Impact Parameter vs. #phi;#phi_{Track};#LT d_{z} #GT [cm]",
506  100,-3.15,3.15));
507  vTrackProfiles_.push_back(tfd.make<TProfile>("p_d0_vs_eta",
508  "Transverse Impact Parameter vs. #eta;#eta_{Track};#LT d_{0} #GT [cm]",
509  100,-3.15,3.15));
510  vTrackProfiles_.push_back(tfd.make<TProfile>("p_dz_vs_eta",
511  "Longitudinal Impact Parameter vs. #eta;#eta_{Track};#LT d_{z} #GT [cm]",
512  100,-3.15,3.15));
513  vTrackProfiles_.push_back(tfd.make<TProfile>("p_chi2_vs_phi",
514  "#chi^{2} vs. #phi;#phi_{Track};#LT #chi^{2} #GT",
515  100,-3.15,3.15));
516  vTrackProfiles_.push_back(tfd.make<TProfile>("p_chi2Prob_vs_phi",
517  "#chi^{2} probablility vs. #phi;#phi_{Track};#LT #chi^{2} probability#GT",
518  100,-3.15,3.15));
519  vTrackProfiles_.push_back(tfd.make<TProfile>("p_chi2Prob_vs_d0",
520  "#chi^{2} probablility vs. |d_{0}|;|d_{0}|[cm];#LT #chi^{2} probability#GT",
521  100,0,80));
522  vTrackProfiles_.push_back(tfd.make<TProfile>("p_normchi2_vs_phi",
523  "#chi^{2}/ndof vs. #phi;#phi_{Track};#LT #chi^{2}/ndof #GT",
524  100,-3.15,3.15));
525  vTrackProfiles_.push_back(tfd.make<TProfile>("p_chi2_vs_eta",
526  "#chi^{2} vs. #eta;#eta_{Track};#LT #chi^{2} #GT",
527  100,-3.15,3.15));
528  //variable binning for chi2/ndof vs. pT
529  double xBins[19]={0.,0.15,0.5,1.,1.5,2.,2.5,3.,3.5,4.,4.5,5.,7.,10.,15.,25.,40.,100.,200.};
530  vTrackProfiles_.push_back(tfd.make<TProfile>("p_normchi2_vs_pt",
531  "norm #chi^{2} vs. p_{T}_{Track}; p_{T}_{Track};#LT #chi^{2}/ndof #GT",
532  18,xBins));
533 
534  vTrackProfiles_.push_back(tfd.make<TProfile>("p_normchi2_vs_p",
535  "#chi^{2}/ndof vs. p_{Track};p_{Track};#LT #chi^{2}/ndof #GT",
536  18,xBins));
537  vTrackProfiles_.push_back(tfd.make<TProfile>("p_chi2Prob_vs_eta",
538  "#chi^{2} probability vs. #eta;#eta_{Track};#LT #chi^{2} probability #GT",
539  100,-3.15,3.15));
540  vTrackProfiles_.push_back(tfd.make<TProfile>("p_normchi2_vs_eta",
541  "#chi^{2}/ndof vs. #eta;#eta_{Track};#LT #chi^{2}/ndof #GT",
542  100,-3.15,3.15));
543  vTrackProfiles_.push_back(tfd.make<TProfile>("p_kappa_vs_phi",
544  "#kappa vs. #phi;#phi_{Track};#kappa",
545  100,-3.15,3.15));
546  vTrackProfiles_.push_back(tfd.make<TProfile>("p_kappa_vs_eta",
547  "#kappa vs. #eta;#eta_{Track};#kappa",
548  100,-3.15,3.15));
549  vTrackProfiles_.push_back(tfd.make<TProfile>("p_ptResolution_vs_phi",
550  "#delta_{p_{T}}/p_{T}^{track};#phi^{track};#delta_{p_{T}}/p_{T}^{track}",
551  100, -3.15,3.15));
552  vTrackProfiles_.push_back(tfd.make<TProfile>("p_ptResolution_vs_eta",
553  "#delta_{p_{T}}/p_{T}^{track};#eta^{track};#delta_{p_{T}}/p_{T}^{track}",
554  100, -3.15,3.15));
555 
556  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_d0_vs_phi",
557  "Transverse Impact Parameter vs. #phi;#phi_{Track};d_{0} [cm]",
558  100, -3.15, 3.15, 100,-1.,1.) );
559  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_dz_vs_phi",
560  "Longitudinal Impact Parameter vs. #phi;#phi_{Track};d_{z} [cm]",
561  100, -3.15, 3.15, 100,-100.,100.));
562  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_d0_vs_eta",
563  "Transverse Impact Parameter vs. #eta;#eta_{Track};d_{0} [cm]",
564  100, -3.15, 3.15, 100,-1.,1.));
565  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_dz_vs_eta",
566  "Longitudinal Impact Parameter vs. #eta;#eta_{Track};d_{z} [cm]",
567  100, -3.15, 3.15, 100,-100.,100.));
568  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_chi2_vs_phi",
569  "#chi^{2} vs. #phi;#phi_{Track};#chi^{2}",
570  100, -3.15, 3.15, 500, 0., 500.));
571  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_chi2Prob_vs_phi",
572  "#chi^{2} probability vs. #phi;#phi_{Track};#chi^{2} probability",
573  100, -3.15, 3.15, 100, 0., 1.));
574  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_chi2Prob_vs_d0",
575  "#chi^{2} probability vs. |d_{0}|;|d_{0}| [cm];#chi^{2} probability",
576  100, 0, 80, 100, 0., 1.));
577  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_normchi2_vs_phi",
578  "#chi^{2}/ndof vs. #phi;#phi_{Track};#chi^{2}/ndof",
579  100, -3.15, 3.15, 100, 0., 10.));
580  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_chi2_vs_eta",
581  "#chi^{2} vs. #eta;#eta_{Track};#chi^{2}",
582  100, -3.15, 3.15, 500, 0., 500.));
583  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_chi2Prob_vs_eta",
584  "#chi^{2} probaility vs. #eta;#eta_{Track};#chi^{2} probability",
585  100, -3.15, 3.15, 100, 0., 1.));
586  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_normchi2_vs_eta",
587  "#chi^{2}/ndof vs. #eta;#eta_{Track};#chi^{2}/ndof",
588  100,-3.15,3.15, 100, 0., 10.));
589  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_kappa_vs_phi",
590  "#kappa vs. #phi;#phi_{Track};#kappa",
591  100,-3.15,3.15, 100, .0,.05));
592  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_kappa_vs_eta",
593  "#kappa vs. #eta;#eta_{Track};#kappa",
594  100,-3.15,3.15, 100, .0,.05));
595  vTrack2DHistos_.push_back(tfd.make<TH2F>("h2_normchi2_vs_kappa",
596  "#kappa vs. #chi^{2}/ndof;#chi^{2}/ndof;#kappa",
597  100,0.,10, 100,-.03,.03));
598 
599  /****************** Definition of 2-D Histos of ResX vs momenta ****************************/
600  vTrack2DHistos_.push_back(tfd.make<TH2F>("p_vs_resXprime_pixB",
601  "res_{x'} vs momentum in BPix;p [GeV]; res_{x'}",
602  15,0.,15., 200, -0.1,0.1));
603  vTrack2DHistos_.push_back(tfd.make<TH2F>("p_vs_resXprime_pixE",
604  "res_{x'} vs momentum in FPix;p [GeV]; res_{x'}",
605  15,0.,15., 200, -0.1,0.1));
606  vTrack2DHistos_.push_back(tfd.make<TH2F>("p_vs_resXprime_TIB",
607  "res_{x'} vs momentum in TIB;p [GeV]; res_{x'}",
608  15,0.,15., 200, -0.1,0.1));
609  vTrack2DHistos_.push_back(tfd.make<TH2F>("p_vs_resXprime_TID",
610  "res_{x'} vs momentum in TID;p [GeV]; res_{x'}",
611  15,0.,15., 200, -0.1,0.1));
612  vTrack2DHistos_.push_back(tfd.make<TH2F>("p_vs_resXprime_TOB",
613  "res_{x'} vs momentum in TOB;p [GeV]; res_{x'}",
614  15,0.,15., 200, -0.1,0.1));
615  vTrack2DHistos_.push_back(tfd.make<TH2F>("p_vs_resXprime_TEC",
616  "res_{x'} vs momentum in TEC;p [GeV]; res_{x'}",
617  15,0.,15., 200, -0.1,0.1));
618 
619  /****************** Definition of 2-D Histos of ResY vs momenta ****************************/
620  vTrack2DHistos_.push_back(tfd.make<TH2F>("p_vs_resYprime_pixB",
621  "res_{y'} vs momentum in BPix;p [GeV]; res_{y'}",
622  15,0.,15., 200, -0.1,0.1));
623  vTrack2DHistos_.push_back(tfd.make<TH2F>("p_vs_resYprime_pixE",
624  "res_{y'} vs momentum in FPix;p [GeV]; res_{y'}",
625  15,0.,15., 200, -0.1,0.1));
626 
627 }
628 
629 
630 void
632 {
633  std::vector<Alignable*> alivec(ali.components());
634  for(int i=0, iEnd = ali.components().size();i < iEnd; ++i) {
635  std::string structurename = AlignableObjectId::idToString((alivec)[i]->alignableObjectId());
636  LogDebug("TrackerOfflineValidation") << "StructureName = " << structurename;
637  std::stringstream dirname;
638  dirname << structurename;
639  // add no suffix counter to Strip and Pixel, just aesthetics
640  if (structurename != "Strip" && structurename != "Pixel") dirname << "_" << i+1;
641 
642  if (structurename.find("Endcap",0) != std::string::npos ) {
643  DirectoryWrapper f(tfd,dirname.str(),moduleDirectory_,dqmMode_);
644  bookHists(f, *(alivec)[i], tTopo, ali.alignableObjectId() , i);
645  bookDirHists( f, *(alivec)[i], tTopo);
646  } else if( !(this->isDetOrDetUnit( (alivec)[i]->alignableObjectId()) )
647  || alivec[i]->components().size() > 1) {
648  DirectoryWrapper f(tfd,dirname.str(),moduleDirectory_,dqmMode_);
649  bookHists(tfd, *(alivec)[i], tTopo, ali.alignableObjectId() , i);
650  bookDirHists( f, *(alivec)[i], tTopo);
651  } else {
652  bookHists(tfd, *(alivec)[i], tTopo, ali.alignableObjectId() , i);
653  }
654  }
655 }
656 
657 
658 void
660 {
661  TrackerAlignableId aliid;
662  const DetId id = ali.id();
663 
664  // comparing subdetandlayer to subdetIds gives a warning at compile time
665  // -> subdetandlayer could also be pair<uint,uint> but this has to be adapted
666  // in AlignableObjId
667  std::pair<int,int> subdetandlayer = aliid.typeAndLayerFromDetId(id, tTopo);
668 
670 
671  // are we on or just above det, detunit level respectively?
672  if (type == align::AlignableDetUnit )subtype = type;
673  else if( this->isDetOrDetUnit(ali.alignableObjectId()) ) subtype = ali.alignableObjectId();
674 
675  // construct histogram title and name
676  std::stringstream histoname, histotitle, normhistoname, normhistotitle,
677  yhistoname, yhistotitle,
678  xprimehistoname, xprimehistotitle, normxprimehistoname, normxprimehistotitle,
679  yprimehistoname, yprimehistotitle, normyprimehistoname, normyprimehistotitle,
680  localxname, localxtitle, localyname, localytitle,
681  resxvsxprofilename, resxvsxprofiletitle, resyvsxprofilename, resyvsxprofiletitle,
682  resxvsyprofilename, resxvsyprofiletitle, resyvsyprofilename, resyvsyprofiletitle;
683 
684  std::string wheel_or_layer;
685 
686  if( this->isEndCap(static_cast<uint32_t>(subdetandlayer.first)) ) wheel_or_layer = "_wheel_";
687  else if ( this->isBarrel(static_cast<uint32_t>(subdetandlayer.first)) ) wheel_or_layer = "_layer_";
688  else edm::LogWarning("TrackerOfflineValidation") << "@SUB=TrackerOfflineValidation::bookHists"
689  << "Unknown subdetid: " << subdetandlayer.first;
690 
691  histoname << "h_residuals_subdet_" << subdetandlayer.first
692  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
693  yhistoname << "h_y_residuals_subdet_" << subdetandlayer.first
694  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
695  xprimehistoname << "h_xprime_residuals_subdet_" << subdetandlayer.first
696  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
697  yprimehistoname << "h_yprime_residuals_subdet_" << subdetandlayer.first
698  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
699  normhistoname << "h_normresiduals_subdet_" << subdetandlayer.first
700  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
701  normxprimehistoname << "h_normxprimeresiduals_subdet_" << subdetandlayer.first
702  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
703  normyprimehistoname << "h_normyprimeresiduals_subdet_" << subdetandlayer.first
704  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
705  histotitle << "X Residual for module " << id.rawId() << ";x_{tr} - x_{hit} [cm]";
706  yhistotitle << "Y Residual for module " << id.rawId() << ";y_{tr} - y_{hit} [cm]";
707  normhistotitle << "Normalized Residual for module " << id.rawId() << ";x_{tr} - x_{hit}/#sigma";
708  xprimehistotitle << "X' Residual for module " << id.rawId() << ";(x_{tr} - x_{hit})' [cm]";
709  normxprimehistotitle << "Normalized X' Residual for module " << id.rawId() << ";(x_{tr} - x_{hit})'/#sigma";
710  yprimehistotitle << "Y' Residual for module " << id.rawId() << ";(y_{tr} - y_{hit})' [cm]";
711  normyprimehistotitle << "Normalized Y' Residual for module " << id.rawId() << ";(y_{tr} - y_{hit})'/#sigma";
712 
713  if ( moduleLevelProfiles_ ) {
714  localxname << "h_localx_subdet_" << subdetandlayer.first
715  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
716  localyname << "h_localy_subdet_" << subdetandlayer.first
717  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
718  localxtitle << "u local for module " << id.rawId() << "; u_{tr,r}";
719  localytitle << "v local for module " << id.rawId() << "; v_{tr,r}";
720 
721  resxvsxprofilename << "p_residuals_x_vs_x_subdet_" << subdetandlayer.first
722  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
723  resyvsxprofilename << "p_residuals_y_vs_x_subdet_" << subdetandlayer.first
724  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
725  resxvsyprofilename << "p_residuals_x_vs_y_subdet_" << subdetandlayer.first
726  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
727  resyvsyprofilename << "p_residuals_y_vs_y_subdet_" << subdetandlayer.first
728  << wheel_or_layer << subdetandlayer.second << "_module_" << id.rawId();
729  resxvsxprofiletitle << "U Residual vs u for module " << id.rawId() << "; u_{tr,r} ;(u_{tr} - u_{hit})/tan#alpha [cm]";
730  resyvsxprofiletitle << "V Residual vs u for module " << id.rawId() << "; u_{tr,r} ;(v_{tr} - v_{hit})/tan#beta [cm]";
731  resxvsyprofiletitle << "U Residual vs v for module " << id.rawId() << "; v_{tr,r} ;(u_{tr} - u_{hit})/tan#alpha [cm]";
732  resyvsyprofiletitle << "V Residual vs v for module " << id.rawId() << "; v_{tr,r} ;(v_{tr} - v_{hit})/tan#beta [cm]";
733  }
734 
735  if( this->isDetOrDetUnit( subtype ) ) {
736  ModuleHistos &histStruct = this->getHistStructFromMap(id);
737  int nbins = 0;
738  double xmin = 0., xmax = 0.;
739  double ymin = -0.1, ymax = 0.1;
740 
741  // do not allow transient hists in DQM mode
742  bool moduleLevelHistsTransient(moduleLevelHistsTransient_);
743  if (dqmMode_) moduleLevelHistsTransient = false;
744 
745  // decide via cfg if hists in local coordinates should be booked
746  if(lCoorHistOn_) {
747  this->getBinning(id.subdetId(), XResidual, nbins, xmin, xmax);
748  histStruct.ResHisto = this->bookTH1F(moduleLevelHistsTransient, tfd,
749  histoname.str().c_str(),histotitle.str().c_str(),
750  nbins, xmin, xmax);
751  this->getBinning(id.subdetId(), NormXResidual, nbins, xmin, xmax);
752  histStruct.NormResHisto = this->bookTH1F(moduleLevelHistsTransient, tfd,
753  normhistoname.str().c_str(),normhistotitle.str().c_str(),
754  nbins, xmin, xmax);
755  }
756  this->getBinning(id.subdetId(), XprimeResidual, nbins, xmin, xmax);
757  histStruct.ResXprimeHisto = this->bookTH1F(moduleLevelHistsTransient, tfd,
758  xprimehistoname.str().c_str(),xprimehistotitle.str().c_str(),
759  nbins, xmin, xmax);
760  this->getBinning(id.subdetId(), NormXprimeResidual, nbins, xmin, xmax);
761  histStruct.NormResXprimeHisto = this->bookTH1F(moduleLevelHistsTransient, tfd,
762  normxprimehistoname.str().c_str(),normxprimehistotitle.str().c_str(),
763  nbins, xmin, xmax);
764 
765  if ( moduleLevelProfiles_ ) {
766  this->getBinning(id.subdetId(), XResidualProfile, nbins, xmin, xmax);
767 
768  histStruct.LocalX = this->bookTH1F(moduleLevelHistsTransient, tfd,
769  localxname.str().c_str(),localxtitle.str().c_str(),
770  nbins, xmin, xmax);
771  histStruct.LocalY = this->bookTH1F(moduleLevelHistsTransient, tfd,
772  localyname.str().c_str(),localytitle.str().c_str(),
773  nbins, xmin, xmax);
774  histStruct.ResXvsXProfile = this->bookTProfile(moduleLevelHistsTransient, tfd,
775  resxvsxprofilename.str().c_str(),resxvsxprofiletitle.str().c_str(),
776  nbins, xmin, xmax, ymin, ymax);
777  histStruct.ResXvsXProfile->Sumw2(); // to be filled with weights, so uncertainties need sum of square of weights
778  histStruct.ResXvsYProfile = this->bookTProfile(moduleLevelHistsTransient, tfd,
779  resxvsyprofilename.str().c_str(),resxvsyprofiletitle.str().c_str(),
780  nbins, xmin, xmax, ymin, ymax);
781  histStruct.ResXvsYProfile->Sumw2(); // to be filled with weights, so uncertainties need sum of square of weights
782  }
783 
784  if( this->isPixel(subdetandlayer.first) || stripYResiduals_ ) {
785  this->getBinning(id.subdetId(), YprimeResidual, nbins, xmin, xmax);
786  histStruct.ResYprimeHisto = this->bookTH1F(moduleLevelHistsTransient, tfd,
787  yprimehistoname.str().c_str(),yprimehistotitle.str().c_str(),
788  nbins, xmin, xmax);
789  if (lCoorHistOn_) { // un-primed y-residual
790  this->getBinning(id.subdetId(), YResidual, nbins, xmin, xmax);
791  histStruct.ResYHisto = this->bookTH1F(moduleLevelHistsTransient, tfd,
792  yhistoname.str().c_str(), yhistotitle.str().c_str(),
793  nbins, xmin, xmax);
794  }
795  this->getBinning(id.subdetId(), NormYprimeResidual, nbins, xmin, xmax);
796  histStruct.NormResYprimeHisto = this->bookTH1F(moduleLevelHistsTransient, tfd,
797  normyprimehistoname.str().c_str(),normyprimehistotitle.str().c_str(),
798  nbins, xmin, xmax);
799  // Here we could add un-primed normalised y-residuals if(lCoorHistOn_)...
800  if ( moduleLevelProfiles_ ) {
801  this->getBinning(id.subdetId(), YResidualProfile, nbins, xmin, xmax);
802 
803  histStruct.ResYvsXProfile = this->bookTProfile(moduleLevelHistsTransient, tfd,
804  resyvsxprofilename.str().c_str(),resyvsxprofiletitle.str().c_str(),
805  nbins, xmin, xmax, ymin, ymax);
806  histStruct.ResYvsXProfile->Sumw2(); // to be filled with weights, so uncertainties need sum of square of weights
807  histStruct.ResYvsYProfile = this->bookTProfile(moduleLevelHistsTransient, tfd,
808  resyvsyprofilename.str().c_str(),resyvsyprofiletitle.str().c_str(),
809  nbins, xmin, xmax, ymin, ymax);
810  histStruct.ResYvsYProfile->Sumw2(); // to be filled with weights, so uncertainties need sum of square of weights
811  }
812  }
813  }
814 }
815 
816 
817 TH1* TrackerOfflineValidation::bookTH1F(bool isTransient, DirectoryWrapper& tfd, const char* histName, const char* histTitle,
818  int nBinsX, double lowX, double highX)
819 {
820  if (isTransient) {
821  vDeleteObjects_.push_back(new TH1F(histName, histTitle, nBinsX, lowX, highX));
822  return vDeleteObjects_.back(); // return last element of vector
823  }
824  else
825  return tfd.make<TH1F>(histName, histTitle, nBinsX, lowX, highX);
826 }
827 
828 TProfile* TrackerOfflineValidation::bookTProfile(bool isTransient, DirectoryWrapper& tfd, const char* histName, const char* histTitle,
829  int nBinsX, double lowX, double highX)
830 {
831  if (isTransient) {
832  TProfile * profile = new TProfile(histName, histTitle, nBinsX, lowX, highX);
833  vDeleteObjects_.push_back(profile);
834  return profile;
835  }
836  else
837  return (TProfile*)tfd.make<TProfile>(histName, histTitle, nBinsX, lowX, highX);
838 }
839 
840 
841 TProfile* TrackerOfflineValidation::bookTProfile(bool isTransient, DirectoryWrapper& tfd, const char* histName, const char* histTitle,
842  int nBinsX, double lowX, double highX, double lowY, double highY)
843 {
844  if (isTransient) {
845  TProfile * profile = new TProfile(histName, histTitle, nBinsX, lowX, highX, lowY, highY);
846  vDeleteObjects_.push_back(profile);
847  return profile;
848  }
849  else
850  return (TProfile*)tfd.make<TProfile>(histName, histTitle, nBinsX, lowX, highX, lowY, highY);
851 }
852 
854 {
855  return (subDetId == StripSubdetector::TIB ||
856  subDetId == StripSubdetector::TOB ||
857  subDetId == PixelSubdetector::PixelBarrel );
858 }
859 
860 
862 {
863  return ( subDetId == StripSubdetector::TID ||
864  subDetId == StripSubdetector::TEC ||
865  subDetId == PixelSubdetector::PixelEndcap );
866 }
867 
868 
870 {
871  return (subDetId == PixelSubdetector::PixelBarrel ||
872  subDetId == PixelSubdetector::PixelEndcap );
873 }
874 
875 
877 {
878  return ( type == align::AlignableDet ||
879  type == align::AlignableDetUnit );
880 }
881 
882 
883 void
886  int& nBinsX, double& lowerBoundX, double& upperBoundX)
887 {
888  // determine if
889  const bool isPixel = this->isPixel(subDetId);
890 
891  edm::ParameterSet binningPSet;
892 
893  switch(residualType)
894  {
895  case XResidual :
896  if(isPixel) binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1XResPixelModules");
897  else binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1XResStripModules");
898  break;
899  case NormXResidual :
900  if(isPixel) binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1NormXResPixelModules");
901  else binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1NormXResStripModules");
902  break;
903  case XprimeResidual :
904  if(isPixel) binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1XprimeResPixelModules");
905  else binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1XprimeResStripModules");
906  break;
907  case NormXprimeResidual :
908  if(isPixel) binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1NormXprimeResPixelModules");
909  else binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1NormXprimeResStripModules");
910  break;
911  case YResidual : // borrow y-residual binning from yprime
912  case YprimeResidual :
913  if(isPixel) binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1YResPixelModules");
914  else binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1YResStripModules");
915  break;
916  /* case NormYResidual :*/
917  case NormYprimeResidual :
918  if(isPixel) binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1NormYResPixelModules");
919  else binningPSet = parSet_.getParameter<edm::ParameterSet>("TH1NormYResStripModules");
920  break;
921  case XResidualProfile :
922  if(isPixel) binningPSet = parSet_.getParameter<edm::ParameterSet>("TProfileXResPixelModules");
923  else binningPSet = parSet_.getParameter<edm::ParameterSet>("TProfileXResStripModules");
924  break;
925  case YResidualProfile :
926  if(isPixel) binningPSet = parSet_.getParameter<edm::ParameterSet>("TProfileYResPixelModules");
927  else binningPSet = parSet_.getParameter<edm::ParameterSet>("TProfileYResStripModules");
928  break;
929  }
930  nBinsX = binningPSet.getParameter<int32_t>("Nbinx");
931  lowerBoundX = binningPSet.getParameter<double>("xmin");
932  upperBoundX = binningPSet.getParameter<double>("xmax");
933 }
934 
935 
936 void
937 TrackerOfflineValidation::setSummaryBin(int bin, TH1* targetHist, TH1* sourceHist)
938 {
939  if(targetHist && sourceHist) {
940  targetHist->SetBinContent(bin, sourceHist->GetMean(1));
941  if(useFwhm_) targetHist->SetBinError(bin, Fwhm(sourceHist)/2.);
942  else targetHist->SetBinError(bin, sourceHist->GetRMS(1) );
943  }
944  else return;
945 }
946 
947 
948 void
950  SummaryContainer& sourceContainer)
951 {
952  summaryBins_.emplace_back(bin, targetContainer.summaryXResiduals_, sourceContainer.sumXResiduals_);
953  summaryBins_.emplace_back(bin, targetContainer.summaryNormXResiduals_, sourceContainer.sumNormXResiduals_);
954  // If no y-residual hists, just returns:
955  summaryBins_.emplace_back(bin, targetContainer.summaryYResiduals_, sourceContainer.sumYResiduals_);
956  summaryBins_.emplace_back(bin, targetContainer.summaryNormYResiduals_, sourceContainer.sumNormYResiduals_);
957 }
958 
959 
960 void
962  SummaryContainer& targetContainer,
963  ModuleHistos& sourceContainer)
964 {
965  // takes two summary Containers and sets summaryBins for all histograms
966  summaryBins_.emplace_back(bin, targetContainer.summaryXResiduals_, sourceContainer.ResXprimeHisto);
967  summaryBins_.emplace_back(bin, targetContainer.summaryNormXResiduals_, sourceContainer.NormResXprimeHisto);
968  if( this->isPixel(subDetId) || stripYResiduals_ ) {
969  summaryBins_.emplace_back(bin, targetContainer.summaryYResiduals_, sourceContainer.ResYprimeHisto);
970  summaryBins_.emplace_back(bin, targetContainer.summaryNormYResiduals_, sourceContainer.NormResYprimeHisto);
971  }
972 }
973 
974 
977 {
978  // get a struct with histograms from the respective map
979  // if no object exist, the reference is automatically created by the map
980  // throw exception if non-tracker id is passed
981  uint subdetid = detid.subdetId();
982  if(subdetid == PixelSubdetector::PixelBarrel ) {
983  return mPxbResiduals_[detid.rawId()];
984  } else if (subdetid == PixelSubdetector::PixelEndcap) {
985  return mPxeResiduals_[detid.rawId()];
986  } else if(subdetid == StripSubdetector::TIB) {
987  return mTibResiduals_[detid.rawId()];
988  } else if(subdetid == StripSubdetector::TID) {
989  return mTidResiduals_[detid.rawId()];
990  } else if(subdetid == StripSubdetector::TOB) {
991  return mTobResiduals_[detid.rawId()];
992  } else if(subdetid == StripSubdetector::TEC) {
993  return mTecResiduals_[detid.rawId()];
994  } else {
995  throw cms::Exception("Geometry Error")
996  << "[TrackerOfflineValidation] Error, tried to get reference for non-tracker subdet " << subdetid
997  << " from detector " << detid.det();
998  return mPxbResiduals_[0];
999  }
1000 }
1001 
1002 
1003 // ------------ method called to for each event ------------
1004 void
1006 {
1007  if (useOverflowForRMS_)TH1::StatOverflows(kTRUE);
1008  this->checkBookHists(iSetup); // check whether hists are booked and do so if not yet done
1009 
1010  std::vector<TrackerValidationVariables::AVTrackStruct> vTrackstruct;
1011  avalidator_.fillTrackQuantities(iEvent, iSetup, vTrackstruct);
1012 
1013  for (std::vector<TrackerValidationVariables::AVTrackStruct>::const_iterator itT = vTrackstruct.begin();
1014  itT != vTrackstruct.end();
1015  ++itT) {
1016 
1017  // Fill 1D track histos
1018  static const int etaindex = this->GetIndex(vTrackHistos_,"h_tracketa");
1019  vTrackHistos_[etaindex]->Fill(itT->eta);
1020  static const int phiindex = this->GetIndex(vTrackHistos_,"h_trackphi");
1021  vTrackHistos_[phiindex]->Fill(itT->phi);
1022  static const int numOfValidHitsindex = this->GetIndex(vTrackHistos_,"h_trackNumberOfValidHits");
1023  vTrackHistos_[numOfValidHitsindex]->Fill(itT->numberOfValidHits);
1024  static const int numOfLostHitsindex = this->GetIndex(vTrackHistos_,"h_trackNumberOfLostHits");
1025  vTrackHistos_[numOfLostHitsindex]->Fill(itT->numberOfLostHits);
1026  static const int kappaindex = this->GetIndex(vTrackHistos_,"h_curvature");
1027  vTrackHistos_[kappaindex]->Fill(itT->kappa);
1028  static const int kappaposindex = this->GetIndex(vTrackHistos_,"h_curvature_pos");
1029  if (itT->charge > 0)
1030  vTrackHistos_[kappaposindex]->Fill(fabs(itT->kappa));
1031  static const int kappanegindex = this->GetIndex(vTrackHistos_,"h_curvature_neg");
1032  if (itT->charge < 0)
1033  vTrackHistos_[kappanegindex]->Fill(fabs(itT->kappa));
1034  static const int normchi2index = this->GetIndex(vTrackHistos_,"h_normchi2");
1035  vTrackHistos_[normchi2index]->Fill(itT->normchi2);
1036  static const int chi2index = this->GetIndex(vTrackHistos_,"h_chi2");
1037  vTrackHistos_[chi2index]->Fill(itT->chi2);
1038  static const int chi2Probindex = this->GetIndex(vTrackHistos_,"h_chi2Prob");
1039  vTrackHistos_[chi2Probindex]->Fill(itT->chi2Prob);
1040  static const int ptindex = this->GetIndex(vTrackHistos_,"h_pt");
1041  vTrackHistos_[ptindex]->Fill(itT->pt);
1042  if (itT->ptError != 0.) {
1043  static const int ptResolutionindex = this->GetIndex(vTrackHistos_,"h_ptResolution");
1044  vTrackHistos_[ptResolutionindex]->Fill(itT->ptError/itT->pt);
1045  }
1046  // Fill track profiles
1047  static const int d0phiindex = this->GetIndex(vTrackProfiles_,"p_d0_vs_phi");
1048  vTrackProfiles_[d0phiindex]->Fill(itT->phi,itT->d0);
1049  static const int dzphiindex = this->GetIndex(vTrackProfiles_,"p_dz_vs_phi");
1050  vTrackProfiles_[dzphiindex]->Fill(itT->phi,itT->dz);
1051  static const int d0etaindex = this->GetIndex(vTrackProfiles_,"p_d0_vs_eta");
1052  vTrackProfiles_[d0etaindex]->Fill(itT->eta,itT->d0);
1053  static const int dzetaindex = this->GetIndex(vTrackProfiles_,"p_dz_vs_eta");
1054  vTrackProfiles_[dzetaindex]->Fill(itT->eta,itT->dz);
1055  static const int chiphiindex = this->GetIndex(vTrackProfiles_,"p_chi2_vs_phi");
1056  vTrackProfiles_[chiphiindex]->Fill(itT->phi,itT->chi2);
1057  static const int chiProbphiindex = this->GetIndex(vTrackProfiles_,"p_chi2Prob_vs_phi");
1058  vTrackProfiles_[chiProbphiindex]->Fill(itT->phi,itT->chi2Prob);
1059  static const int chiProbabsd0index = this->GetIndex(vTrackProfiles_,"p_chi2Prob_vs_d0");
1060  vTrackProfiles_[chiProbabsd0index]->Fill(fabs(itT->d0),itT->chi2Prob);
1061  static const int normchiphiindex = this->GetIndex(vTrackProfiles_,"p_normchi2_vs_phi");
1062  vTrackProfiles_[normchiphiindex]->Fill(itT->phi,itT->normchi2);
1063  static const int chietaindex = this->GetIndex(vTrackProfiles_,"p_chi2_vs_eta");
1064  vTrackProfiles_[chietaindex]->Fill(itT->eta,itT->chi2);
1065  static const int normchiptindex = this->GetIndex(vTrackProfiles_,"p_normchi2_vs_pt");
1066  vTrackProfiles_[normchiptindex]->Fill(itT->pt,itT->normchi2);
1067  static const int normchipindex = this->GetIndex(vTrackProfiles_,"p_normchi2_vs_p");
1068  vTrackProfiles_[normchipindex]->Fill(itT->p,itT->normchi2);
1069  static const int chiProbetaindex = this->GetIndex(vTrackProfiles_,"p_chi2Prob_vs_eta");
1070  vTrackProfiles_[chiProbetaindex]->Fill(itT->eta,itT->chi2Prob);
1071  static const int normchietaindex = this->GetIndex(vTrackProfiles_,"p_normchi2_vs_eta");
1072  vTrackProfiles_[normchietaindex]->Fill(itT->eta,itT->normchi2);
1073  static const int kappaphiindex = this->GetIndex(vTrackProfiles_,"p_kappa_vs_phi");
1074  vTrackProfiles_[kappaphiindex]->Fill(itT->phi,itT->kappa);
1075  static const int kappaetaindex = this->GetIndex(vTrackProfiles_,"p_kappa_vs_eta");
1076  vTrackProfiles_[kappaetaindex]->Fill(itT->eta,itT->kappa);
1077  static const int ptResphiindex = this->GetIndex(vTrackProfiles_,"p_ptResolution_vs_phi");
1078  vTrackProfiles_[ptResphiindex]->Fill(itT->phi,itT->ptError/itT->pt);
1079  static const int ptResetaindex = this->GetIndex(vTrackProfiles_,"p_ptResolution_vs_eta");
1080  vTrackProfiles_[ptResetaindex]->Fill(itT->eta,itT->ptError/itT->pt);
1081 
1082  // Fill 2D track histos
1083  static const int d0phiindex_2d = this->GetIndex(vTrack2DHistos_,"h2_d0_vs_phi");
1084  vTrack2DHistos_[d0phiindex_2d]->Fill(itT->phi,itT->d0);
1085  static const int dzphiindex_2d = this->GetIndex(vTrack2DHistos_,"h2_dz_vs_phi");
1086  vTrack2DHistos_[dzphiindex_2d]->Fill(itT->phi,itT->dz);
1087  static const int d0etaindex_2d = this->GetIndex(vTrack2DHistos_,"h2_d0_vs_eta");
1088  vTrack2DHistos_[d0etaindex_2d]->Fill(itT->eta,itT->d0);
1089  static const int dzetaindex_2d = this->GetIndex(vTrack2DHistos_,"h2_dz_vs_eta");
1090  vTrack2DHistos_[dzetaindex_2d]->Fill(itT->eta,itT->dz);
1091  static const int chiphiindex_2d = this->GetIndex(vTrack2DHistos_,"h2_chi2_vs_phi");
1092  vTrack2DHistos_[chiphiindex_2d]->Fill(itT->phi,itT->chi2);
1093  static const int chiProbphiindex_2d = this->GetIndex(vTrack2DHistos_,"h2_chi2Prob_vs_phi");
1094  vTrack2DHistos_[chiProbphiindex_2d]->Fill(itT->phi,itT->chi2Prob);
1095  static const int chiProbabsd0index_2d = this->GetIndex(vTrack2DHistos_,"h2_chi2Prob_vs_d0");
1096  vTrack2DHistos_[chiProbabsd0index_2d]->Fill(fabs(itT->d0),itT->chi2Prob);
1097  static const int normchiphiindex_2d = this->GetIndex(vTrack2DHistos_,"h2_normchi2_vs_phi");
1098  vTrack2DHistos_[normchiphiindex_2d]->Fill(itT->phi,itT->normchi2);
1099  static const int chietaindex_2d = this->GetIndex(vTrack2DHistos_,"h2_chi2_vs_eta");
1100  vTrack2DHistos_[chietaindex_2d]->Fill(itT->eta,itT->chi2);
1101  static const int chiProbetaindex_2d = this->GetIndex(vTrack2DHistos_,"h2_chi2Prob_vs_eta");
1102  vTrack2DHistos_[chiProbetaindex_2d]->Fill(itT->eta,itT->chi2Prob);
1103  static const int normchietaindex_2d = this->GetIndex(vTrack2DHistos_,"h2_normchi2_vs_eta");
1104  vTrack2DHistos_[normchietaindex_2d]->Fill(itT->eta,itT->normchi2);
1105  static const int kappaphiindex_2d = this->GetIndex(vTrack2DHistos_,"h2_kappa_vs_phi");
1106  vTrack2DHistos_[kappaphiindex_2d]->Fill(itT->phi,itT->kappa);
1107  static const int kappaetaindex_2d = this->GetIndex(vTrack2DHistos_,"h2_kappa_vs_eta");
1108  vTrack2DHistos_[kappaetaindex_2d]->Fill(itT->eta,itT->kappa);
1109  static const int normchi2kappa_2d = this->GetIndex(vTrack2DHistos_,"h2_normchi2_vs_kappa");
1110  vTrack2DHistos_[normchi2kappa_2d]->Fill(itT->normchi2,itT->kappa);
1111 
1112  // hit quantities: residuals, normalized residuals
1113  for (std::vector<TrackerValidationVariables::AVHitStruct>::const_iterator itH = itT->hits.begin();
1114  itH != itT->hits.end();
1115  ++itH) {
1116 
1117  DetId detid(itH->rawDetId);
1118  ModuleHistos &histStruct = this->getHistStructFromMap(detid);
1119 
1120  // fill histos in local coordinates if set in cf
1121  if (lCoorHistOn_) {
1122  histStruct.ResHisto->Fill(itH->resX);
1123  if(itH->resErrX != 0) histStruct.NormResHisto->Fill(itH->resX/itH->resErrX);
1124  if (this->isPixel(detid.subdetId()) || stripYResiduals_ ) {
1125  histStruct.ResYHisto->Fill(itH->resY);
1126  // here add un-primed normalised y-residuals if wanted
1127  }
1128  }
1129  if (itH->resXprime != -999.) {
1130  histStruct.ResXprimeHisto->Fill(itH->resXprime);
1131 
1132  /******************************* Fill 2-D histo ResX vs momenta *****************************/
1133  if (detid.subdetId() == PixelSubdetector::PixelBarrel) {
1134  static const int resXvsPindex_2d = this->GetIndex(vTrack2DHistos_,"p_vs_resXprime_pixB");
1135  vTrack2DHistos_[resXvsPindex_2d]->Fill(itT->p,itH->resXprime);
1136  }
1137  if (detid.subdetId() == PixelSubdetector::PixelEndcap) {
1138  static const int resXvsPindex_2d = this->GetIndex(vTrack2DHistos_,"p_vs_resXprime_pixE");
1139  vTrack2DHistos_[resXvsPindex_2d]->Fill(itT->p,itH->resXprime);
1140  }
1141  if (detid.subdetId() == StripSubdetector::TIB) {
1142  static const int resXvsPindex_2d = this->GetIndex(vTrack2DHistos_,"p_vs_resXprime_TIB");
1143  vTrack2DHistos_[resXvsPindex_2d]->Fill(itT->p,itH->resXprime);
1144  }
1145  if (detid.subdetId() == StripSubdetector::TID) {
1146  static const int resXvsPindex_2d = this->GetIndex(vTrack2DHistos_,"p_vs_resXprime_TID");
1147  vTrack2DHistos_[resXvsPindex_2d]->Fill(itT->p,itH->resXprime);
1148  }
1149  if (detid.subdetId() == StripSubdetector::TOB) {
1150  static const int resXvsPindex_2d = this->GetIndex(vTrack2DHistos_,"p_vs_resXprime_TOB");
1151  vTrack2DHistos_[resXvsPindex_2d]->Fill(itT->p,itH->resXprime);
1152  }
1153  if (detid.subdetId() == StripSubdetector::TEC) {
1154  static const int resXvsPindex_2d = this->GetIndex(vTrack2DHistos_,"p_vs_resXprime_TEC");
1155  vTrack2DHistos_[resXvsPindex_2d]->Fill(itT->p,itH->resXprime);
1156  }
1157  /******************************************/
1158 
1159  if ( moduleLevelProfiles_ && itH->inside ) {
1160  float tgalpha = tan(itH->localAlpha);
1161  if ( fabs(tgalpha)!=0 ){
1162  histStruct.LocalX->Fill(itH->localXnorm, tgalpha*tgalpha);
1163  histStruct.LocalY->Fill(itH->localYnorm, tgalpha*tgalpha);
1164 /* if (this->isEndCap(detid.subdetId()) && !this->isPixel(detid.subdetId())) {
1165  if((itH->resX)*(itH->resXprime)>0){
1166  histStruct.ResXvsXProfile->Fill(itH->localXnorm, itH->resXatTrkY/tgalpha, tgalpha*tgalpha);
1167  histStruct.ResXvsYProfile->Fill(itH->localYnorm, itH->resXatTrkY/tgalpha, tgalpha*tgalpha);
1168  } else {
1169  histStruct.ResXvsXProfile->Fill(itH->localXnorm, (-1)*itH->resXatTrkY/tgalpha, tgalpha*tgalpha);
1170  histStruct.ResXvsYProfile->Fill(itH->localYnorm, (-1)*itH->resXatTrkY/tgalpha, tgalpha*tgalpha);
1171  }
1172 
1173  }else {
1174 */
1175  histStruct.ResXvsXProfile->Fill(itH->localXnorm, itH->resXatTrkY/tgalpha, tgalpha*tgalpha);
1176  histStruct.ResXvsYProfile->Fill(itH->localYnorm, itH->resXatTrkY/tgalpha, tgalpha*tgalpha);
1177 
1178 // }
1179 
1180  }
1181  }
1182 
1183  if(itH->resXprimeErr != 0 && itH->resXprimeErr != -999 ) {
1184  histStruct.NormResXprimeHisto->Fill(itH->resXprime/itH->resXprimeErr);
1185  }
1186  }
1187 
1188  if (itH->resYprime != -999.) {
1189  if (this->isPixel(detid.subdetId()) || stripYResiduals_ ) {
1190  histStruct.ResYprimeHisto->Fill(itH->resYprime);
1191 
1192  /******************************* Fill 2-D histo ResY vs momenta *****************************/
1193  if (detid.subdetId() == PixelSubdetector::PixelBarrel) {
1194  static const int resYvsPindex_2d = this->GetIndex(vTrack2DHistos_,"p_vs_resYprime_pixB");
1195  vTrack2DHistos_[resYvsPindex_2d]->Fill(itT->p,itH->resYprime);
1196  }
1197  if (detid.subdetId() == PixelSubdetector::PixelEndcap) {
1198  static const int resYvsPindex_2d = this->GetIndex(vTrack2DHistos_,"p_vs_resYprime_pixE");
1199  vTrack2DHistos_[resYvsPindex_2d]->Fill(itT->p,itH->resYprime);
1200  }
1201  /******************************************/
1202 
1203  if ( moduleLevelProfiles_ && itH->inside ) {
1204  float tgbeta = tan(itH->localBeta);
1205  if ( fabs(tgbeta)!=0 ){
1206 /* if (this->isEndCap(detid.subdetId()) && !this->isPixel(detid.subdetId())) {
1207 
1208  if((itH->resY)*(itH->resYprime)>0){
1209  histStruct.ResYvsXProfile->Fill(itH->localXnorm, itH->resYprime/tgbeta, tgbeta*tgbeta);
1210  histStruct.ResYvsYProfile->Fill(itH->localYnorm, itH->resYprime/tgbeta, tgbeta*tgbeta);
1211  } else {
1212  histStruct.ResYvsXProfile->Fill(itH->localXnorm, (-1)*itH->resYprime/tgbeta, tgbeta*tgbeta);
1213  histStruct.ResYvsYProfile->Fill(itH->localYnorm, (-1)*itH->resYprime/tgbeta, tgbeta*tgbeta);
1214  }
1215 
1216  }else {
1217 */
1218  histStruct.ResYvsXProfile->Fill(itH->localXnorm, itH->resY/tgbeta, tgbeta*tgbeta);
1219  histStruct.ResYvsYProfile->Fill(itH->localYnorm, itH->resY/tgbeta, tgbeta*tgbeta);
1220 // }
1221  }
1222  }
1223 
1224  if (itH->resYprimeErr != 0 && itH->resYprimeErr != -999. ) {
1225  histStruct.NormResYprimeHisto->Fill(itH->resYprime/itH->resYprimeErr);
1226  }
1227  }
1228  }
1229 
1230  } // finish loop over hit quantities
1231  } // finish loop over track quantities
1232 
1233  if (useOverflowForRMS_) TH1::StatOverflows(kFALSE);
1234 }
1235 
1236 
1237 // ------------ method called once each job just after ending the event loop ------------
1238 void
1240 {
1241  if (!tkGeom_.product()) return;
1242 
1243  static const int kappadiffindex = this->GetIndex(vTrackHistos_,"h_diff_curvature");
1244  vTrackHistos_[kappadiffindex]->Add(vTrackHistos_[this->GetIndex(vTrackHistos_,"h_curvature_neg")],
1245  vTrackHistos_[this->GetIndex(vTrackHistos_,"h_curvature_pos")],-1,1);
1246 
1247  // Collate Information for Subdetectors
1248  // create summary histograms recursively
1249  this->collateSummaryHists();
1250 
1251  if (dqmMode_) return;
1252  // Should be excluded in dqmMode, since TTree is not usable
1253  // In dqmMode tree operations are are sourced out to the additional module TrackerOfflineValidationSummary
1254 
1256  TTree *tree = fs->make<TTree>("TkOffVal","TkOffVal");
1257 
1258  TkOffTreeVariables *treeMemPtr = new TkOffTreeVariables;
1259  // We create branches for all members of 'TkOffTreeVariables' (even if not needed).
1260  // This works because we have a dictionary for 'TkOffTreeVariables'
1261  // (see src/classes_def.xml and src/classes.h):
1262  tree->Branch("TkOffTreeVariables", &treeMemPtr); // address of pointer!
1263 
1264  this->fillTree(*tree, *treeMemPtr, mPxbResiduals_);
1265  this->fillTree(*tree, *treeMemPtr, mPxeResiduals_);
1266  this->fillTree(*tree, *treeMemPtr, mTibResiduals_);
1267  this->fillTree(*tree, *treeMemPtr, mTidResiduals_);
1268  this->fillTree(*tree, *treeMemPtr, mTobResiduals_);
1269  this->fillTree(*tree, *treeMemPtr, mTecResiduals_);
1270 
1271  delete treeMemPtr; treeMemPtr = 0;
1272 }
1273 
1274 
1275 void
1277  std::vector<TrackerOfflineValidation::SummaryContainer>& vLevelProfiles)
1278 {
1279  std::vector<Alignable*> alivec(ali.components());
1280  if( this->isDetOrDetUnit((alivec)[0]->alignableObjectId()) ) return;
1281 
1282  for(int iComp=0, iCompEnd = ali.components().size();iComp < iCompEnd; ++iComp) {
1283  std::vector< TrackerOfflineValidation::SummaryContainer > vProfiles;
1284  std::string structurename = AlignableObjectId::idToString((alivec)[iComp]->alignableObjectId());
1285 
1286  LogDebug("TrackerOfflineValidation") << "StructureName = " << structurename;
1287  std::stringstream dirname;
1288  dirname << structurename;
1289 
1290  // add no suffix counter to strip and pixel -> just aesthetics
1291  if (structurename != "Strip" && structurename != "Pixel") dirname << "_" << iComp+1;
1292 
1293  if( !(this->isDetOrDetUnit( (alivec)[iComp]->alignableObjectId()) )
1294  || (alivec)[0]->components().size() > 1 ) {
1295  DirectoryWrapper f(tfd,dirname.str(),moduleDirectory_,dqmMode_);
1296  this->prepareSummaryHists( f, *(alivec)[iComp], vProfiles);
1297  vLevelProfiles.push_back(this->bookSummaryHists(tfd, *(alivec[iComp]), ali.alignableObjectId(), iComp+1));
1298  TH1 *hX = vLevelProfiles[iComp].sumXResiduals_;
1299  TH1 *hNormX = vLevelProfiles[iComp].sumNormXResiduals_;
1300  TH1 *hY = vLevelProfiles[iComp].sumYResiduals_;
1301  TH1 *hNormY = vLevelProfiles[iComp].sumNormYResiduals_;
1302  TH1 *pXX = vLevelProfiles[iComp].sumResXvsXProfile_;
1303  TH1 *pXY = vLevelProfiles[iComp].sumResXvsYProfile_;
1304  TH1 *pYX = vLevelProfiles[iComp].sumResYvsXProfile_;
1305  TH1 *pYY = vLevelProfiles[iComp].sumResYvsYProfile_;
1306  for(uint n = 0; n < vProfiles.size(); ++n) {
1307  this->summarizeBinInContainer(n+1, vLevelProfiles[iComp], vProfiles[n]);
1308  sumHistStructure_.emplace_back(hX, vProfiles[n].sumXResiduals_);
1309  sumHistStructure_.emplace_back(hNormX, vProfiles[n].sumNormXResiduals_);
1310  if (hY) sumHistStructure_.emplace_back(hY, vProfiles[n].sumYResiduals_); // only if existing
1311  if (hNormY) sumHistStructure_.emplace_back(hNormY, vProfiles[n].sumNormYResiduals_); // ditto (pxl, stripYResiduals_)
1312  if (pXX) sumHistStructure_.emplace_back(pXX, vProfiles[n].sumResXvsXProfile_);
1313  if (pXY) sumHistStructure_.emplace_back(pXY, vProfiles[n].sumResXvsYProfile_);
1314  if (pYX) sumHistStructure_.emplace_back(pYX, vProfiles[n].sumResYvsXProfile_);
1315  if (pYY) sumHistStructure_.emplace_back(pYY, vProfiles[n].sumResYvsYProfile_);
1316  }
1317  if(dqmMode_)continue; // No fits in dqmMode
1318  //add fit values to stat box
1319  toFit_.push_back(vLevelProfiles[iComp].sumXResiduals_);
1320  toFit_.push_back(vLevelProfiles[iComp].sumNormXResiduals_);
1321  if (hY) toFit_.push_back(hY); // only if existing (pixel or stripYResiduals_)
1322  if (hNormY) toFit_.push_back(hNormY); // ditto
1323  } else {
1324  // nothing to be done for det or detunits
1325  continue;
1326  }
1327  }
1328 }
1329 
1330 void
1332 {
1333  for (std::vector<std::pair<TH1*,TH1*> >::const_iterator it = sumHistStructure_.begin();
1334  it != sumHistStructure_.end();
1335  ++it)
1336  it->first->Add(it->second);
1337 
1338  for (std::vector<std::tuple<int,TH1*,TH1*> >::const_iterator it = summaryBins_.begin();
1339  it != summaryBins_.end();
1340  ++it)
1341  setSummaryBin(std::get<0>(*it), std::get<1>(*it), std::get<2>(*it));
1342 
1343  for (std::vector<TH1*>::const_iterator it = toFit_.begin();
1344  it != toFit_.end();
1345  ++it)
1346  fitResiduals(*it);
1347 }
1348 
1349 
1352  align::StructureType type, int i)
1353 {
1354  const uint aliSize = ali.components().size();
1355  const align::StructureType alitype = ali.alignableObjectId();
1356  const align::StructureType subtype = ali.components()[0]->alignableObjectId();
1357  const char *aliTypeName = AlignableObjectId::idToString(alitype); // lifetime of char* OK
1358  const char *aliSubtypeName = AlignableObjectId::idToString(subtype);
1359  const char *typeName = AlignableObjectId::idToString(type);
1360 
1361  const DetId aliDetId = ali.id();
1362  // y residuals only if pixel or specially requested for strip:
1363  const bool bookResidY = this->isPixel(aliDetId.subdetId()) || stripYResiduals_;
1364 
1365  SummaryContainer sumContainer;
1366 
1367  // Book summary hists with one bin per component,
1368  // but special case for Det with two DetUnit that we want to summarize one level up
1369  // (e.g. in TOBRods with 12 bins for 6 stereo and 6 rphi DetUnit.)
1370  // component of ali is not Det or Det with just one components
1371  const uint subcompSize = ali.components()[0]->components().size();
1372  if (subtype != align::AlignableDet || subcompSize == 1) { // Det with 1 comp. should not exist anymore...
1373  const TString title(Form("Summary for substructures in %s %d;%s;",aliTypeName,i,aliSubtypeName));
1374 
1375  sumContainer.summaryXResiduals_ = tfd.make<TH1F>(Form("h_summaryX%s_%d",aliTypeName,i),
1376  title + "#LT #Delta x' #GT",
1377  aliSize, 0.5, aliSize+0.5);
1378  sumContainer.summaryNormXResiduals_ = tfd.make<TH1F>(Form("h_summaryNormX%s_%d",aliTypeName,i),
1379  title + "#LT #Delta x'/#sigma #GT",
1380  aliSize,0.5,aliSize+0.5);
1381 
1382  if (bookResidY) {
1383  sumContainer.summaryYResiduals_ = tfd.make<TH1F>(Form("h_summaryY%s_%d",aliTypeName,i),
1384  title + "#LT #Delta y' #GT",
1385  aliSize, 0.5, aliSize+0.5);
1386  sumContainer.summaryNormYResiduals_ = tfd.make<TH1F>(Form("h_summaryNormY%s_%d",aliTypeName,i),
1387  title + "#LT #Delta y'/#sigma #GT",
1388  aliSize,0.5,aliSize+0.5);
1389  }
1390 
1391  } else if (subtype == align::AlignableDet && subcompSize > 1) { // fixed: was aliSize before
1392  if (subcompSize != 2) { // strange... expect only 2 DetUnits in DS layers
1393  // this 2 is hardcoded factor 2 in binning below and also assumed later on
1394  edm::LogError("Alignment") << "@SUB=bookSummaryHists"
1395  << "Det with " << subcompSize << " components";
1396  }
1397  // title contains x-title
1398  const TString title(Form("Summary for substructures in %s %d;%s;", aliTypeName, i,
1399  AlignableObjectId::idToString(ali.components()[0]->components()[0]->alignableObjectId())));
1400 
1401  sumContainer.summaryXResiduals_
1402  = tfd.make<TH1F>(Form("h_summaryX%s_%d", aliTypeName, i),
1403  title + "#LT #Delta x' #GT", (2*aliSize), 0.5, 2*aliSize+0.5);
1404  sumContainer.summaryNormXResiduals_
1405  = tfd.make<TH1F>(Form("h_summaryNormX%s_%d", aliTypeName, i),
1406  title + "#LT #Delta x'/#sigma #GT", (2*aliSize), 0.5, 2*aliSize+0.5);
1407 
1408  if (bookResidY) {
1409  sumContainer.summaryYResiduals_
1410  = tfd.make<TH1F>(Form("h_summaryY%s_%d", aliTypeName, i),
1411  title + "#LT #Delta y' #GT", (2*aliSize), 0.5, 2*aliSize+0.5);
1412  sumContainer.summaryNormYResiduals_
1413  = tfd.make<TH1F>(Form("h_summaryNormY%s_%d", aliTypeName, i),
1414  title + "#LT #Delta y'/#sigma #GT", (2*aliSize), 0.5, 2*aliSize+0.5);
1415  }
1416 
1417  } else {
1418  edm::LogError("TrackerOfflineValidation") << "@SUB=TrackerOfflineValidation::bookSummaryHists"
1419  << "No summary histogram for hierarchy level "
1420  << aliTypeName << " in subdet " << aliDetId.subdetId();
1421  }
1422 
1423  // Now book hists that just sum up the residual histograms from lower levels.
1424  // Axis title is copied from lowest level module of structure.
1425  // Should be safe that y-hists are only touched if non-null pointers...
1426  int nbins = 0;
1427  double xmin = 0., xmax = 0.;
1428  const TString sumTitle(Form("Residual for %s %d in %s;", aliTypeName, i, typeName));
1429  const ModuleHistos &xTitHists = this->getHistStructFromMap(aliDetId); // for x-axis titles
1430  this->getBinning(aliDetId.subdetId(), XprimeResidual, nbins, xmin, xmax);
1431 
1432  sumContainer.sumXResiduals_ = tfd.make<TH1F>(Form("h_Xprime_%s_%d", aliTypeName, i),
1433  sumTitle + xTitHists.ResXprimeHisto->GetXaxis()->GetTitle(),
1434  nbins, xmin, xmax);
1435 
1436  this->getBinning(aliDetId.subdetId(), NormXprimeResidual, nbins, xmin, xmax);
1437  sumContainer.sumNormXResiduals_ = tfd.make<TH1F>(Form("h_NormXprime_%s_%d",aliTypeName,i),
1438  sumTitle + xTitHists.NormResXprimeHisto->GetXaxis()->GetTitle(),
1439  nbins, xmin, xmax);
1440 
1441  if ( moduleLevelProfiles_ ) {
1442  this->getBinning(aliDetId.subdetId(), XResidualProfile, nbins, xmin, xmax);
1443  sumContainer.sumResXvsXProfile_ = tfd.make<TProfile>(Form("p_resXX_%s_%d",aliTypeName,i),
1444  sumTitle + xTitHists.ResXvsXProfile->GetXaxis()->GetTitle()
1445  + ";" + xTitHists.ResXvsXProfile->GetYaxis()->GetTitle(),
1446  nbins, xmin, xmax);
1447  sumContainer.sumResXvsXProfile_->Sumw2();
1448  sumContainer.sumResXvsYProfile_ = tfd.make<TProfile>(Form("p_resXY_%s_%d",aliTypeName,i),
1449  sumTitle + xTitHists.ResXvsYProfile->GetXaxis()->GetTitle()
1450  + ";" + xTitHists.ResXvsYProfile->GetYaxis()->GetTitle(),
1451  nbins, xmin, xmax);
1452  sumContainer.sumResXvsYProfile_->Sumw2();
1453  }
1454 
1455  if (bookResidY) {
1456  this->getBinning(aliDetId.subdetId(), YprimeResidual, nbins, xmin, xmax);
1457  sumContainer.sumYResiduals_ = tfd.make<TH1F>(Form("h_Yprime_%s_%d",aliTypeName,i),
1458  sumTitle + xTitHists.ResYprimeHisto->GetXaxis()->GetTitle(),
1459  nbins, xmin, xmax);
1460 
1461  this->getBinning(aliDetId.subdetId(), NormYprimeResidual, nbins, xmin, xmax);
1462  sumContainer.sumNormYResiduals_ = tfd.make<TH1F>(Form("h_NormYprime_%s_%d",aliTypeName,i),
1463  sumTitle + xTitHists.NormResYprimeHisto->GetXaxis()->GetTitle(),
1464  nbins, xmin, xmax);
1465 
1466  if ( moduleLevelProfiles_ ) {
1467  this->getBinning(aliDetId.subdetId(), YResidualProfile, nbins, xmin, xmax);
1468  sumContainer.sumResYvsXProfile_ = tfd.make<TProfile>(Form("p_resYX_%s_%d",aliTypeName,i),
1469  sumTitle + xTitHists.ResYvsXProfile->GetXaxis()->GetTitle()
1470  + ";" + xTitHists.ResYvsXProfile->GetYaxis()->GetTitle(),
1471  nbins, xmin, xmax);
1472  sumContainer.sumResYvsXProfile_->Sumw2();
1473  sumContainer.sumResYvsYProfile_ = tfd.make<TProfile>(Form("p_resYY_%s_%d",aliTypeName,i),
1474  sumTitle + xTitHists.ResYvsYProfile->GetXaxis()->GetTitle()
1475  + ";" + xTitHists.ResYvsYProfile->GetYaxis()->GetTitle(),
1476  nbins, xmin, xmax);
1477  sumContainer.sumResYvsYProfile_->Sumw2();
1478  }
1479  }
1480 
1481  // If we are at the lowest level, we already sum up and fill the summary.
1482 
1483  // special case I: For DetUnits and Dets with only one subcomponent start filling summary histos
1484  if( ( subtype == align::AlignableDet && subcompSize == 1) || subtype == align::AlignableDetUnit ) {
1485  for(uint k = 0; k < aliSize; ++k) {
1486  DetId detid = ali.components()[k]->id();
1487  ModuleHistos &histStruct = this->getHistStructFromMap(detid);
1488  this->summarizeBinInContainer(k+1, detid.subdetId(), sumContainer, histStruct);
1489  sumHistStructure_.emplace_back(sumContainer.sumXResiduals_, histStruct.ResXprimeHisto);
1490  sumHistStructure_.emplace_back(sumContainer.sumNormXResiduals_, histStruct.NormResXprimeHisto);
1491  if ( moduleLevelProfiles_ ) {
1492  sumHistStructure_.emplace_back(sumContainer.sumResXvsXProfile_, histStruct.ResXvsXProfile);
1493  sumHistStructure_.emplace_back(sumContainer.sumResXvsYProfile_, histStruct.ResXvsYProfile);
1494  }
1495  if( this->isPixel(detid.subdetId()) || stripYResiduals_ ) {
1496  sumHistStructure_.emplace_back(sumContainer.sumYResiduals_, histStruct.ResYprimeHisto);
1497  sumHistStructure_.emplace_back(sumContainer.sumNormYResiduals_, histStruct.NormResYprimeHisto);
1498  if ( moduleLevelProfiles_ ) {
1499  sumHistStructure_.emplace_back(sumContainer.sumResYvsXProfile_, histStruct.ResYvsXProfile);
1500  sumHistStructure_.emplace_back(sumContainer.sumResYvsYProfile_, histStruct.ResYvsYProfile);
1501  }
1502  }
1503  }
1504  } else if( subtype == align::AlignableDet && subcompSize > 1) { // fixed: was aliSize before
1505  // special case II: Fill summary histos for dets with two detunits
1506  for(uint k = 0; k < aliSize; ++k) {
1507  for(uint j = 0; j < subcompSize; ++j) { // assumes all have same size (as binning does)
1508  DetId detid = ali.components()[k]->components()[j]->id();
1509  ModuleHistos &histStruct = this->getHistStructFromMap(detid);
1510  this->summarizeBinInContainer(2*k+j+1, detid.subdetId(), sumContainer, histStruct );
1511  sumHistStructure_.emplace_back(sumContainer.sumXResiduals_, histStruct.ResXprimeHisto);
1512  sumHistStructure_.emplace_back(sumContainer.sumNormXResiduals_, histStruct.NormResXprimeHisto);
1513  if ( moduleLevelProfiles_ ) {
1514  sumHistStructure_.emplace_back(sumContainer.sumResXvsXProfile_, histStruct.ResXvsXProfile);
1515  sumHistStructure_.emplace_back(sumContainer.sumResXvsYProfile_, histStruct.ResXvsYProfile);
1516  }
1517  if( this->isPixel(detid.subdetId()) || stripYResiduals_ ) {
1518  sumHistStructure_.emplace_back(sumContainer.sumYResiduals_, histStruct.ResYprimeHisto);
1519  sumHistStructure_.emplace_back(sumContainer.sumNormYResiduals_, histStruct.NormResYprimeHisto);
1520  if ( moduleLevelProfiles_ ) {
1521  sumHistStructure_.emplace_back(sumContainer.sumResYvsXProfile_, histStruct.ResYvsXProfile);
1522  sumHistStructure_.emplace_back(sumContainer.sumResYvsYProfile_, histStruct.ResYvsYProfile);
1523  }
1524  }
1525  }
1526  }
1527  }
1528  return sumContainer;
1529 }
1530 
1531 
1532 float
1534 {
1535  float max = hist->GetMaximum();
1536  int left = -1, right = -1;
1537  for(unsigned int i = 1, iEnd = hist->GetNbinsX(); i <= iEnd; ++i) {
1538  if(hist->GetBinContent(i) < max/2. && hist->GetBinContent(i+1) > max/2. && left == -1) {
1539  if(max/2. - hist->GetBinContent(i) < hist->GetBinContent(i+1) - max/2.) {
1540  left = i;
1541  ++i;
1542  } else {
1543  left = i+1;
1544  ++i;
1545  }
1546  }
1547  if(left != -1 && right == -1) {
1548  if(hist->GetBinContent(i) > max/2. && hist->GetBinContent(i+1) < max/2.) {
1549  if( hist->GetBinContent(i) - max/2. < max/2. - hist->GetBinContent(i+1)) {
1550  right = i;
1551  } else {
1552  right = i+1;
1553  }
1554 
1555  }
1556  }
1557  }
1558  return hist->GetXaxis()->GetBinCenter(right) - hist->GetXaxis()->GetBinCenter(left);
1559 }
1560 
1561 
1562 void
1563 TrackerOfflineValidation::setUpTreeMembers(const std::map<int, TrackerOfflineValidation::ModuleHistos>& moduleHist_,
1564  const TrackerGeometry& tkgeom, const TrackerTopology* tTopo)
1565 {
1566 
1567  for(std::map<int, TrackerOfflineValidation::ModuleHistos>::const_iterator it = moduleHist_.begin(),
1568  itEnd= moduleHist_.end(); it != itEnd;++it ) {
1569  TkOffTreeVariables &treeMem = mTreeMembers_[it->first];
1570 
1571  //variables concerning the tracker components/hierarchy levels
1572  DetId detId_ = it->first;
1573  treeMem.moduleId = detId_;
1574  treeMem.subDetId = detId_.subdetId();
1575  treeMem.isDoubleSide =0;
1576 
1577  if(treeMem.subDetId == PixelSubdetector::PixelBarrel){
1578  unsigned int whichHalfBarrel(1), rawId(detId_.rawId()); //DetId does not know about halfBarrels is PXB ...
1579  if( (rawId>=302056964 && rawId<302059300) || (rawId>=302123268 && rawId<302127140) ||
1580  (rawId>=302189572 && rawId<302194980) ) whichHalfBarrel=2;
1581  treeMem.layer = tTopo->pxbLayer(detId_);
1582  treeMem.half = whichHalfBarrel;
1583  treeMem.rod = tTopo->pxbLadder(detId_); // ... so, ladder is not per halfBarrel-Layer, but per barrel-layer!
1584  treeMem.module = tTopo->pxbModule(detId_);
1585  } else if(treeMem.subDetId == PixelSubdetector::PixelEndcap){
1586  unsigned int whichHalfCylinder(1), rawId(detId_.rawId()); //DetId does not kmow about halfCylinders in PXF
1587  if( (rawId>=352394500 && rawId<352406032) || (rawId>=352460036 && rawId<352471568) ||
1588  (rawId>=344005892 && rawId<344017424) || (rawId>=344071428 && rawId<344082960) ) whichHalfCylinder=2;
1589  treeMem.layer = tTopo->pxfDisk(detId_);
1590  treeMem.side = tTopo->pxfSide(detId_);
1591  treeMem.half = whichHalfCylinder;
1592  treeMem.blade = tTopo->pxfBlade(detId_);
1593  treeMem.panel = tTopo->pxfPanel(detId_);
1594  treeMem.module = tTopo->pxfModule(detId_);
1595  } else if(treeMem.subDetId == StripSubdetector::TIB){
1596  unsigned int whichHalfShell(1), rawId(detId_.rawId()); //DetId does not kmow about halfShells in TIB
1597  if ( (rawId>=369120484 && rawId<369120688) || (rawId>=369121540 && rawId<369121776) ||
1598  (rawId>=369136932 && rawId<369137200) || (rawId>=369137988 && rawId<369138288) ||
1599  (rawId>=369153396 && rawId<369153744) || (rawId>=369154436 && rawId<369154800) ||
1600  (rawId>=369169844 && rawId<369170256) || (rawId>=369170900 && rawId<369171344) ||
1601  (rawId>=369124580 && rawId<369124784) || (rawId>=369125636 && rawId<369125872) ||
1602  (rawId>=369141028 && rawId<369141296) || (rawId>=369142084 && rawId<369142384) ||
1603  (rawId>=369157492 && rawId<369157840) || (rawId>=369158532 && rawId<369158896) ||
1604  (rawId>=369173940 && rawId<369174352) || (rawId>=369174996 && rawId<369175440) ) whichHalfShell=2;
1605  treeMem.layer = tTopo->tibLayer(detId_);
1606  treeMem.side = tTopo->tibStringInfo(detId_)[0];
1607  treeMem.half = whichHalfShell;
1608  treeMem.rod = tTopo->tibStringInfo(detId_)[2];
1609  treeMem.outerInner = tTopo->tibStringInfo(detId_)[1];
1610  treeMem.module = tTopo->tibModule(detId_);
1611  treeMem.isStereo = tTopo->tibStereo(detId_);
1612  treeMem.isDoubleSide = tTopo->tibIsDoubleSide(detId_);
1613  } else if(treeMem.subDetId == StripSubdetector::TID){
1614  treeMem.layer = tTopo->tidWheel(detId_);
1615  treeMem.side = tTopo->tidSide(detId_);
1616  treeMem.ring = tTopo->tidRing(detId_);
1617  treeMem.outerInner = tTopo->tidModuleInfo(detId_)[0];
1618  treeMem.module = tTopo->tidModuleInfo(detId_)[1];
1619  treeMem.isStereo = tTopo->tidStereo(detId_);
1620  treeMem.isDoubleSide = tTopo->tidIsDoubleSide(detId_);
1621  } else if(treeMem.subDetId == StripSubdetector::TOB){
1622  treeMem.layer = tTopo->tobLayer(detId_);
1623  treeMem.side = tTopo->tobRodInfo(detId_)[0];
1624  treeMem.rod = tTopo->tobRodInfo(detId_)[1];
1625  treeMem.module = tTopo->tobModule(detId_);
1626  treeMem.isStereo = tTopo->tobStereo(detId_);
1627  treeMem.isDoubleSide = tTopo->tobIsDoubleSide(detId_);
1628  } else if(treeMem.subDetId == StripSubdetector::TEC) {
1629  treeMem.layer = tTopo->tecWheel(detId_);
1630  treeMem.side = tTopo->tecSide(detId_);
1631  treeMem.ring = tTopo->tecRing(detId_);
1632  treeMem.petal = tTopo->tecPetalInfo(detId_)[1];
1633  treeMem.outerInner = tTopo->tecPetalInfo(detId_)[0];
1634  treeMem.module = tTopo->tecModule(detId_);
1635  treeMem.isStereo = tTopo->tecStereo(detId_);
1636  treeMem.isDoubleSide = tTopo->tecIsDoubleSide(detId_);
1637  }
1638 
1639  //variables concerning the tracker geometry
1640  const Surface::PositionType &gPModule = tkgeom.idToDet(detId_)->position();
1641  treeMem.posPhi = gPModule.phi();
1642  treeMem.posEta = gPModule.eta();
1643  treeMem.posR = gPModule.perp();
1644  treeMem.posX = gPModule.x();
1645  treeMem.posY = gPModule.y();
1646  treeMem.posZ = gPModule.z();
1647 
1648  const Surface& surface = tkgeom.idToDet(detId_)->surface();
1649 
1650  //global Orientation of local coordinate system of dets/detUnits
1651  LocalPoint lUDirection(1.,0.,0.), lVDirection(0.,1.,0.), lWDirection(0.,0.,1.);
1652  GlobalPoint gUDirection = surface.toGlobal(lUDirection),
1653  gVDirection = surface.toGlobal(lVDirection),
1654  gWDirection = surface.toGlobal(lWDirection);
1655  double dR(999.), dPhi(999.), dZ(999.);
1657  dR = gWDirection.perp() - gPModule.perp();
1658  dPhi = deltaPhi(gUDirection.phi(),gPModule.phi());
1659  dZ = gVDirection.z() - gPModule.z();
1660  if(dZ>=0.)treeMem.rOrZDirection = 1; else treeMem.rOrZDirection = -1;
1661  }else if(treeMem.subDetId==PixelSubdetector::PixelEndcap){
1662  dR = gUDirection.perp() - gPModule.perp();
1663  dPhi = deltaPhi(gVDirection.phi(),gPModule.phi());
1664  dZ = gWDirection.z() - gPModule.z();
1665  if(dR>=0.)treeMem.rOrZDirection = 1; else treeMem.rOrZDirection = -1;
1666  }else if(treeMem.subDetId==StripSubdetector::TID || treeMem.subDetId==StripSubdetector::TEC){
1667  dR = gVDirection.perp() - gPModule.perp();
1668  dPhi = deltaPhi(gUDirection.phi(),gPModule.phi());
1669  dZ = gWDirection.z() - gPModule.z();
1670  if(dR>=0.)treeMem.rOrZDirection = 1; else treeMem.rOrZDirection = -1;
1671  }
1672  if(dR>=0.)treeMem.rDirection = 1; else treeMem.rDirection = -1;
1673  if(dPhi>=0.)treeMem.phiDirection = 1; else treeMem.phiDirection = -1;
1674  if(dZ>=0.)treeMem.zDirection = 1; else treeMem.zDirection = -1;
1675  }
1676 }
1677 
1678 void
1680  const std::map<int, TrackerOfflineValidation::ModuleHistos>& moduleHist_)
1681 {
1682  for(std::map<int, TrackerOfflineValidation::ModuleHistos>::const_iterator it = moduleHist_.begin(),
1683  itEnd= moduleHist_.end(); it != itEnd;++it ) {
1684  treeMem = mTreeMembers_[it->first];
1685 
1686  //mean and RMS values (extracted from histograms(Xprime on module level)
1687  treeMem.entries = static_cast<UInt_t>(it->second.ResXprimeHisto->GetEntries());
1688  treeMem.meanX = it->second.ResXprimeHisto->GetMean();
1689  treeMem.rmsX = it->second.ResXprimeHisto->GetRMS();
1690  //treeMem.sigmaX = Fwhm(it->second.ResXprimeHisto)/2.355;
1691 
1692  if (useFit_) {
1693  //call fit function which returns mean and sigma from the fit
1694  //for absolute residuals
1695  std::pair<float,float> fitResult1 = this->fitResiduals(it->second.ResXprimeHisto);
1696  treeMem.fitMeanX = fitResult1.first;
1697  treeMem.fitSigmaX = fitResult1.second;
1698  //for normalized residuals
1699  std::pair<float,float> fitResult2 = this->fitResiduals(it->second.NormResXprimeHisto);
1700  treeMem.fitMeanNormX = fitResult2.first;
1701  treeMem.fitSigmaNormX = fitResult2.second;
1702  }
1703 
1704  //get median for absolute residuals
1705  treeMem.medianX = this->getMedian(it->second.ResXprimeHisto);
1706 
1707  int numberOfBins=it->second.ResXprimeHisto->GetNbinsX();
1708  treeMem.numberOfUnderflows = it->second.ResXprimeHisto->GetBinContent(0);
1709  treeMem.numberOfOverflows = it->second.ResXprimeHisto->GetBinContent(numberOfBins+1);
1710  treeMem.numberOfOutliers = it->second.ResXprimeHisto->GetBinContent(0)+it->second.ResXprimeHisto->GetBinContent(numberOfBins+1);
1711 
1712  //mean and RMS values (extracted from histograms(normalized Xprime on module level)
1713  treeMem.meanNormX = it->second.NormResXprimeHisto->GetMean();
1714  treeMem.rmsNormX = it->second.NormResXprimeHisto->GetRMS();
1715 
1716  double stats[20];
1717  it->second.NormResXprimeHisto->GetStats(stats);
1718  // GF treeMem.chi2PerDofX = stats[3]/(stats[0]-1);
1719  if (stats[0]) treeMem.chi2PerDofX = stats[3]/stats[0];
1720 
1721  treeMem.sigmaNormX = Fwhm(it->second.NormResXprimeHisto)/2.355;
1722  treeMem.histNameX = it->second.ResXprimeHisto->GetName();
1723  treeMem.histNameNormX = it->second.NormResXprimeHisto->GetName();
1724 
1725  // fill tree variables in local coordinates if set in cfg
1726  if(lCoorHistOn_) {
1727  treeMem.meanLocalX = it->second.ResHisto->GetMean();
1728  treeMem.rmsLocalX = it->second.ResHisto->GetRMS();
1729  treeMem.meanNormLocalX = it->second.NormResHisto->GetMean();
1730  treeMem.rmsNormLocalX = it->second.NormResHisto->GetRMS();
1731 
1732  treeMem.histNameLocalX = it->second.ResHisto->GetName();
1733  treeMem.histNameNormLocalX = it->second.NormResHisto->GetName();
1734  if (it->second.ResYHisto) treeMem.histNameLocalY = it->second.ResYHisto->GetName();
1735  }
1736 
1737  // mean and RMS values in local y (extracted from histograms(normalized Yprime on module level)
1738  // might exist in pixel only
1739  if (it->second.ResYprimeHisto) {//(stripYResiduals_)
1740  TH1 *h = it->second.ResYprimeHisto;
1741  treeMem.meanY = h->GetMean();
1742  treeMem.rmsY = h->GetRMS();
1743 
1744  if (useFit_) { // fit function which returns mean and sigma from the fit
1745  std::pair<float,float> fitMeanSigma = this->fitResiduals(h);
1746  treeMem.fitMeanY = fitMeanSigma.first;
1747  treeMem.fitSigmaY = fitMeanSigma.second;
1748  }
1749 
1750  //get median for absolute residuals
1751  treeMem.medianY = this->getMedian(h);
1752 
1753  treeMem.histNameY = h->GetName();
1754  }
1755  if (it->second.NormResYprimeHisto) {
1756  TH1 *h = it->second.NormResYprimeHisto;
1757  treeMem.meanNormY = h->GetMean();
1758  treeMem.rmsNormY = h->GetRMS();
1759  h->GetStats(stats); // stats buffer defined above
1760  if (stats[0]) treeMem.chi2PerDofY = stats[3]/stats[0];
1761 
1762  if (useFit_) { // fit function which returns mean and sigma from the fit
1763  std::pair<float,float> fitMeanSigma = this->fitResiduals(h);
1764  treeMem.fitMeanNormY = fitMeanSigma.first;
1765  treeMem.fitSigmaNormY = fitMeanSigma.second;
1766  }
1767  treeMem.histNameNormY = h->GetName();
1768  }
1769 
1770  if (moduleLevelProfiles_) {
1771  if (it->second.ResXvsXProfile) {
1772  TH1 *h = it->second.ResXvsXProfile;
1773  treeMem.meanResXvsX = h->GetMean();
1774  treeMem.rmsResXvsX = h->GetRMS();
1775  treeMem.profileNameResXvsX = h->GetName();
1776  }
1777  if (it->second.ResXvsYProfile) {
1778  TH1 *h = it->second.ResXvsYProfile;
1779  treeMem.meanResXvsY = h->GetMean();
1780  treeMem.rmsResXvsY = h->GetRMS();
1781  treeMem.profileNameResXvsY = h->GetName();
1782  }
1783  if (it->second.ResYvsXProfile) {
1784  TH1 *h = it->second.ResYvsXProfile;
1785  treeMem.meanResYvsX = h->GetMean();
1786  treeMem.rmsResYvsX = h->GetRMS();
1787  treeMem.profileNameResYvsX = h->GetName();
1788  }
1789  if (it->second.ResYvsYProfile) {
1790  TH1 *h = it->second.ResYvsYProfile;
1791  treeMem.meanResYvsY = h->GetMean();
1792  treeMem.rmsResYvsY = h->GetRMS();
1793  treeMem.profileNameResYvsY = h->GetName();
1794  }
1795  }
1796 
1797  tree.Fill();
1798  }
1799 }
1800 
1801 
1802 std::pair<float,float>
1804 {
1805  std::pair<float,float> fitResult(9999., 9999.);
1806  if (!hist || hist->GetEntries() < 20) return fitResult;
1807 
1808  float mean = hist->GetMean();
1809  float sigma = hist->GetRMS();
1810 
1811  try { // for < CMSSW_2_2_0 since ROOT warnings from fit are converted to exceptions
1812  // Remove the try/catch for more recent CMSSW!
1813  // first fit: two RMS around mean
1814  TF1 func("tmp", "gaus", mean - 2.*sigma, mean + 2.*sigma);
1815  if (0 == hist->Fit(&func,"QNR")) { // N: do not blow up file by storing fit!
1816  mean = func.GetParameter(1);
1817  sigma = func.GetParameter(2);
1818  // second fit: three sigma of first fit around mean of first fit
1819  func.SetRange(mean - 3.*sigma, mean + 3.*sigma);
1820  // I: integral gives more correct results if binning is too wide
1821  // L: Likelihood can treat empty bins correctly (if hist not weighted...)
1822  if (0 == hist->Fit(&func, "Q0LR")) {
1823  if (hist->GetFunction(func.GetName())) { // Take care that it is later on drawn:
1824  hist->GetFunction(func.GetName())->ResetBit(TF1::kNotDraw);
1825  }
1826  fitResult.first = func.GetParameter(1);
1827  fitResult.second = func.GetParameter(2);
1828  }
1829  }
1830  } catch (cms::Exception const & e) {
1831  edm::LogWarning("Alignment") << "@SUB=TrackerOfflineValidation::fitResiduals"
1832  << "Caught this exception during ROOT fit: "
1833  << e.what();
1834  }
1835  return fitResult;
1836 }
1837 
1838 
1839 float
1841 {
1842  float median = 999;
1843  int nbins = histo->GetNbinsX();
1844 
1845  //extract median from histogram
1846  double *x = new double[nbins];
1847  double *y = new double[nbins];
1848  for (int j = 0; j < nbins; j++) {
1849  x[j] = histo->GetBinCenter(j+1);
1850  y[j] = histo->GetBinContent(j+1);
1851  }
1852  median = TMath::Median(nbins, x, y);
1853 
1854  delete[] x; x = 0;
1855  delete [] y; y = 0;
1856 
1857  return median;
1858 
1859 }
1860 //define this as a plug-in
#define LogDebug(id)
const TrackerGeometry * bareTkGeomPtr_
virtual char const * what() const
Definition: Exception.cc:141
type
Definition: HCALResponse.h:21
GlobalPoint toGlobal(const Point2DBase< Scalar, LocalTag > lp) const
Definition: Surface.h:114
T getParameter(std::string const &) const
align::ID id() const
Return the ID of Alignable, i.e. DetId of &#39;first&#39; component GeomDet(Unit).
Definition: Alignable.h:180
int i
Definition: DBlmapReader.cc:9
bool tecIsDoubleSide(const DetId &id) const
bool tobIsDoubleSide(const DetId &id) const
std::vector< TH1 * > vDeleteObjects_
std::map< int, TrackerOfflineValidation::ModuleHistos > mPxeResiduals_
bool tibIsDoubleSide(const DetId &id) const
T perp() const
Definition: PV3DBase.h:72
unsigned int tibLayer(const DetId &id) const
std::pair< int, int > typeAndLayerFromDetId(const DetId &detId, const TrackerTopology *tTopo) const
unsigned int tidRing(const DetId &id) const
TH1 * make(const char *name, const char *title, int nBinX, double minBinX, double maxBinX)
bool isPixel(uint32_t subDetId)
std::vector< unsigned int > tidModuleInfo(const DetId &id) const
std::vector< TH1 * > vTrack2DHistos_
TH1 * bookTH1F(bool isTransient, DirectoryWrapper &tfd, const char *histName, const char *histTitle, int nBinsX, double lowX, double highX)
std::map< int, TrackerOfflineValidation::ModuleHistos > mTecResiduals_
#define DEFINE_FWK_MODULE(type)
Definition: MakerMacros.h:17
unsigned int pxfDisk(const DetId &id) const
container to hold data to be written into TTree
std::string profileNameResXvsX
void fillTree(TTree &tree, TkOffTreeVariables &treeMem, const std::map< int, TrackerOfflineValidation::ModuleHistos > &moduleHist_)
unsigned int tecRing(const DetId &id) const
ring id
uint32_t tobStereo(const DetId &id) const
Geom::Phi< T > phi() const
Definition: PV3DBase.h:69
unsigned int pxbLadder(const DetId &id) const
edm::ESHandle< TrackerGeometry > tkGeom_
T y() const
Definition: PV3DBase.h:63
int GetIndex(const std::vector< OBJECT_TYPE * > &vec, const TString &name)
unsigned int tidWheel(const DetId &id) const
unsigned int pxbModule(const DetId &id) const
T * make(const Args &...args) const
make new ROOT object
Definition: TFileService.h:64
float getMedian(const TH1 *hist) const
ModuleHistos & getHistStructFromMap(const DetId &detid)
void setSummaryBin(int bin, TH1 *targetHist, TH1 *sourceHist)
std::vector< unsigned int > tibStringInfo(const DetId &id) const
virtual Alignables components() const =0
Return vector of all direct components.
std::map< int, TrackerOfflineValidation::ModuleHistos > mTibResiduals_
TrackerOfflineValidation::SummaryContainer bookSummaryHists(DirectoryWrapper &tfd, const Alignable &ali, align::StructureType type, int i)
const Plane & surface() const
The nominal surface of the GeomDet.
Definition: GeomDet.h:40
std::vector< std::tuple< int, TH1 *, TH1 * > > summaryBins_
std::string profileNameResYvsX
std::map< int, TrackerOfflineValidation::ModuleHistos > mTidResiduals_
uint32_t rawId() const
get the raw id
Definition: DetId.h:43
virtual const DetIdContainer & detIds() const
Returm a vector of all GeomDet DetIds (including those of GeomDetUnits)
std::vector< std::pair< TH1 *, TH1 * > > sumHistStructure_
TFileDirectory & tFileDirectory()
Definition: TFileService.h:42
int iEvent
Definition: GenABIO.cc:230
std::vector< unsigned int > tecPetalInfo(const DetId &id) const
const Surface::PositionType & position() const
The position (origin of the R.F.)
Definition: GeomDet.h:46
unsigned int tidSide(const DetId &id) const
double dPhi(double phi1, double phi2)
Definition: JetUtil.h:30
void setUpTreeMembers(const std::map< int, TrackerOfflineValidation::ModuleHistos > &moduleHist_, const TrackerGeometry &tkgeom, const TrackerTopology *tTopo)
uint32_t tidStereo(const DetId &id) const
std::vector< unsigned int > tobRodInfo(const DetId &id) const
unsigned int subDetId[18]
T z() const
Definition: PV3DBase.h:64
tuple result
Definition: query.py:137
Tan< T >::type tan(const T &t)
Definition: Tan.h:22
virtual StructureType alignableObjectId() const =0
Return the alignable type identifier.
int j
Definition: DBlmapReader.cc:9
void getBinning(uint32_t subDetId, TrackerOfflineValidation::HistogramType residualtype, int &nBinsX, double &lowerBoundX, double &upperBoundX)
virtual void checkBookHists(const edm::EventSetup &setup)
TProfile * bookTProfile(bool isTransient, DirectoryWrapper &tfd, const char *histName, const char *histTitle, int nBinsX, double lowX, double highX)
double f[11][100]
The Signals That Services Can Subscribe To This is based on ActivityRegistry h
Helper function to determine trigger accepts.
Definition: Activities.doc:4
void prepareSummaryHists(DirectoryWrapper &tfd, const Alignable &ali, std::vector< TrackerOfflineValidation::SummaryContainer > &vLevelProfiles)
int subdetId() const
get the contents of the subdetector field (not cast into any detector&#39;s numbering enum) ...
Definition: DetId.h:37
std::string histNameLocalY
std::string histNameNormLocalX
unsigned int tibModule(const DetId &id) const
unsigned int pxfModule(const DetId &id) const
bool isDetOrDetUnit(align::StructureType type)
std::map< int, TrackerOfflineValidation::ModuleHistos > mTobResiduals_
unsigned int pxbLayer(const DetId &id) const
unsigned int tecModule(const DetId &id) const
DirectoryWrapper(const std::string &newDir, const std::string &basedir, bool useDqmMode)
Definition: DetId.h:18
void fillTrackQuantities(const edm::Event &, const edm::EventSetup &, std::vector< AVTrackStruct > &v_avtrackout)
TFileDirectory mkdir(const std::string &dir, const std::string &descr="")
create a new subdirectory
Definition: TFileService.h:69
std::pair< float, float > fitResiduals(TH1 *hist) const
std::string histNameLocalX
const T & get() const
Definition: EventSetup.h:55
bool tidIsDoubleSide(const DetId &id) const
T const * product() const
Definition: ESHandle.h:86
void summarizeBinInContainer(int bin, SummaryContainer &targetContainer, SummaryContainer &sourceContainer)
bool isEndCap(uint32_t subDetId)
unsigned int tobModule(const DetId &id) const
std::string profileNameResXvsY
T eta() const
Definition: PV3DBase.h:76
void bookGlobalHists(DirectoryWrapper &tfd)
DirectoryWrapper(const DirectoryWrapper &upDir, const std::string &newDir, const std::string &basedir, bool useDqmMode)
TrackerValidationVariables avalidator_
std::map< int, TkOffTreeVariables > mTreeMembers_
uint32_t tecStereo(const DetId &id) const
virtual const DetIdContainer & detUnitIds() const
Returm a vector of all GeomDetUnit DetIds.
std::vector< TH1 * > vTrackProfiles_
unsigned int pxfSide(const DetId &id) const
void bookDirHists(DirectoryWrapper &tfd, const Alignable &ali, const TrackerTopology *tTopo)
static const char * idToString(align::StructureType type)
std::map< int, TrackerOfflineValidation::ModuleHistos > mPxbResiduals_
uint32_t tibStereo(const DetId &id) const
Detector det() const
get the detector field from this detid
Definition: DetId.h:35
const edm::ParameterSet parSet_
TrackerOfflineValidation(const edm::ParameterSet &)
T x() const
Definition: PV3DBase.h:62
float Fwhm(const TH1 *hist) const
unsigned int tecWheel(const DetId &id) const
void setup(std::vector< TH2F > &depth, std::string name, std::string units="")
tuple size
Write out results.
unsigned int pxfPanel(const DetId &id) const
unsigned int pxfBlade(const DetId &id) const
virtual void analyze(const edm::Event &, const edm::EventSetup &) override
std::string profileNameResYvsY
unsigned int tobLayer(const DetId &id) const
void bookHists(DirectoryWrapper &tfd, const Alignable &ali, const TrackerTopology *tTopo, align::StructureType type, int i)
unsigned int tecSide(const DetId &id) const
virtual const TrackerGeomDet * idToDet(DetId) const
bool isBarrel(uint32_t subDetId)