ATLAS Offline Software
Loading...
Searching...
No Matches
MTT0PatternRecognition.cxx
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2026 CERN for the benefit of the ATLAS collaboration
3*/
4
6
8#include "GaudiKernel/MsgStream.h"
9#include "TGraph.h"
10#include "TH1.h"
11#include "TLine.h"
12
13namespace MuonCalib {
14
16 // estimate_background(const TH1 &hist, double scale_min) //
18
19 bool MTT0PatternRecognition::estimate_background(TH1F* hist, double scale_min) {
20 // Get first bin in input histogram which is not empty. This avoids underestimation of the background rate if the range of
21 // the input histogram exceeds the TDC-range
22 int min(-1);
23 for (int i = 1; i <= hist->GetNbinsX(); i++) {
24 if (hist->GetBinContent(i) > 0) {
25 min = i;
26 break;
27 }
28 }
29 if (min == -1) {
30 MsgStream log(Athena::getMessageSvc(), "MTT0PattternRecognition");
31 log << MSG::WARNING << "estimate_background() - No hits in input histogram!" << endmsg;
32 m_error = true;
33 return false;
34 }
35 double maxx = scale_min - 40;
36 int max = hist->FindBin(maxx);
37 // we want 10 bins minimum for the background estimate
38 if (max - min < m_settings->MinBackgroundBins()) {
39 min = max - 128;
40 if (min < 0) min = 0;
41 }
42 // if there are still not enough bins for the background estimate we have a problem
43 if (max - min < m_settings->MinBackgroundBins()) {
44 MsgStream log(Athena::getMessageSvc(), "MTT0PattternRecognition");
45 log << MSG::WARNING << "estimate_background() - Rising edge is to close to lower histogram range!" << endmsg;
46 m_error = true;
47 return false;
48 }
49 // calculate average bin content
50 m_background = 0.0;
51 double back_squared = 0.0;
52 double n_bins = 0.0;
53 double referenceChi2 = 0.0;
54 for (int i = min; i < max; i++) {
55 n_bins++;
56 m_background += hist->GetBinContent(i);
57 back_squared += hist->GetBinContent(i) * hist->GetBinContent(i);
58 if (n_bins == m_settings->MinBackgroundBins()) {
59 //coverity[DIVIDE_BY_ZERO:FALSE]
60 double bac = m_background / n_bins;
61 //coverity[DIVIDE_BY_ZERO:FALSE]
62 referenceChi2 = 2 * (back_squared / n_bins - bac * bac);
63 }
64 if (n_bins > m_settings->MinBackgroundBins()) {
65 //coverity[DIVIDE_BY_ZERO:FALSE]
66 double bac = m_background / n_bins;
67 //coverity[DIVIDE_BY_ZERO:FALSE]
68 double chi2 = 2 * (back_squared / n_bins - bac * bac);
69 if (chi2 > 5 * referenceChi2) break;
70 }
71 }
72 if (n_bins == 0){
73 //messaging should be revisited in this whole class
74 MsgStream log(Athena::getMessageSvc(), "MTT0PattternRecognition");
75 log << MSG::WARNING << "n_bins is zero" << endmsg;
76 m_background =0.;
77 } else {
78 m_background /= n_bins;
79 }
80 // store lower edge of fit range
81 m_fit_min = hist->GetBinCenter(min);
82 m_t0_est = 0.5 * (scale_min + hist->GetBinCenter(max));
83 // mark selected range
85 (new TLine(hist->GetBinCenter(min), 0, hist->GetBinCenter(min), hist->GetMaximum()))->Write("t0_back_left");
86 (new TLine(hist->GetBinCenter(max), 0, hist->GetBinCenter(max), hist->GetMaximum()))->Write("t0_back_right");
87 }
88
89 return true;
90 }
91
93 // estimate_height(const TH1 &hist) //
95
97 // smooth histogram
98 if (!m_vbh.Smooth(hist->GetBinWidth(1))) {
99 m_error = true;
100 return -1;
101 }
102 if (!m_vbh.Smooth(hist->GetBinWidth(1) / 2)) {
103 m_error = true;
104 return -1;
105 }
106 // draw debug graphs
107 if (m_draw_debug_graph) {
108 m_vbh.DenistyGraph()->Write("t0_density");
109 m_vbh.BinWidthGraph()->Write("t0_binwidth");
110 m_vbh.BinContentGraph()->Write("t0_bin_content");
111 m_vbh.DiffDensityGraph()->Write("t0_diff_density");
112 m_vbh.DiffDensityGraph()->Write("t0_diffbinwidth");
113 }
114 // get the range in which the smallest, and second smallest bins are
115 double lower = m_vbh.GetSortedBin(0).Width();
116 double left(9e9), right(-9e9);
117 // bool smallest_found(false);
118 for (unsigned int i = 0; i < m_vbh.GetNumberOfBins(); i++) {
119 if (m_vbh.GetSortedBin(i).Left() < left) left = m_vbh.GetSortedBin(i).Left();
120 if (m_vbh.GetSortedBin(i).Right() > right) right = m_vbh.GetSortedBin(i).Right();
121 // NOTE: For greater numerical stability m_vbh.GetSortedBin(i).Width() is considered greater only if it is greater by
122 // hist->GetBinWidth(1) / 100.0. I have seen differences in Binwidth in the order of 1e-13. On the other hand, due to the
123 // binning of the input histogram, e real difference in the binwidth of the VBH n*hist->GetBinWidth(1).
124 if ((m_vbh.GetSortedBin(i).Width() - lower) > hist->GetBinWidth(1) / 100.0) {
125 // reqire minimum distance between bins, and minimum number if significant bins
126 if (right - left > 50 && i > 20) break;
127 lower = m_vbh.GetSortedBin(i).Width();
128 }
129 }
130 // mark selected range
131 if (m_draw_debug_graph) {
132 (new TLine(left, 0, left, hist->GetMaximum()))->Write("t0_height_left");
133 (new TLine(right, 0, right, hist->GetMaximum()))->Write("t0_height_right");
134 }
135 // calcularte mean bin content of input histogram in range
136 int bleft(hist->FindBin(left)), bright(hist->FindBin(right));
137 double nbins = 0.0;
138 m_height = 0.0;
139 for (int i = bleft; i <= bright; i++) {
140 m_height += hist->GetBinContent(i);
141 nbins++;
142 }
143 if (nbins < 1) {
144 MsgStream log(Athena::getMessageSvc(), "MTT0PattternRecognition");
145 log << MSG::WARNING << "estimate_height() - top region is too small! left=" << left << " right=" << right << endmsg;
146 m_error = true;
147 return -1;
148 }
149 m_height /= nbins;
150 m_fit_max = right;
151 return left;
152 }
153
154} // namespace MuonCalib
#define endmsg
#define min(a, b)
Definition cfImp.cxx:40
#define max(a, b)
Definition cfImp.cxx:41
double estimate_height(TH1F *hist)
estimates the height of the spectrum.
VariableBinwidthHistogram m_vbh
Variable binwidth histogram.
bool estimate_background(TH1F *hist, double scale_min)
estimates the background level
const T0MTSettingsT0 * m_settings
settings
double chi2(TH1 *h0, TH1 *h1)
singleton-like access to IMessageSvc via open function and helper
IMessageSvc * getMessageSvc(bool quiet=false)
CscCalcPed - algorithm that finds the Cathode Strip Chamber pedestals from an RDO.