ATLAS Offline Software
Loading...
Searching...
No Matches
January2018_specialStatTerms/ProviderHistoHelpers.py
Go to the documentation of this file.
1from ROOT import *
2from array import array
3import glob
4import re
5import math
6
7
8def GetDefaultPtBins(numBins=100,lowVal=15.0,highVal=2500.0):
9 dx = (math.log(highVal)-math.log(lowVal))/numBins
10 bins = []
11 for iBin in range(0,numBins+1):
12 bins.append(math.exp(math.log(lowVal)+iBin*dx))
13
14 return bins
15
16def GetDefaultEtaBins():
17 etaValuesAsym = [0,0.15,0.3,0.8,1.0,1.2,1.65,2.1,2.45,2.8,3.0,3.2,3.6,4.5]
18 etaValuesSym = []
19 for aVal in etaValuesAsym:
20 etaValuesSym.append(aVal)
21 if math.fabs(aVal) > 1.e-4: # Don't double-count zero
22 etaValuesSym.append(-aVal)
23
24 return sorted(etaValuesSym)
25
26def GetCentredBins(values):
27 if len(values) == 1:
28 return [values[0]*0.5,values[0]*1.5]
29
30 binList = []
31 for iVal in range(0,len(values)-1):
32 binList.append(values[iVal]+(values[iVal+1]-values[iVal])/2.0)
33 binList.insert(0,values[0]-(values[1]-values[0])/2.0)
34 binList.append(values[-1]+(values[-1]-values[-2])/2.0)
35
36 return binList
37
38def MakeProviderHisto(histoName,ptBins=GetDefaultPtBins(),etaBins=GetDefaultEtaBins()):
39 return TH2D(histoName,histoName,len(ptBins)-1,array('d',ptBins),len(etaBins)-1,array('d',etaBins))
40
41
42def ConvertPtHistoToProviderHisto(histo1D,histoName):
43 histo2D = MakeProviderHisto(histoName,etaBins=[min(GetDefaultEtaBins()),0,max(GetDefaultEtaBins())])
44
45 oldMinPt = histo1D.GetXaxis().GetBinLowEdge(1)
46 oldMaxPt = histo1D.GetXaxis().GetBinLowEdge(histo1D.GetNbinsX()+1)
47 tolerance = 1.0e-4
48 for ptBin in range(1,histo2D.GetNbinsX()+1):
49 pt = histo2D.GetXaxis().GetBinCenter(ptBin)
50 unc = 0.0
51 if pt <= oldMinPt:
52 unc = histo1D.Interpolate(oldMinPt+tolerance)
53 elif pt >= oldMaxPt:
54 unc = histo1D.Interpolate(oldMaxPt+tolerance)
55 else:
56 unc = histo1D.Interpolate(pt)
57
58 for etaBin in range(1,histo2D.GetNbinsY()+1):
59 histo2D.SetBinContent(ptBin,etaBin,unc)
60
61 return histo2D
62
63def ConvertTGraphToProviderHisto(graph,histoName):
64 pointsX = []
65 pointsY = []
66 for iPoint in range(0,graph.GetN()):
67 px = Double(0)
68 py = Double(0)
69 graph.GetPoint(iPoint,px,py)
70 pointsX.append(px)
71 pointsY.append(py)
72
73 # Make bins with the points as the centre where possible
74 bins = GetCentredBins(pointsX)
75
76 # Extend the range to cover [15,2500] if necessary
77 if bins[0] > 15:
78 bins.insert(0,15.)
79 pointsX.inset(0,(bins[0]+bins[1])/2.0)
80 pointsY.insert(0,pointsY[0])
81
82 if bins[-1] < 2500:
83 bins.append(2500.)
84 pointsX.append((bins[-1]+bins[-2])/2.0)
85 pointsY.append(pointsY[-1])
86
87 # Make the histo and fill it
88 histo = MakeProviderHisto(histoName,ptBins=bins,etaBins=[min(GetDefaultEtaBins()),0,max(GetDefaultEtaBins())])
89 for ptBin in range(1,histo.GetNbinsX()+1):
90 for etaBin in range(1,histo.GetNbinsY()+1):
91 histo.SetBinContent(ptBin,etaBin,pointsY[ptBin-1])
92
93 return histo
94
95def ExtendPtRangeOfHisto(histo,histoName):
96 # Get the current bins
97 ptBins = []
98 for xBin in range(1,histo.GetNbinsX()+2):
99 ptBins.append(histo.GetXaxis().GetBinLowEdge(xBin))
100
101 # Extend only if necessary
102 if math.fabs(ptBins[-1] - 2500) < 1.e-4:
103 print "Histo already went to 2500 GeV, doing nothing"
104 return histo
105 elif ptBins[-1] > 2500:
106 print "Histo beyond range, cannot extend"
107 return None
108 ptBins.append(2500.)
109
110 # Get eta bins
111 etaBins = []
112 for yBin in range(1,histo.GetNbinsY()+2):
113 etaBins.append(histo.GetYaxis().GetBinLowEdge(yBin))
114
115 # Make and fill
116 newHisto = MakeProviderHisto(histoName,ptBins=ptBins,etaBins=etaBins)
117 for xBin in range(1,histo.GetNbinsX()+1):
118 for yBin in range(1,histo.GetNbinsY()+1):
119 newHisto.SetBinContent(xBin,yBin,histo.GetBinContent(xBin,yBin))
120 for yBin in range(1,histo.GetNbinsY()+1):
121 newHisto.SetBinContent(histo.GetNbinsX()+1,yBin,histo.GetBinContent(histo.GetNbinsX(),yBin))
122
123 return newHisto
124
125def SymmetrizeHistoInEta(histo,histoName):
126 # Get the current eta bins and symmetrize
127 etaBins = []
128 for yBin in range(1,histo.GetNbinsY()+2):
129 etaVal = histo.GetYaxis().GetBinLowEdge(yBin)
130 if math.fabs(etaVal) > 1.e-4:
131 etaBins.append(-etaVal)
132 etaBins.append(etaVal)
133 etaBins = sorted(etaBins)
134
135 # Get the current pT bins
136 ptBins = []
137 for xBin in range(1,histo.GetNbinsX()+2):
138 ptBins.append(histo.GetXaxis().GetBinLowEdge(xBin))
139
140 # Make and fill
141 newHisto = MakeProviderHisto(histoName,ptBins=ptBins,etaBins=etaBins)
142 for xBin in range(1,histo.GetNbinsX()+1):
143 xVal = histo.GetXaxis().GetBinCenter(xBin)
144 for yBin in range(1,histo.GetNbinsY()+1):
145 yVal = histo.GetYaxis().GetBinCenter(yBin)
146 newHisto.SetBinContent(newHisto.GetXaxis().FindBin(xVal),newHisto.GetYaxis().FindBin(-yVal),histo.GetBinContent(xBin,yBin))
147 newHisto.SetBinContent(newHisto.GetXaxis().FindBin(xVal),newHisto.GetYaxis().FindBin(yVal),histo.GetBinContent(xBin,yBin))
148
149 return newHisto
150
151def QuadratureSumHisto(histoName,histos):
152 # If it's one histo, just return it
153 if len(histos) == 1:
154 return histos[0]
155
156 # Ensure that the binning is the same
157 tolerance = 1.e-4
158 for aHisto in histos[1:]:
159 if aHisto.GetNbinsX() != histos[0].GetNbinsX():
160 print "Input histograms have different number of x bins - can't do quadrature sum safely"
161 return None
162 elif aHisto.GetNbinsY() != histos[0].GetNbinsY():
163 print "Input histograms have different number of y bins - can't do quadrature sum safely"
164 return None
165 for xBin in range(1,histos[0].GetNbinsX()+2):
166 edge = None
167 for aHisto in histos:
168 if edge is None:
169 edge = aHisto.GetXaxis().GetBinLowEdge(xBin)
170 elif math.fabs(edge-aHisto.GetXaxis().GetBinLowEdge(xBin)) > tolerance:
171 print "Input histograms have different x binning - can't do quadrature sum safely"
172 return None
173 for yBin in range(1,histos[0].GetNbinsY()+2):
174 edge = None
175 for aHisto in histos:
176 if edge is None:
177 edge = aHisto.GetYaxis().GetBinLowEdge(yBin)
178 elif math.fabs(edge-aHisto.GetYaxis().GetBinLowEdge(yBin)) > tolerance:
179 print "Input histograms have different y binning - can't do quadrature sum safely"
180 return None
181
182 # Same binning - good, we can continue
183 # Clone the first histo for the binning
184 quadSumHisto = histos[0].Clone()
185 for xBin in range(1,quadSumHisto.GetNbinsX()+1):
186 for yBin in range(1,quadSumHisto.GetNbinsY()+1):
187 quadSum = 0
188 for aHisto in histos:
189 quadSum += pow(aHisto.GetBinContent(xBin,yBin),2)
190 quadSumHisto.SetBinContent(xBin,yBin,sqrt(quadSum))
191
192 return quadSumHisto
193
194
195
196
constexpr int pow(int base, int exp) noexcept
#define min(a, b)
Definition cfImp.cxx:40
#define max(a, b)
Definition cfImp.cxx:41
STL class.