Logo ROOT  
Reference Guide
rf102_dataimport.py
Go to the documentation of this file.
1## \file
2## \ingroup tutorial_roofit
3## \notebook
4## 'BASIC FUNCTIONALITY' RooFit tutorial macro #102
5## Importing data from ROOT TTrees and THx histograms
6##
7## \macro_code
8##
9## \date February 2018
10## \authors Clemens Lange, Wouter Verkerke (C version)
11
12import ROOT
13from array import array
14
15
16def makeTH1():
17
18 # Create ROOT ROOT.TH1 filled with a Gaussian distribution
19
20 hh = ROOT.TH1D("hh", "hh", 25, -10, 10)
21 for i in range(100):
22 hh.Fill(ROOT.gRandom.Gaus(0, 3))
23 return hh
24
25
26def makeTTree():
27 # Create ROOT ROOT.TTree filled with a Gaussian distribution in x and a
28 # uniform distribution in y
29
30 tree = ROOT.TTree("tree", "tree")
31 px = array("d", [0])
32 py = array("d", [0])
33 tree.Branch("x", px, "x/D")
34 tree.Branch("y", py, "y/D")
35 for i in range(100):
36 px[0] = ROOT.gRandom.Gaus(0, 3)
37 py[0] = ROOT.gRandom.Uniform() * 30 - 15
38 tree.Fill()
39 return tree
40
41
42############################
43# Importing ROOT histograms
44############################
45# Import ROOT TH1 into a RooDataHist
46# ---------------------------------------------------------
47# Create a ROOT TH1 histogram
48hh = makeTH1()
49
50# Declare observable x
51x = ROOT.RooRealVar("x", "x", -10, 10)
52
53# Create a binned dataset that imports contents of ROOT.TH1 and associates
54# its contents to observable 'x'
55dh = ROOT.RooDataHist("dh", "dh", [x], Import=hh)
56
57# Plot and fit a RooDataHist
58# ---------------------------------------------------
59# Make plot of binned dataset showing Poisson error bars (RooFit default)
60frame = x.frame(Title="Imported ROOT.TH1 with Poisson error bars")
61dh.plotOn(frame)
62
63# Fit a Gaussian p.d.f to the data
64mean = ROOT.RooRealVar("mean", "mean", 0, -10, 10)
65sigma = ROOT.RooRealVar("sigma", "sigma", 3, 0.1, 10)
66gauss = ROOT.RooGaussian("gauss", "gauss", x, mean, sigma)
67gauss.fitTo(dh)
68gauss.plotOn(frame)
69
70# Plot and fit a RooDataHist with internal errors
71# ---------------------------------------------------------------------------------------------
72
73# If histogram has custom error (i.e. its contents is does not originate from a Poisson process
74# but e.g. is a sum of weighted events) you can data with symmetric 'sum-of-weights' error instead
75# (same error bars as shown by ROOT)
76frame2 = x.frame(Title="Imported ROOT.TH1 with internal errors")
77dh.plotOn(frame2, DataError="SumW2")
78gauss.plotOn(frame2)
79
80# Please note that error bars shown (Poisson or SumW2) are for visualization only, the are NOT used
81# in a maximum likelihood fit
82#
83# A (binned) ML fit will ALWAYS assume the Poisson error interpretation of data (the mathematical definition
84# of likelihood does not take any external definition of errors). Data with non-unit weights can only be correctly
85# fitted with a chi^2 fit (see rf602_chi2fit.py)
86#
87# Importing ROOT TTrees
88# -----------------------------------------------------------
89# Import ROOT TTree into a RooDataSet
90
91tree = makeTTree()
92
93# Define 2nd observable y
94y = ROOT.RooRealVar("y", "y", -10, 10)
95
96# Construct unbinned dataset importing tree branches x and y matching between branches and ROOT.RooRealVars
97# is done by name of the branch/RRV
98#
99# Note that ONLY entries for which x,y have values within their allowed ranges as defined in
100# ROOT.RooRealVar x and y are imported. Since the y values in the import tree are in the range [-15,15]
101# and RRV y defines a range [-10,10] this means that the ROOT.RooDataSet
102# below will have less entries than the ROOT.TTree 'tree'
103
104ds = ROOT.RooDataSet("ds", "ds", {x, y}, Import=tree)
105
106# Use ascii import/export for datasets
107# ------------------------------------------------------------------------------------
108
109
110def write_dataset(ds, filename):
111 # Write data to output stream
112 outstream = ROOT.std.ofstream(filename)
113 # Optionally, adjust the stream here (e.g. std::setprecision)
114 ds.write(outstream)
115 outstream.close()
116
117
118write_dataset(ds, "rf102_testData.txt")
119
120# Read data from input stream. The variables of the dataset need to be supplied
121# to the RooDataSet::read() function.
122print("\n-----------------------\nReading data from ASCII")
123dataReadBack = ROOT.RooDataSet.read(
124 "rf102_testData.txt",
125 [x, y], # variables to be read. If the file has more fields, these are ignored.
126 "D", # Prints if a RooFit message stream listens for debug messages. Use Q for quiet.
127)
128
129dataReadBack.Print("V")
130
131print("\nOriginal data, line 20:")
132ds.get(20).Print("V")
133
134print("\nRead-back data, line 20:")
135dataReadBack.get(20).Print("V")
136
137
138# Plot data set with multiple binning choices
139# ------------------------------------------------------------------------------------
140# Print number of events in dataset
141ds.Print()
142
143# Print unbinned dataset with default frame binning (100 bins)
144frame3 = y.frame(Title="Unbinned data shown in default frame binning")
145ds.plotOn(frame3)
146
147# Print unbinned dataset with custom binning choice (20 bins)
148frame4 = y.frame(Title="Unbinned data shown with custom binning")
149ds.plotOn(frame4, Binning=20)
150
151frame5 = y.frame(Title="Unbinned data read back from ASCII file")
152ds.plotOn(frame5, Binning=20)
153dataReadBack.plotOn(frame5, Binning=20, MarkerColor="r", MarkerStyle=5)
154
155# Draw all frames on a canvas
156c = ROOT.TCanvas("rf102_dataimport", "rf102_dataimport", 800, 800)
157c.Divide(3, 2)
158c.cd(1)
159ROOT.gPad.SetLeftMargin(0.15)
160frame.GetYaxis().SetTitleOffset(1.4)
161frame.Draw()
162c.cd(2)
163ROOT.gPad.SetLeftMargin(0.15)
164frame2.GetYaxis().SetTitleOffset(1.4)
165frame2.Draw()
166c.cd(4)
167ROOT.gPad.SetLeftMargin(0.15)
168frame3.GetYaxis().SetTitleOffset(1.4)
169frame3.Draw()
170c.cd(5)
171ROOT.gPad.SetLeftMargin(0.15)
172frame4.GetYaxis().SetTitleOffset(1.4)
173frame4.Draw()
174c.cd(6)
175ROOT.gPad.SetLeftMargin(0.15)
176frame4.GetYaxis().SetTitleOffset(1.4)
177frame5.Draw()
178
179c.SaveAs("rf102_dataimport.png")
void Print(std::ostream &os, const OptionType &opt)