CMS 3D CMS Logo

MuScleFitBase.cc
Go to the documentation of this file.
1 #ifndef MUSCLEFITBASE_C
2 #define MUSCLEFITBASE_C
3 
4 #include "MuScleFitBase.h"
6 #include <memory>
7 #include <array>
8 
9 void MuScleFitBase::fillHistoMap(TFile* outputFile, unsigned int iLoop) {
10  //Reconstructed muon kinematics
11  //-----------------------------
12  outputFile->cd();
13  // If no Z is required, use a smaller mass range.
14  double minMass = 0.;
15  double maxMass = 200.;
16  double maxPt = 100.;
17  double yMaxEta = 4.;
18  double yMaxPt = 2.;
19  if (MuScleFitUtils::resfind[0] != 1) {
20  maxMass = 20.;
21  maxPt = 20.;
22  yMaxEta = 0.2;
23  yMaxPt = 0.2;
24  // If running on standalone muons we need to expand the window range
25  if (theMuonType_ == 2) {
26  yMaxEta = 20.;
27  }
28  }
29 
30  LogDebug("MuScleFitBase") << "Creating new histograms" << std::endl;
31 
32  mapHisto_["hRecBestMu"] = new HParticle("hRecBestMu", minMass, maxMass, maxPt);
33  mapHisto_["hRecBestMuVSEta"] = new HPartVSEta("hRecBestMuVSEta", minMass, maxMass, maxPt);
34  //mapHisto_["hRecBestMuVSPhi"] = new HPartVSPhi ("hRecBestMuVSPhi");
35  //mapHisto_["hRecBestMu_Acc"] = new HParticle ("hRecBestMu_Acc", minMass, maxMass);
36  mapHisto_["hDeltaRecBestMu"] = new HDelta("hDeltaRecBestMu");
37 
38  mapHisto_["hRecBestRes"] = new HParticle("hRecBestRes", minMass, maxMass, maxPt);
39  mapHisto_["hRecBestResAllEvents"] = new HParticle("hRecBestResAllEvents", minMass, maxMass, maxPt);
40  //mapHisto_["hRecBestRes_Acc"] = new HParticle ("hRecBestRes_Acc", minMass, maxMass);
41  // If not finding Z, use a smaller mass window
42  mapHisto_["hRecBestResVSMu"] = new HMassVSPart("hRecBestResVSMu", minMass, maxMass, maxPt);
43  mapHisto_["hRecBestResVSRes"] = new HMassVSPart("hRecBestResVSRes", minMass, maxMass, maxPt);
44  //Generated Mass versus pt
45  mapHisto_["hGenResVSMu"] = new HMassVSPart("hGenResVSMu", minMass, maxMass, maxPt);
46  // Likelihood values VS muon variables
47  // -------------------------------------
48  mapHisto_["hLikeVSMu"] = new HLikelihoodVSPart("hLikeVSMu");
49  mapHisto_["hLikeVSMuMinus"] = new HLikelihoodVSPart("hLikeVSMuMinus");
50  mapHisto_["hLikeVSMuPlus"] = new HLikelihoodVSPart("hLikeVSMuPlus");
51 
52  //Resolution VS muon kinematic
53  //----------------------------
54  mapHisto_["hResolMassVSMu"] =
55  new HResolutionVSPart(outputFile, "hResolMassVSMu", maxPt, 0., yMaxEta, 0., yMaxPt, true);
56  mapHisto_["hFunctionResolMassVSMu"] =
57  new HResolutionVSPart(outputFile, "hFunctionResolMassVSMu", maxPt, 0, 0.1, 0, 0.1, true);
58  mapHisto_["hResolPtGenVSMu"] = new HResolutionVSPart(outputFile, "hResolPtGenVSMu", maxPt, -0.1, 0.1, -0.1, 0.1);
59  mapHisto_["hResolPtSimVSMu"] = new HResolutionVSPart(outputFile, "hResolPtSimVSMu", maxPt, -0.1, 0.1, -0.1, 0.1);
60  mapHisto_["hResolEtaGenVSMu"] =
61  new HResolutionVSPart(outputFile, "hResolEtaGenVSMu", maxPt, -0.02, 0.02, -0.02, 0.02);
62  mapHisto_["hResolEtaSimVSMu"] =
63  new HResolutionVSPart(outputFile, "hResolEtaSimVSMu", maxPt, -0.02, 0.02, -0.02, 0.02);
64  mapHisto_["hResolThetaGenVSMu"] =
65  new HResolutionVSPart(outputFile, "hResolThetaGenVSMu", maxPt, -0.02, 0.02, -0.02, 0.02);
66  mapHisto_["hResolThetaSimVSMu"] =
67  new HResolutionVSPart(outputFile, "hResolThetaSimVSMu", maxPt, -0.02, 0.02, -0.02, 0.02);
68  mapHisto_["hResolCotgThetaGenVSMu"] =
69  new HResolutionVSPart(outputFile, "hResolCotgThetaGenVSMu", maxPt, -0.02, 0.02, -0.02, 0.02);
70  mapHisto_["hResolCotgThetaSimVSMu"] =
71  new HResolutionVSPart(outputFile, "hResolCotgThetaSimVSMu", maxPt, -0.02, 0.02, -0.02, 0.02);
72  mapHisto_["hResolPhiGenVSMu"] =
73  new HResolutionVSPart(outputFile, "hResolPhiGenVSMu", maxPt, -0.02, 0.02, -0.02, 0.02);
74  mapHisto_["hResolPhiSimVSMu"] =
75  new HResolutionVSPart(outputFile, "hResolPhiSimVSMu", maxPt, -0.02, 0.02, -0.02, 0.02);
76 
78  mapHisto_["hdMdPt1"] = new HResolutionVSPart(outputFile, "hdMdPt1", maxPt, 0, 100, -3.2, 3.2, true);
79  mapHisto_["hdMdPt2"] = new HResolutionVSPart(outputFile, "hdMdPt2", maxPt, 0, 100, -3.2, 3.2, true);
80  mapHisto_["hdMdPhi1"] = new HResolutionVSPart(outputFile, "hdMdPhi1", maxPt, 0, 100, -3.2, 3.2, true);
81  mapHisto_["hdMdPhi2"] = new HResolutionVSPart(outputFile, "hdMdPhi2", maxPt, 0, 100, -3.2, 3.2, true);
82  mapHisto_["hdMdCotgTh1"] = new HResolutionVSPart(outputFile, "hdMdCotgTh1", maxPt, 0, 100, -3.2, 3.2, true);
83  mapHisto_["hdMdCotgTh2"] = new HResolutionVSPart(outputFile, "hdMdCotgTh2", maxPt, 0, 100, -3.2, 3.2, true);
84  }
85 
86  HTH2D* recoGenHisto =
87  new HTH2D(outputFile, "hPtRecoVsPtGen", "Pt reco vs Pt gen", "hPtRecoVsPtGen", 120, 0., 120., 120, 0, 120.);
88  (*recoGenHisto)->SetXTitle("Pt gen (GeV)");
89  (*recoGenHisto)->SetYTitle("Pt reco (GeV)");
90  mapHisto_["hPtRecoVsPtGen"] = recoGenHisto;
91  HTH2D* recoSimHisto =
92  new HTH2D(outputFile, "hPtRecoVsPtSim", "Pt reco vs Pt sim", "hPtRecoVsPtSim", 120, 0., 120., 120, 0, 120.);
93  (*recoSimHisto)->SetXTitle("Pt sim (GeV)");
94  (*recoSimHisto)->SetYTitle("Pt reco (GeV)");
95  mapHisto_["hPtRecoVsPtSim"] = recoSimHisto;
96  // Resolutions from resolution functions
97  // -------------------------------------
98  mapHisto_["hFunctionResolPt"] = new HFunctionResolution(outputFile, "hFunctionResolPt", maxPt);
99  mapHisto_["hFunctionResolCotgTheta"] = new HFunctionResolution(outputFile, "hFunctionResolCotgTheta", maxPt);
100  mapHisto_["hFunctionResolPhi"] = new HFunctionResolution(outputFile, "hFunctionResolPhi", maxPt);
101 
102  // Mass probability histograms
103  // ---------------------------
104  // The word "profile" is added to the title automatically
105  mapHisto_["hMass_P"] = new HTProfile(outputFile, "Mass_P", "Mass probability", 4000, 0., 200., 0., 50.);
106  mapHisto_["hMass_fine_P"] = new HTProfile(outputFile, "Mass_fine_P", "Mass probability", 4000, 0., 20., 0., 50.);
107  mapHisto_["hMass_Probability"] = new HTH1D(outputFile, "Mass_Probability", "Mass probability", 4000, 0., 200.);
108  mapHisto_["hMass_fine_Probability"] =
109  new HTH1D(outputFile, "Mass_fine_Probability", "Mass probability", 4000, 0., 20.);
110  mapHisto_["hMassProbVsMu"] = new HMassVSPartProfile("hMassProbVsMu", minMass, maxMass, maxPt);
111  mapHisto_["hMassProbVsRes"] = new HMassVSPartProfile("hMassProbVsRes", minMass, maxMass, maxPt);
112  mapHisto_["hMassProbVsMu_fine"] = new HMassVSPartProfile("hMassProbVsMu_fine", minMass, maxMass, maxPt);
113  mapHisto_["hMassProbVsRes_fine"] = new HMassVSPartProfile("hMassProbVsRes_fine", minMass, maxMass, maxPt);
114 
115  // (M_reco-M_gen)/M_gen vs (pt, eta) of the muons from MC
116  mapHisto_["hDeltaMassOverGenMassVsPt"] = new HTH2D(outputFile,
117  "DeltaMassOverGenMassVsPt",
118  "DeltaMassOverGenMassVsPt",
119  "DeltaMassOverGenMass",
120  200,
121  0,
122  maxPt,
123  200,
124  -0.2,
125  0.2);
126  mapHisto_["hDeltaMassOverGenMassVsEta"] = new HTH2D(outputFile,
127  "DeltaMassOverGenMassVsEta",
128  "DeltaMassOverGenMassVsEta",
129  "DeltaMassOverGenMass",
130  200,
131  -3.,
132  3.,
133  200,
134  -0.2,
135  0.2);
136 
137  // Square of mass resolution vs (pt, eta) of the muons from MC
138  // EM 2012.12.19 mapHisto_["hMassResolutionVsPtEta"] = new HCovarianceVSxy( "Mass", "Mass", 100, 0., maxPt, 60, -3, 3, outputFile->mkdir("MassCovariance") );
139  // Mass resolution vs (pt, eta) from resolution function
140  mapHisto_["hFunctionResolMass"] = new HFunctionResolution(outputFile, "hFunctionResolMass", maxPt);
141 }
142 
144  for (std::map<std::string, Histograms*>::const_iterator histo = mapHisto_.begin(); histo != mapHisto_.end();
145  histo++) {
146  delete (*histo).second;
147  }
148 }
149 
150 void MuScleFitBase::writeHistoMap(const unsigned int iLoop) {
151  for (std::map<std::string, Histograms*>::const_iterator histo = mapHisto_.begin(); histo != mapHisto_.end();
152  histo++) {
153  // This is to avoid writing into subdirs. Need a workaround.
154  theFiles_[iLoop]->cd();
155  (*histo).second->Write();
156  }
157 }
158 
160  std::array<TH2D*, 6> GLZ = {{nullptr}};
161  std::array<TH2D*, 6> GL = {{nullptr}};
162  std::unique_ptr<TFile> ProbsFile;
163  if (!probabilitiesFile_.empty()) {
164  ProbsFile = std::make_unique<TFile>(probabilitiesFile_.c_str());
165  std::cout << "[MuScleFit-Constructor]: Reading TH2D probabilities from " << probabilitiesFile_ << std::endl;
166  } else {
167  // edm::FileInPath file("MuonAnalysis/MomentumScaleCalibration/test/Probs_new_1000_CTEQ.root");
168  // edm::FileInPath file("MuonAnalysis/MomentumScaleCalibration/test/Probs_new_Horace_CTEQ_1000.root");
169  // edm::FileInPath file("MuonAnalysis/MomentumScaleCalibration/test/Probs_merge.root");
171  ProbsFile = std::make_unique<TFile>(file.fullPath().c_str());
172  std::cout << "[MuScleFit-Constructor]: Reading TH2D probabilities from " << probabilitiesFileInPath_ << std::endl;
173  }
174 
175  ProbsFile->cd();
176  bool resfindEmpty = true;
178  resfindEmpty = false;
179  for (unsigned char i = 0; i < GLZ.size(); i++) {
180  char nameh[6];
181  snprintf(nameh, 6, "GLZ%hhu", i);
182  GLZ[i] = dynamic_cast<TH2D*>(ProbsFile->Get(nameh));
183  }
184  } else if (MuScleFitUtils::resfind[0] && theMuonType_ == 2) {
185  GL[0] = dynamic_cast<TH2D*>(ProbsFile->Get("GL0"));
186  resfindEmpty = false;
187  }
188  for (unsigned char i = 1; i < GL.size(); ++i) {
189  if (MuScleFitUtils::resfind[i]) {
190  char nameh[6];
191  snprintf(nameh, 6, "GL%hhu", i);
192  GL[i] = dynamic_cast<TH2D*>(ProbsFile->Get(nameh));
193  resfindEmpty = false;
194  }
195  }
196  if (resfindEmpty) {
197  std::cout << "[MuScleFit-Constructor]: No resonance selected, please fill the resfind array" << std::endl;
198  exit(1);
199  }
200 
201  // Read the limits for M and Sigma axis for each pdf
202  // Note: we assume all the Z histograms to have the same limits
203  // x is mass, y is sigma
205  MuScleFitUtils::ResHalfWidth[0] = (GLZ[0]->GetXaxis()->GetXmax() - GLZ[0]->GetXaxis()->GetXmin()) / 2.;
206  MuScleFitUtils::ResMaxSigma[0] = (GLZ[0]->GetYaxis()->GetXmax() - GLZ[0]->GetYaxis()->GetXmin());
207  MuScleFitUtils::ResMinMass[0] = (GLZ[0]->GetXaxis()->GetXmin());
208  }
209  if (MuScleFitUtils::resfind[0] && theMuonType_ == 2) {
210  MuScleFitUtils::ResHalfWidth[0] = (GL[0]->GetXaxis()->GetXmax() - GL[0]->GetXaxis()->GetXmin()) / 2.;
211  MuScleFitUtils::ResMaxSigma[0] = (GL[0]->GetYaxis()->GetXmax() - GL[0]->GetYaxis()->GetXmin());
212  MuScleFitUtils::ResMinMass[0] = (GL[0]->GetXaxis()->GetXmin());
213  }
214  for (unsigned int i = 1; i < GL.size(); ++i) {
215  if (MuScleFitUtils::resfind[i]) {
216  MuScleFitUtils::ResHalfWidth[i] = (GL[i]->GetXaxis()->GetXmax() - GL[i]->GetXaxis()->GetXmin()) / 2.;
217  MuScleFitUtils::ResMaxSigma[i] = (GL[i]->GetYaxis()->GetXmax() - GL[i]->GetYaxis()->GetXmin());
218  MuScleFitUtils::ResMinMass[i] = (GL[i]->GetXaxis()->GetXmin());
219  // if( debug_>2 ) {
220  std::cout << "MuScleFitUtils::ResHalfWidth[" << i << "] = " << MuScleFitUtils::ResHalfWidth[i] << std::endl;
221  std::cout << "MuScleFitUtils::ResMaxSigma[" << i << "] = " << MuScleFitUtils::ResMaxSigma[i] << std::endl;
222  // }
223  }
224  }
225 
226  // Extract normalization for mass slice in Y bins of Z
227  // ---------------------------------------------------
229  for (unsigned int iY = 0; iY < GLZ.size(); iY++) {
230  int nBinsX = GLZ[iY]->GetNbinsX();
231  int nBinsY = GLZ[iY]->GetNbinsY();
232  if (nBinsX != MuScleFitUtils::nbins + 1 || nBinsY != MuScleFitUtils::nbins + 1) {
233  std::cout << "Error: for histogram \"" << GLZ[iY]->GetName() << "\" bins are not " << MuScleFitUtils::nbins
234  << std::endl;
235  std::cout << "nBinsX = " << nBinsX << ", nBinsY = " << nBinsY << std::endl;
236  exit(1);
237  }
238  for (int iy = 0; iy <= MuScleFitUtils::nbins; iy++) {
239  MuScleFitUtils::GLZNorm[iY][iy] = 0.;
240  for (int ix = 0; ix <= MuScleFitUtils::nbins; ix++) {
241  MuScleFitUtils::GLZValue[iY][ix][iy] = GLZ[iY]->GetBinContent(ix + 1, iy + 1);
242  MuScleFitUtils::GLZNorm[iY][iy] +=
244  }
245  }
246  }
247  }
248 
249  if (MuScleFitUtils::resfind[0] && theMuonType_ == 2) {
250  int nBinsX = GL[0]->GetNbinsX();
251  int nBinsY = GL[0]->GetNbinsY();
252  if (nBinsX != MuScleFitUtils::nbins + 1 || nBinsY != MuScleFitUtils::nbins + 1) {
253  std::cout << "Error: for histogram \"" << GL[0]->GetName() << "\" bins are not " << MuScleFitUtils::nbins
254  << std::endl;
255  std::cout << "nBinsX = " << nBinsX << ", nBinsY = " << nBinsY << std::endl;
256  exit(1);
257  }
258 
259  for (int iy = 0; iy <= MuScleFitUtils::nbins; iy++) {
260  MuScleFitUtils::GLNorm[0][iy] = 0.;
261  for (int ix = 0; ix <= MuScleFitUtils::nbins; ix++) {
262  MuScleFitUtils::GLValue[0][ix][iy] = GL[0]->GetBinContent(ix + 1, iy + 1);
263  // N.B. approximation: we should compute the integral of the function used to compute the probability (linear
264  // interpolation of the mass points). This computation could be troublesome because the points have a steep
265  // variation near the mass peak and the normal integral is not precise in these conditions.
266  // Furthermore it is slow.
267  MuScleFitUtils::GLNorm[0][iy] +=
269  }
270  }
271  }
272  // Extract normalization for each mass slice
273  // -----------------------------------------
274  for (unsigned int ires = 1; ires < GL.size(); ires++) {
275  if (MuScleFitUtils::resfind[ires]) {
276  int nBinsX = GL[ires]->GetNbinsX();
277  int nBinsY = GL[ires]->GetNbinsY();
278  if (nBinsX != MuScleFitUtils::nbins + 1 || nBinsY != MuScleFitUtils::nbins + 1) {
279  std::cout << "Error: for histogram \"" << GL[ires]->GetName() << "\" bins are not " << MuScleFitUtils::nbins
280  << std::endl;
281  std::cout << "nBinsX = " << nBinsX << ", nBinsY = " << nBinsY << std::endl;
282  exit(1);
283  }
284 
285  for (int iy = 0; iy <= MuScleFitUtils::nbins; iy++) {
286  MuScleFitUtils::GLNorm[ires][iy] = 0.;
287  for (int ix = 0; ix <= MuScleFitUtils::nbins; ix++) {
288  MuScleFitUtils::GLValue[ires][ix][iy] = GL[ires]->GetBinContent(ix + 1, iy + 1);
289  // N.B. approximation: we should compute the integral of the function used to compute the probability (linear
290  // interpolation of the mass points). This computation could be troublesome because the points have a steep
291  // variation near the mass peak and the normal integral is not precise in these conditions.
292  // Furthermore it is slow.
293  MuScleFitUtils::GLNorm[ires][iy] +=
295  }
296  }
297  }
298  }
299  // Free all the memory for the probability histograms.
301  for (unsigned int i = 0; i < GLZ.size(); i++) {
302  delete GLZ[i];
303  }
304  }
305  if (MuScleFitUtils::resfind[0] && theMuonType_ == 2)
306  delete GL[0];
307  for (unsigned int ires = 1; ires < GL.size(); ires++) {
308  if (MuScleFitUtils::resfind[ires])
309  delete GL[ires];
310  }
311 }
312 
313 #endif
static double GLValue[6][1001][1001]
static int nbins
static bool debugMassResol_
static double ResMinMass[6]
TF1 * GL
A wrapper for the TH1D histogram to allow it to be put inside the same map as all the other classes i...
Definition: Histograms.h:187
std::map< std::string, Histograms * > mapHisto_
The map of histograms.
Definition: MuScleFitBase.h:79
A wrapper for the TProfile histogram to allow it to be put inside the same map as all the other class...
Definition: Histograms.h:213
static double GLZNorm[40][1001]
void clearHistoMap()
Clean the histograms map.
static double ResMaxSigma[6]
static double GLZValue[40][1001][1001]
void writeHistoMap(const unsigned int iLoop)
Save the histograms map to file.
maxPt
Definition: PV_cfg.py:223
static bool rapidityBinsForZ_
void fillHistoMap(TFile *outputFile, unsigned int iLoop)
Create the histograms map.
Definition: MuScleFitBase.cc:9
std::vector< TFile * > theFiles_
The files were the histograms are saved.
Definition: MuScleFitBase.h:76
static double GLNorm[6][1001]
A wrapper for the TH2D histogram to allow it to be put inside the same map as all the other classes i...
Definition: Histograms.h:137
static std::vector< int > resfind
static double ResHalfWidth[6]
void readProbabilityDistributionsFromFile()
Read probability distributions from a local root file.
std::string probabilitiesFileInPath_
Definition: MuScleFitBase.h:44
A set of histograms for resolution.
Definition: Histograms.h:1201
std::string probabilitiesFile_
Definition: MuScleFitBase.h:45
#define LogDebug(id)
def exit(msg="")