Analysis Software
Documentation for sPHENIX simulation software
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
ResPlotTool.cpp
Go to the documentation of this file. Or view the newest version in sPHENIX GitHub for file ResPlotTool.cpp
1 // This file is part of the Acts project.
2 //
3 // Copyright (C) 2019-2023 CERN for the benefit of the Acts project
4 //
5 // This Source Code Form is subject to the terms of the Mozilla Public
6 // License, v. 2.0. If a copy of the MPL was not distributed with this
7 // file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 
10 
16 
17 #include <algorithm>
18 #include <cmath>
19 #include <optional>
20 #include <ostream>
21 
22 #include <TH1.h>
23 #include <TH2.h>
24 #include <TString.h>
25 
28  : m_cfg(cfg), m_logger(Acts::getDefaultLogger("ResPlotTool", lvl)) {}
29 
31  ResPlotTool::ResPlotCache& resPlotCache) const {
32  PlotHelpers::Binning bEta = m_cfg.varBinning.at("Eta");
33  PlotHelpers::Binning bPt = m_cfg.varBinning.at("Pt");
34  PlotHelpers::Binning bPull = m_cfg.varBinning.at("Pull");
35 
36  ACTS_DEBUG("Initialize the histograms for residual and pull plots");
37  for (unsigned int parID = 0; parID < Acts::eBoundSize; parID++) {
38  std::string parName = m_cfg.paramNames.at(parID);
39 
40  std::string parResidual = "Residual_" + parName;
41  // Binning for residual is parameter dependent
42  PlotHelpers::Binning bResidual = m_cfg.varBinning.at(parResidual);
43 
44  // residual distributions
45  resPlotCache.res[parName] = PlotHelpers::bookHisto(
46  Form("res_%s", parName.c_str()),
47  Form("Residual of %s", parName.c_str()), bResidual);
48  // residual vs eta scatter plots
49  resPlotCache.res_vs_eta[parName] = PlotHelpers::bookHisto(
50  Form("res_%s_vs_eta", parName.c_str()),
51  Form("Residual of %s vs eta", parName.c_str()), bEta, bResidual);
52  // residual mean in each eta bin
53  resPlotCache.resMean_vs_eta[parName] = PlotHelpers::bookHisto(
54  Form("resmean_%s_vs_eta", parName.c_str()),
55  Form("Residual mean of %s", parName.c_str()), bEta);
56  // residual width in each eta bin
57  resPlotCache.resWidth_vs_eta[parName] = PlotHelpers::bookHisto(
58  Form("reswidth_%s_vs_eta", parName.c_str()),
59  Form("Residual width of %s", parName.c_str()), bEta);
60  // residual vs pT scatter plots
61  resPlotCache.res_vs_pT[parName] = PlotHelpers::bookHisto(
62  Form("res_%s_vs_pT", parName.c_str()),
63  Form("Residual of %s vs pT", parName.c_str()), bPt, bResidual);
64  // residual mean in each pT bin
65  resPlotCache.resMean_vs_pT[parName] = PlotHelpers::bookHisto(
66  Form("resmean_%s_vs_pT", parName.c_str()),
67  Form("Residual mean of %s", parName.c_str()), bPt);
68  // residual width in each pT bin
69  resPlotCache.resWidth_vs_pT[parName] = PlotHelpers::bookHisto(
70  Form("reswidth_%s_vs_pT", parName.c_str()),
71  Form("Residual width of %s", parName.c_str()), bPt);
72 
73  // pull distritutions
74  resPlotCache.pull[parName] =
75  PlotHelpers::bookHisto(Form("pull_%s", parName.c_str()),
76  Form("Pull of %s", parName.c_str()), bPull);
77  // pull vs eta scatter plots
78  resPlotCache.pull_vs_eta[parName] = PlotHelpers::bookHisto(
79  Form("pull_%s_vs_eta", parName.c_str()),
80  Form("Pull of %s vs eta", parName.c_str()), bEta, bPull);
81  // pull mean in each eta bin
82  resPlotCache.pullMean_vs_eta[parName] =
83  PlotHelpers::bookHisto(Form("pullmean_%s_vs_eta", parName.c_str()),
84  Form("Pull mean of %s", parName.c_str()), bEta);
85  // pull width in each eta bin
86  resPlotCache.pullWidth_vs_eta[parName] =
87  PlotHelpers::bookHisto(Form("pullwidth_%s_vs_eta", parName.c_str()),
88  Form("Pull width of %s", parName.c_str()), bEta);
89  // pull vs pT scatter plots
90  resPlotCache.pull_vs_pT[parName] = PlotHelpers::bookHisto(
91  Form("pull_%s_vs_pT", parName.c_str()),
92  Form("Pull of %s vs pT", parName.c_str()), bPt, bPull);
93  // pull mean in each pT bin
94  resPlotCache.pullMean_vs_pT[parName] =
95  PlotHelpers::bookHisto(Form("pullmean_%s_vs_pT", parName.c_str()),
96  Form("Pull mean of %s", parName.c_str()), bPt);
97  // pull width in each pT bin
98  resPlotCache.pullWidth_vs_pT[parName] =
99  PlotHelpers::bookHisto(Form("pullwidth_%s_vs_pT", parName.c_str()),
100  Form("Pull width of %s", parName.c_str()), bPt);
101  }
102 }
103 
105  ACTS_DEBUG("Delete the hists.");
106  for (unsigned int parID = 0; parID < Acts::eBoundSize; parID++) {
107  std::string parName = m_cfg.paramNames.at(parID);
108  delete resPlotCache.res.at(parName);
109  delete resPlotCache.res_vs_eta.at(parName);
110  delete resPlotCache.resMean_vs_eta.at(parName);
111  delete resPlotCache.resWidth_vs_eta.at(parName);
112  delete resPlotCache.res_vs_pT.at(parName);
113  delete resPlotCache.resMean_vs_pT.at(parName);
114  delete resPlotCache.resWidth_vs_pT.at(parName);
115  delete resPlotCache.pull.at(parName);
116  delete resPlotCache.pull_vs_eta.at(parName);
117  delete resPlotCache.pullMean_vs_eta.at(parName);
118  delete resPlotCache.pullWidth_vs_eta.at(parName);
119  delete resPlotCache.pull_vs_pT.at(parName);
120  delete resPlotCache.pullMean_vs_pT.at(parName);
121  delete resPlotCache.pullWidth_vs_pT.at(parName);
122  }
123 }
124 
126  const ResPlotTool::ResPlotCache& resPlotCache) const {
127  ACTS_DEBUG("Write the hists to output file.");
128  for (unsigned int parID = 0; parID < Acts::eBoundSize; parID++) {
129  std::string parName = m_cfg.paramNames.at(parID);
130  resPlotCache.res.at(parName)->Write();
131  resPlotCache.res_vs_eta.at(parName)->Write();
132  resPlotCache.resMean_vs_eta.at(parName)->Write();
133  resPlotCache.resWidth_vs_eta.at(parName)->Write();
134  resPlotCache.res_vs_pT.at(parName)->Write();
135  resPlotCache.resMean_vs_pT.at(parName)->Write();
136  resPlotCache.resWidth_vs_pT.at(parName)->Write();
137  resPlotCache.pull.at(parName)->Write();
138  resPlotCache.pull_vs_eta.at(parName)->Write();
139  resPlotCache.pullMean_vs_eta.at(parName)->Write();
140  resPlotCache.pullWidth_vs_eta.at(parName)->Write();
141  resPlotCache.pull_vs_pT.at(parName)->Write();
142  resPlotCache.pullMean_vs_pT.at(parName)->Write();
143  resPlotCache.pullWidth_vs_pT.at(parName)->Write();
144  }
145 }
146 
149  const ActsFatras::Particle& truthParticle,
150  const Acts::BoundTrackParameters& fittedParamters) const {
151  using ParametersVector = Acts::BoundTrackParameters::ParametersVector;
156 
157  // get the fitted parameter (at perigee surface) and its error
158  auto trackParameter = fittedParamters.parameters();
159 
160  // get the perigee surface
161  auto pSurface = &fittedParamters.referenceSurface();
162 
163  // get the truth position and momentum
164  ParametersVector truthParameter = ParametersVector::Zero();
165 
166  // get the truth perigee parameter
167  auto lpResult = pSurface->globalToLocal(gctx, truthParticle.position(),
168  truthParticle.direction());
169  if (lpResult.ok()) {
170  truthParameter[Acts::BoundIndices::eBoundLoc0] =
171  lpResult.value()[Acts::BoundIndices::eBoundLoc0];
172  truthParameter[Acts::BoundIndices::eBoundLoc1] =
173  lpResult.value()[Acts::BoundIndices::eBoundLoc1];
174  } else {
175  ACTS_ERROR("Global to local transformation did not succeed.");
176  }
177  truthParameter[Acts::BoundIndices::eBoundPhi] =
178  phi(truthParticle.direction());
179  truthParameter[Acts::BoundIndices::eBoundTheta] =
180  theta(truthParticle.direction());
181  truthParameter[Acts::BoundIndices::eBoundQOverP] =
182  truthParticle.charge() / truthParticle.absoluteMomentum();
183  truthParameter[Acts::BoundIndices::eBoundTime] = truthParticle.time();
184 
185  // get the truth eta and pT
186  const auto truthEta = eta(truthParticle.direction());
187  const auto truthPt = truthParticle.transverseMomentum();
188 
189  // fill the histograms for residual and pull
190  for (unsigned int parID = 0; parID < Acts::eBoundSize; parID++) {
191  std::string parName = m_cfg.paramNames.at(parID);
192  float residual = trackParameter[parID] - truthParameter[parID];
193  PlotHelpers::fillHisto(resPlotCache.res.at(parName), residual);
194  PlotHelpers::fillHisto(resPlotCache.res_vs_eta.at(parName), truthEta,
195  residual);
196  PlotHelpers::fillHisto(resPlotCache.res_vs_pT.at(parName), truthPt,
197  residual);
198 
199  if (fittedParamters.covariance().has_value()) {
200  auto covariance = *fittedParamters.covariance();
201  if (covariance(parID, parID) > 0) {
202  float pull = residual / sqrt(covariance(parID, parID));
203  PlotHelpers::fillHisto(resPlotCache.pull[parName], pull);
204  PlotHelpers::fillHisto(resPlotCache.pull_vs_eta.at(parName), truthEta,
205  pull);
206  PlotHelpers::fillHisto(resPlotCache.pull_vs_pT.at(parName), truthPt,
207  pull);
208  } else {
209  ACTS_WARNING("Fitted track parameter :" << parName
210  << " has negative covariance = "
211  << covariance(parID, parID));
212  }
213  } else {
214  ACTS_WARNING("Fitted track parameter :" << parName
215  << " has no covariance");
216  }
217  }
218 }
219 
220 // get the mean and width of residual/pull in each eta/pT bin and fill them into
221 // histograms
223  ResPlotTool::ResPlotCache& resPlotCache) const {
224  PlotHelpers::Binning bEta = m_cfg.varBinning.at("Eta");
225  PlotHelpers::Binning bPt = m_cfg.varBinning.at("Pt");
226  for (unsigned int parID = 0; parID < Acts::eBoundSize; parID++) {
227  std::string parName = m_cfg.paramNames.at(parID);
228  // refine the plots vs eta
229  for (int j = 1; j <= static_cast<int>(bEta.nBins()); j++) {
230  TH1D* temp_res = resPlotCache.res_vs_eta.at(parName)->ProjectionY(
231  Form("%s_projy_bin%d", "Residual_vs_eta_Histo", j), j, j);
232  PlotHelpers::anaHisto(temp_res, j,
233  resPlotCache.resMean_vs_eta.at(parName),
234  resPlotCache.resWidth_vs_eta.at(parName));
235 
236  TH1D* temp_pull = resPlotCache.pull_vs_eta.at(parName)->ProjectionY(
237  Form("%s_projy_bin%d", "Pull_vs_eta_Histo", j), j, j);
238  PlotHelpers::anaHisto(temp_pull, j,
239  resPlotCache.pullMean_vs_eta.at(parName),
240  resPlotCache.pullWidth_vs_eta.at(parName));
241  }
242 
243  // refine the plots vs pT
244  for (int j = 1; j <= static_cast<int>(bPt.nBins()); j++) {
245  TH1D* temp_res = resPlotCache.res_vs_pT.at(parName)->ProjectionY(
246  Form("%s_projy_bin%d", "Residual_vs_pT_Histo", j), j, j);
247  PlotHelpers::anaHisto(temp_res, j, resPlotCache.resMean_vs_pT.at(parName),
248  resPlotCache.resWidth_vs_pT.at(parName));
249 
250  TH1D* temp_pull = resPlotCache.pull_vs_pT.at(parName)->ProjectionY(
251  Form("%s_projy_bin%d", "Pull_vs_pT_Histo", j), j, j);
252  PlotHelpers::anaHisto(temp_pull, j,
253  resPlotCache.pullMean_vs_pT.at(parName),
254  resPlotCache.pullWidth_vs_pT.at(parName));
255  }
256  }
257 }