Logo ROOT  
Reference Guide
 
Loading...
Searching...
No Matches
TH1.cxx
Go to the documentation of this file.
1// @(#)root/hist:$Id$
2// Author: Rene Brun 26/12/94
3
4/*************************************************************************
5 * Copyright (C) 1995-2000, Rene Brun and Fons Rademakers. *
6 * All rights reserved. *
7 * *
8 * For the licensing terms see $ROOTSYS/LICENSE. *
9 * For the list of contributors see $ROOTSYS/README/CREDITS. *
10 *************************************************************************/
11
12#include <cstdlib>
13#include <cstring>
14#include <cstdio>
15#include <cctype>
16#include <climits>
17#include <sstream>
18#include <cmath>
19#include <iostream>
20
21#include "TROOT.h"
22#include "TBuffer.h"
23#include "TEnv.h"
24#include "TClass.h"
25#include "TMath.h"
26#include "THashList.h"
27#include "TH1.h"
28#include "TH2.h"
29#include "TH3.h"
30#include "TF2.h"
31#include "TF3.h"
32#include "TPluginManager.h"
33#include "TVirtualPad.h"
34#include "TRandom.h"
35#include "TVirtualFitter.h"
36#include "THLimitsFinder.h"
37#include "TProfile.h"
38#include "TStyle.h"
39#include "TVectorF.h"
40#include "TVectorD.h"
41#include "TBrowser.h"
42#include "TError.h"
43#include "TVirtualHistPainter.h"
44#include "TVirtualFFT.h"
45#include "TVirtualPaveStats.h"
46
47#include "HFitInterface.h"
48#include "Fit/DataRange.h"
49#include "Fit/BinData.h"
50#include "Math/GoFTest.h"
53
54#include "TH1Merger.h"
55
56/** \addtogroup Histograms
57@{
58\class TH1C
59\brief 1-D histogram with a byte per channel (see TH1 documentation)
60\class TH1S
61\brief 1-D histogram with a short per channel (see TH1 documentation)
62\class TH1I
63\brief 1-D histogram with an int per channel (see TH1 documentation)}
64\class TH1F
65\brief 1-D histogram with a float per channel (see TH1 documentation)}
66\class TH1D
67\brief 1-D histogram with a double per channel (see TH1 documentation)}
68@}
69*/
70
71/** \class TH1
72 \ingroup Histograms
73TH1 is the base class of all histogram classes in %ROOT.
74
75It provides the common interface for operations such as binning, filling, drawing, which
76will be detailed below.
77
78-# [Creating histograms](\ref creating-histograms)
79 - [Labelling axes](\ref labelling-axis)
80-# [Binning](\ref binning)
81 - [Fix or variable bin size](\ref fix-var)
82 - [Convention for numbering bins](\ref convention)
83 - [Alphanumeric Bin Labels](\ref alpha)
84 - [Histograms with automatic bins](\ref auto-bin)
85 - [Rebinning](\ref rebinning)
86-# [Filling histograms](\ref filling-histograms)
87 - [Associated errors](\ref associated-errors)
88 - [Associated functions](\ref associated-functions)
89 - [Projections of histograms](\ref prof-hist)
90 - [Random Numbers and histograms](\ref random-numbers)
91 - [Making a copy of a histogram](\ref making-a-copy)
92 - [Normalizing histograms](\ref normalizing)
93-# [Drawing histograms](\ref drawing-histograms)
94 - [Setting Drawing histogram contour levels (2-D hists only)](\ref cont-level)
95 - [Setting histogram graphics attributes](\ref graph-att)
96 - [Customising how axes are drawn](\ref axis-drawing)
97-# [Saving/reading histograms to/from a ROOT file](\ref saving-histograms)
98-# [Operations on histograms](\ref operations-on-histograms)
99 - [Fitting histograms](\ref fitting-histograms)
100-# [Miscellaneous operations](\ref misc)
101
102ROOT supports the following histogram types:
103
104 - 1-D histograms:
105 - TH1C : histograms with one byte per channel. Maximum bin content = 127
106 - TH1S : histograms with one short per channel. Maximum bin content = 32767
107 - TH1I : histograms with one int per channel. Maximum bin content = INT_MAX (\ref intmax "*")
108 - TH1F : histograms with one float per channel. Maximum precision 7 digits
109 - TH1D : histograms with one double per channel. Maximum precision 14 digits
110 - 2-D histograms:
111 - TH2C : histograms with one byte per channel. Maximum bin content = 127
112 - TH2S : histograms with one short per channel. Maximum bin content = 32767
113 - TH2I : histograms with one int per channel. Maximum bin content = INT_MAX (\ref intmax "*")
114 - TH2F : histograms with one float per channel. Maximum precision 7 digits
115 - TH2D : histograms with one double per channel. Maximum precision 14 digits
116 - 3-D histograms:
117 - TH3C : histograms with one byte per channel. Maximum bin content = 127
118 - TH3S : histograms with one short per channel. Maximum bin content = 32767
119 - TH3I : histograms with one int per channel. Maximum bin content = INT_MAX (\ref intmax "*")
120 - TH3F : histograms with one float per channel. Maximum precision 7 digits
121 - TH3D : histograms with one double per channel. Maximum precision 14 digits
122 - Profile histograms: See classes TProfile, TProfile2D and TProfile3D.
123 Profile histograms are used to display the mean value of Y and its standard deviation
124 for each bin in X. Profile histograms are in many cases an elegant
125 replacement of two-dimensional histograms : the inter-relation of two
126 measured quantities X and Y can always be visualized by a two-dimensional
127 histogram or scatter-plot; If Y is an unknown (but single-valued)
128 approximate function of X, this function is displayed by a profile
129 histogram with much better precision than by a scatter-plot.
130
131<sup>
132\anchor intmax (*) INT_MAX = 2147483647 is the [maximum value for a variable of type int.](https://docs.microsoft.com/en-us/cpp/c-language/cpp-integer-limits)
133</sup>
134
135The inheritance hierarchy looks as follows:
136
137\image html classTH1__inherit__graph_org.svg width=100%
138
139\anchor creating-histograms
140## Creating histograms
141
142Histograms are created by invoking one of the constructors, e.g.
143~~~ {.cpp}
144 TH1F *h1 = new TH1F("h1", "h1 title", 100, 0, 4.4);
145 TH2F *h2 = new TH2F("h2", "h2 title", 40, 0, 4, 30, -3, 3);
146~~~
147Histograms may also be created by:
148
149 - calling the Clone() function, see below
150 - making a projection from a 2-D or 3-D histogram, see below
151 - reading a histogram from a file
152
153 When a histogram is created, a reference to it is automatically added
154 to the list of in-memory objects for the current file or directory.
155 Then the pointer to this histogram in the current directory can be found
156 by its name, doing:
157~~~ {.cpp}
158 TH1F *h1 = (TH1F*)gDirectory->FindObject(name);
159~~~
160
161 This default behaviour can be changed by:
162~~~ {.cpp}
163 h->SetDirectory(0); // for the current histogram h
164 TH1::AddDirectory(kFALSE); // sets a global switch disabling the referencing
165~~~
166 When the histogram is deleted, the reference to it is removed from
167 the list of objects in memory.
168 When a file is closed, all histograms in memory associated with this file
169 are automatically deleted.
170
171\anchor labelling-axis
172### Labelling axes
173
174 Axis titles can be specified in the title argument of the constructor.
175 They must be separated by ";":
176~~~ {.cpp}
177 TH1F* h=new TH1F("h", "Histogram title;X Axis;Y Axis", 100, 0, 1);
178~~~
179 The histogram title and the axis titles can be any TLatex string, and
180 are persisted if a histogram is written to a file.
181
182 Any title can be omitted:
183~~~ {.cpp}
184 TH1F* h=new TH1F("h", "Histogram title;;Y Axis", 100, 0, 1);
185 TH1F* h=new TH1F("h", ";;Y Axis", 100, 0, 1);
186~~~
187 The method SetTitle() has the same syntax:
188~~~ {.cpp}
189 h->SetTitle("Histogram title;Another X title Axis");
190~~~
191Alternatively, the title of each axis can be set directly:
192~~~ {.cpp}
193 h->GetXaxis()->SetTitle("X axis title");
194 h->GetYaxis()->SetTitle("Y axis title");
195~~~
196For bin labels see \ref binning.
197
198\anchor binning
199## Binning
200
201\anchor fix-var
202### Fix or variable bin size
203
204 All histogram types support either fix or variable bin sizes.
205 2-D histograms may have fix size bins along X and variable size bins
206 along Y or vice-versa. The functions to fill, manipulate, draw or access
207 histograms are identical in both cases.
208
209 Each histogram always contains 3 axis objects of type TAxis: fXaxis, fYaxis and fZaxis.
210 To access the axis parameters, use:
211~~~ {.cpp}
212 TAxis *xaxis = h->GetXaxis(); etc.
213 Double_t binCenter = xaxis->GetBinCenter(bin), etc.
214~~~
215 See class TAxis for a description of all the access functions.
216 The axis range is always stored internally in double precision.
217
218\anchor convention
219### Convention for numbering bins
220
221 For all histogram types: nbins, xlow, xup
222~~~ {.cpp}
223 bin = 0; underflow bin
224 bin = 1; first bin with low-edge xlow INCLUDED
225 bin = nbins; last bin with upper-edge xup EXCLUDED
226 bin = nbins+1; overflow bin
227~~~
228 In case of 2-D or 3-D histograms, a "global bin" number is defined.
229 For example, assuming a 3-D histogram with (binx, biny, binz), the function
230~~~ {.cpp}
231 Int_t gbin = h->GetBin(binx, biny, binz);
232~~~
233 returns a global/linearized gbin number. This global gbin is useful
234 to access the bin content/error information independently of the dimension.
235 Note that to access the information other than bin content and errors
236 one should use the TAxis object directly with e.g.:
237~~~ {.cpp}
238 Double_t xcenter = h3->GetZaxis()->GetBinCenter(27);
239~~~
240 returns the center along z of bin number 27 (not the global bin)
241 in the 3-D histogram h3.
242
243\anchor alpha
244### Alphanumeric Bin Labels
245
246 By default, a histogram axis is drawn with its numeric bin labels.
247 One can specify alphanumeric labels instead with:
248
249 - call TAxis::SetBinLabel(bin, label);
250 This can always be done before or after filling.
251 When the histogram is drawn, bin labels will be automatically drawn.
252 See examples labels1.C and labels2.C
253 - call to a Fill function with one of the arguments being a string, e.g.
254~~~ {.cpp}
255 hist1->Fill(somename, weight);
256 hist2->Fill(x, somename, weight);
257 hist2->Fill(somename, y, weight);
258 hist2->Fill(somenamex, somenamey, weight);
259~~~
260 See examples hlabels1.C and hlabels2.C
261 - via TTree::Draw. see for example cernstaff.C
262~~~ {.cpp}
263 tree.Draw("Nation::Division");
264~~~
265 where "Nation" and "Division" are two branches of a Tree.
266
267When using the options 2 or 3 above, the labels are automatically
268 added to the list (THashList) of labels for a given axis.
269 By default, an axis is drawn with the order of bins corresponding
270 to the filling sequence. It is possible to reorder the axis
272 - alphabetically
273 - by increasing or decreasing values
274
275 The reordering can be triggered via the TAxis context menu by selecting
276 the menu item "LabelsOption" or by calling directly
277 TH1::LabelsOption(option, axis) where
278
279 - axis may be "X", "Y" or "Z"
280 - option may be:
281 - "a" sort by alphabetic order
282 - ">" sort by decreasing values
283 - "<" sort by increasing values
284 - "h" draw labels horizontal
285 - "v" draw labels vertical
286 - "u" draw labels up (end of label right adjusted)
287 - "d" draw labels down (start of label left adjusted)
288
289 When using the option 2 above, new labels are added by doubling the current
290 number of bins in case one label does not exist yet.
291 When the Filling is terminated, it is possible to trim the number
292 of bins to match the number of active labels by calling
293~~~ {.cpp}
294 TH1::LabelsDeflate(axis) with axis = "X", "Y" or "Z"
295~~~
296 This operation is automatic when using TTree::Draw.
297 Once bin labels have been created, they become persistent if the histogram
298 is written to a file or when generating the C++ code via SavePrimitive.
299
300\anchor auto-bin
301### Histograms with automatic bins
302
303 When a histogram is created with an axis lower limit greater or equal
304 to its upper limit, the SetBuffer is automatically called with an
305 argument fBufferSize equal to fgBufferSize (default value=1000).
306 fgBufferSize may be reset via the static function TH1::SetDefaultBufferSize.
307 The axis limits will be automatically computed when the buffer will
308 be full or when the function BufferEmpty is called.
309
310\anchor rebinning
311### Rebinning
312
313 At any time, a histogram can be rebinned via TH1::Rebin. This function
314 returns a new histogram with the rebinned contents.
315 If bin errors were stored, they are recomputed during the rebinning.
316
317
318\anchor filling-histograms
319## Filling histograms
320
321 A histogram is typically filled with statements like:
322~~~ {.cpp}
323 h1->Fill(x);
324 h1->Fill(x, w); //fill with weight
325 h2->Fill(x, y)
326 h2->Fill(x, y, w)
327 h3->Fill(x, y, z)
328 h3->Fill(x, y, z, w)
329~~~
330 or via one of the Fill functions accepting names described above.
331 The Fill functions compute the bin number corresponding to the given
332 x, y or z argument and increment this bin by the given weight.
333 The Fill functions return the bin number for 1-D histograms or global
334 bin number for 2-D and 3-D histograms.
335 If TH1::Sumw2 has been called before filling, the sum of squares of
336 weights is also stored.
337 One can also increment directly a bin number via TH1::AddBinContent
338 or replace the existing content via TH1::SetBinContent.
339 To access the bin content of a given bin, do:
340~~~ {.cpp}
341 Double_t binContent = h->GetBinContent(bin);
342~~~
343
344 By default, the bin number is computed using the current axis ranges.
345 If the automatic binning option has been set via
346~~~ {.cpp}
347 h->SetCanExtend(TH1::kAllAxes);
348~~~
349 then, the Fill Function will automatically extend the axis range to
350 accomodate the new value specified in the Fill argument. The method
351 used is to double the bin size until the new value fits in the range,
352 merging bins two by two. This automatic binning options is extensively
353 used by the TTree::Draw function when histogramming Tree variables
354 with an unknown range.
355 This automatic binning option is supported for 1-D, 2-D and 3-D histograms.
356
357 During filling, some statistics parameters are incremented to compute
358 the mean value and Root Mean Square with the maximum precision.
359
360 In case of histograms of type TH1C, TH1S, TH2C, TH2S, TH3C, TH3S
361 a check is made that the bin contents do not exceed the maximum positive
362 capacity (127 or 32767). Histograms of all types may have positive
363 or/and negative bin contents.
364
365\anchor associated-errors
366### Associated errors
367 By default, for each bin, the sum of weights is computed at fill time.
368 One can also call TH1::Sumw2 to force the storage and computation
369 of the sum of the square of weights per bin.
370 If Sumw2 has been called, the error per bin is computed as the
371 sqrt(sum of squares of weights), otherwise the error is set equal
372 to the sqrt(bin content).
373 To return the error for a given bin number, do:
374~~~ {.cpp}
375 Double_t error = h->GetBinError(bin);
376~~~
377
378\anchor associated-functions
379### Associated functions
380 One or more object (typically a TF1*) can be added to the list
381 of functions (fFunctions) associated to each histogram.
382 When TH1::Fit is invoked, the fitted function is added to this list.
383 Given a histogram h, one can retrieve an associated function
384 with:
385~~~ {.cpp}
386 TF1 *myfunc = h->GetFunction("myfunc");
387~~~
388
389
390\anchor operations-on-histograms
391## Operations on histograms
392
393 Many types of operations are supported on histograms or between histograms
394
395 - Addition of a histogram to the current histogram.
396 - Additions of two histograms with coefficients and storage into the current
397 histogram.
398 - Multiplications and Divisions are supported in the same way as additions.
399 - The Add, Divide and Multiply functions also exist to add, divide or multiply
400 a histogram by a function.
401
402 If a histogram has associated error bars (TH1::Sumw2 has been called),
403 the resulting error bars are also computed assuming independent histograms.
404 In case of divisions, Binomial errors are also supported.
405 One can mark a histogram to be an "average" histogram by setting its bit kIsAverage via
406 myhist.SetBit(TH1::kIsAverage);
407 When adding (see TH1::Add) average histograms, the histograms are averaged and not summed.
408
409\anchor fitting-histograms
410### Fitting histograms
411
412 Histograms (1-D, 2-D, 3-D and Profiles) can be fitted with a user
413 specified function via TH1::Fit. When a histogram is fitted, the
414 resulting function with its parameters is added to the list of functions
415 of this histogram. If the histogram is made persistent, the list of
416 associated functions is also persistent. Given a pointer (see above)
417 to an associated function myfunc, one can retrieve the function/fit
418 parameters with calls such as:
419~~~ {.cpp}
420 Double_t chi2 = myfunc->GetChisquare();
421 Double_t par0 = myfunc->GetParameter(0); value of 1st parameter
422 Double_t err0 = myfunc->GetParError(0); error on first parameter
423~~~
424
425\anchor prof-hist
426### Projections of histograms
427
428 One can:
429
430 - make a 1-D projection of a 2-D histogram or Profile
431 see functions TH2::ProjectionX,Y, TH2::ProfileX,Y, TProfile::ProjectionX
432 - make a 1-D, 2-D or profile out of a 3-D histogram
433 see functions TH3::ProjectionZ, TH3::Project3D.
434
435 One can fit these projections via:
436~~~ {.cpp}
437 TH2::FitSlicesX,Y, TH3::FitSlicesZ.
438~~~
439
440\anchor random-numbers
441### Random Numbers and histograms
442
443 TH1::FillRandom can be used to randomly fill a histogram using
444 the contents of an existing TF1 function or another
445 TH1 histogram (for all dimensions).
446 For example, the following two statements create and fill a histogram
447 10000 times with a default gaussian distribution of mean 0 and sigma 1:
448~~~ {.cpp}
449 TH1F h1("h1", "histo from a gaussian", 100, -3, 3);
450 h1.FillRandom("gaus", 10000);
451~~~
452 TH1::GetRandom can be used to return a random number distributed
453 according to the contents of a histogram.
454
455\anchor making-a-copy
456### Making a copy of a histogram
457 Like for any other ROOT object derived from TObject, one can use
458 the Clone() function. This makes an identical copy of the original
459 histogram including all associated errors and functions, e.g.:
460~~~ {.cpp}
461 TH1F *hnew = (TH1F*)h->Clone("hnew");
462~~~
463
464\anchor normalizing
465### Normalizing histograms
466
467 One can scale a histogram such that the bins integral is equal to
468 the normalization parameter via TH1::Scale(Double_t norm), where norm
469 is the desired normalization divided by the integral of the histogram.
470
471
472\anchor drawing-histograms
473## Drawing histograms
474
475 Histograms are drawn via the THistPainter class. Each histogram has
476 a pointer to its own painter (to be usable in a multithreaded program).
477 Many drawing options are supported.
478 See THistPainter::Paint() for more details.
479
480 The same histogram can be drawn with different options in different pads.
481 When a histogram drawn in a pad is deleted, the histogram is
482 automatically removed from the pad or pads where it was drawn.
483 If a histogram is drawn in a pad, then filled again, the new status
484 of the histogram will be automatically shown in the pad next time
485 the pad is updated. One does not need to redraw the histogram.
486 To draw the current version of a histogram in a pad, one can use
487~~~ {.cpp}
488 h->DrawCopy();
489~~~
490 This makes a clone (see Clone below) of the histogram. Once the clone
491 is drawn, the original histogram may be modified or deleted without
492 affecting the aspect of the clone.
493
494 One can use TH1::SetMaximum() and TH1::SetMinimum() to force a particular
495 value for the maximum or the minimum scale on the plot. (For 1-D
496 histograms this means the y-axis, while for 2-D histograms these
497 functions affect the z-axis).
498
499 TH1::UseCurrentStyle() can be used to change all histogram graphics
500 attributes to correspond to the current selected style.
501 This function must be called for each histogram.
502 In case one reads and draws many histograms from a file, one can force
503 the histograms to inherit automatically the current graphics style
504 by calling before gROOT->ForceStyle().
505
506\anchor cont-level
507### Setting Drawing histogram contour levels (2-D hists only)
508
509 By default contours are automatically generated at equidistant
510 intervals. A default value of 20 levels is used. This can be modified
511 via TH1::SetContour() or TH1::SetContourLevel().
512 the contours level info is used by the drawing options "cont", "surf",
513 and "lego".
514
515\anchor graph-att
516### Setting histogram graphics attributes
517
518 The histogram classes inherit from the attribute classes:
519 TAttLine, TAttFill, and TAttMarker.
520 See the member functions of these classes for the list of options.
521
522\anchor axis-drawing
523### Customising how axes are drawn
524
525 Use the functions of TAxis, such as
526~~~ {.cpp}
527 histogram.GetXaxis()->SetTicks("+");
528 histogram.GetYaxis()->SetRangeUser(1., 5.);
529~~~
530
531\anchor saving-histograms
532## Saving/reading histograms to/from a ROOT file
533
534 The following statements create a ROOT file and store a histogram
535 on the file. Because TH1 derives from TNamed, the key identifier on
536 the file is the histogram name:
537~~~ {.cpp}
538 TFile f("histos.root", "new");
539 TH1F h1("hgaus", "histo from a gaussian", 100, -3, 3);
540 h1.FillRandom("gaus", 10000);
541 h1->Write();
542~~~
543 To read this histogram in another Root session, do:
544~~~ {.cpp}
545 TFile f("histos.root");
546 TH1F *h = (TH1F*)f.Get("hgaus");
547~~~
548 One can save all histograms in memory to the file by:
549~~~ {.cpp}
550 file->Write();
551~~~
552
553
554\anchor misc
555## Miscellaneous operations
556
557~~~ {.cpp}
558 TH1::KolmogorovTest(): statistical test of compatibility in shape
559 between two histograms
560 TH1::Smooth() smooths the bin contents of a 1-d histogram
561 TH1::Integral() returns the integral of bin contents in a given bin range
562 TH1::GetMean(int axis) returns the mean value along axis
563 TH1::GetStdDev(int axis) returns the sigma distribution along axis
564 TH1::GetEntries() returns the number of entries
565 TH1::Reset() resets the bin contents and errors of a histogram
566~~~
567 IMPORTANT NOTE: The returned values for GetMean and GetStdDev depend on how the
568 histogram statistics are calculated. By default, if no range has been set, the
569 returned values are the (unbinned) ones calculated at fill time. If a range has been
570 set, however, the values are calculated using the bins in range; THIS IS TRUE EVEN
571 IF THE RANGE INCLUDES ALL BINS--use TAxis::SetRange(0, 0) to unset the range.
572 To ensure that the returned values are always those of the binned data stored in the
573 histogram, call TH1::ResetStats. See TH1::GetStats.
574*/
575
576TF1 *gF1=0; //left for back compatibility (use TVirtualFitter::GetUserFunc instead)
577
582
583extern void H1InitGaus();
584extern void H1InitExpo();
585extern void H1InitPolynom();
586extern void H1LeastSquareFit(Int_t n, Int_t m, Double_t *a);
587extern void H1LeastSquareLinearFit(Int_t ndata, Double_t &a0, Double_t &a1, Int_t &ifail);
588extern void H1LeastSquareSeqnd(Int_t n, Double_t *a, Int_t idim, Int_t &ifail, Int_t k, Double_t *b);
589
590// Internal exceptions for the CheckConsistency method
591class DifferentDimension: public std::exception {};
592class DifferentNumberOfBins: public std::exception {};
593class DifferentAxisLimits: public std::exception {};
594class DifferentBinLimits: public std::exception {};
595class DifferentLabels: public std::exception {};
596
598
599////////////////////////////////////////////////////////////////////////////////
600/// Histogram default constructor.
601
603{
604 fDirectory = 0;
605 fFunctions = new TList;
606 fNcells = 0;
607 fIntegral = 0;
608 fPainter = 0;
609 fEntries = 0;
610 fNormFactor = 0;
612 fMaximum = -1111;
613 fMinimum = -1111;
614 fBufferSize = 0;
615 fBuffer = 0;
618 fXaxis.SetName("xaxis");
619 fYaxis.SetName("yaxis");
620 fZaxis.SetName("zaxis");
621 fXaxis.SetParent(this);
622 fYaxis.SetParent(this);
623 fZaxis.SetParent(this);
625}
626
627////////////////////////////////////////////////////////////////////////////////
628/// Histogram default destructor.
629
631{
633 return;
634 }
635 delete[] fIntegral;
636 fIntegral = 0;
637 delete[] fBuffer;
638 fBuffer = 0;
639 if (fFunctions) {
641
643 TObject* obj = 0;
644 //special logic to support the case where the same object is
645 //added multiple times in fFunctions.
646 //This case happens when the same object is added with different
647 //drawing modes
648 //In the loop below we must be careful with objects (eg TCutG) that may
649 // have been added to the list of functions of several histograms
650 //and may have been already deleted.
651 while ((obj = fFunctions->First())) {
652 while(fFunctions->Remove(obj)) { }
654 break;
655 }
656 delete obj;
657 obj = 0;
658 }
659 delete fFunctions;
660 fFunctions = 0;
661 }
662 if (fDirectory) {
663 fDirectory->Remove(this);
664 fDirectory = 0;
665 }
666 delete fPainter;
667 fPainter = 0;
668}
669
670////////////////////////////////////////////////////////////////////////////////
671/// Constructor for fix bin size histograms.
672/// Creates the main histogram structure.
673///
674/// \param[in] name name of histogram (avoid blanks)
675/// \param[in] title histogram title.
676/// If title is of the form `stringt;stringx;stringy;stringz`,
677/// the histogram title is set to `stringt`,
678/// the x axis title to `stringx`, the y axis title to `stringy`, etc.
679/// \param[in] nbins number of bins
680/// \param[in] xlow low edge of first bin
681/// \param[in] xup upper edge of last bin (not included in last bin)
682
683
684TH1::TH1(const char *name,const char *title,Int_t nbins,Double_t xlow,Double_t xup)
685 :TNamed(name,title), TAttLine(), TAttFill(), TAttMarker()
686{
687 Build();
688 if (nbins <= 0) {Warning("TH1","nbins is <=0 - set to nbins = 1"); nbins = 1; }
689 fXaxis.Set(nbins,xlow,xup);
690 fNcells = fXaxis.GetNbins()+2;
691}
692
693////////////////////////////////////////////////////////////////////////////////
694/// Constructor for variable bin size histograms using an input array of type float.
695/// Creates the main histogram structure.
696///
697/// \param[in] name name of histogram (avoid blanks)
698/// \param[in] title histogram title.
699/// If title is of the form `stringt;stringx;stringy;stringz`
700/// the histogram title is set to `stringt`,
701/// the x axis title to `stringx`, the y axis title to `stringy`, etc.
702/// \param[in] nbins number of bins
703/// \param[in] xbins array of low-edges for each bin.
704/// This is an array of type float and size nbins+1
705
706TH1::TH1(const char *name,const char *title,Int_t nbins,const Float_t *xbins)
707 :TNamed(name,title), TAttLine(), TAttFill(), TAttMarker()
708{
709 Build();
710 if (nbins <= 0) {Warning("TH1","nbins is <=0 - set to nbins = 1"); nbins = 1; }
711 if (xbins) fXaxis.Set(nbins,xbins);
712 else fXaxis.Set(nbins,0,1);
713 fNcells = fXaxis.GetNbins()+2;
714}
715
716////////////////////////////////////////////////////////////////////////////////
717/// Constructor for variable bin size histograms using an input array of type double.
718///
719/// \param[in] name name of histogram (avoid blanks)
720/// \param[in] title histogram title.
721/// If title is of the form `stringt;stringx;stringy;stringz`
722/// the histogram title is set to `stringt`,
723/// the x axis title to `stringx`, the y axis title to `stringy`, etc.
724/// \param[in] nbins number of bins
725/// \param[in] xbins array of low-edges for each bin.
726/// This is an array of type double and size nbins+1
727
728TH1::TH1(const char *name,const char *title,Int_t nbins,const Double_t *xbins)
729 :TNamed(name,title), TAttLine(), TAttFill(), TAttMarker()
730{
731 Build();
732 if (nbins <= 0) {Warning("TH1","nbins is <=0 - set to nbins = 1"); nbins = 1; }
733 if (xbins) fXaxis.Set(nbins,xbins);
734 else fXaxis.Set(nbins,0,1);
735 fNcells = fXaxis.GetNbins()+2;
736}
737
738////////////////////////////////////////////////////////////////////////////////
739/// Private copy constructor.
740/// One should use the copy constructor of the derived classes (e.g. TH1D, TH1F ...).
741/// The list of functions is not copied. (Use Clone() if needed)
742
744{
745 ((TH1&)h).Copy(*this);
746}
747
748////////////////////////////////////////////////////////////////////////////////
749/// Static function: cannot be inlined on Windows/NT.
750
752{
753 return fgAddDirectory;
754}
755
756////////////////////////////////////////////////////////////////////////////////
757/// Browse the Histogram object.
758
760{
761 Draw(b ? b->GetDrawOption() : "");
762 gPad->Update();
763}
764
765////////////////////////////////////////////////////////////////////////////////
766/// Creates histogram basic data structure.
767
769{
770 fDirectory = 0;
771 fPainter = 0;
772 fIntegral = 0;
773 fEntries = 0;
774 fNormFactor = 0;
776 fMaximum = -1111;
777 fMinimum = -1111;
778 fBufferSize = 0;
779 fBuffer = 0;
782 fXaxis.SetName("xaxis");
783 fYaxis.SetName("yaxis");
784 fZaxis.SetName("zaxis");
785 fYaxis.Set(1,0.,1.);
786 fZaxis.Set(1,0.,1.);
787 fXaxis.SetParent(this);
788 fYaxis.SetParent(this);
789 fZaxis.SetParent(this);
790
792
793 fFunctions = new TList;
794
796
799 if (fDirectory) {
801 fDirectory->Append(this,kTRUE);
802 }
803 }
804}
805
806////////////////////////////////////////////////////////////////////////////////
807/// Performs the operation: `this = this + c1*f1`
808/// if errors are defined (see TH1::Sumw2), errors are also recalculated.
809///
810/// By default, the function is computed at the centre of the bin.
811/// if option "I" is specified (1-d histogram only), the integral of the
812/// function in each bin is used instead of the value of the function at
813/// the centre of the bin.
814///
815/// Only bins inside the function range are recomputed.
816///
817/// IMPORTANT NOTE: If you intend to use the errors of this histogram later
818/// you should call Sumw2 before making this operation.
819/// This is particularly important if you fit the histogram after TH1::Add
820///
821/// The function return kFALSE if the Add operation failed
822
824{
825 if (!f1) {
826 Error("Add","Attempt to add a non-existing function");
827 return kFALSE;
828 }
829
830 TString opt = option;
831 opt.ToLower();
832 Bool_t integral = kFALSE;
833 if (opt.Contains("i") && fDimension == 1) integral = kTRUE;
834
835 Int_t ncellsx = GetNbinsX() + 2; // cells = normal bins + underflow bin + overflow bin
836 Int_t ncellsy = GetNbinsY() + 2;
837 Int_t ncellsz = GetNbinsZ() + 2;
838 if (fDimension < 2) ncellsy = 1;
839 if (fDimension < 3) ncellsz = 1;
840
841 // delete buffer if it is there since it will become invalid
842 if (fBuffer) BufferEmpty(1);
843
844 // - Add statistics
845 Double_t s1[10];
846 for (Int_t i = 0; i < 10; ++i) s1[i] = 0;
847 PutStats(s1);
848 SetMinimum();
849 SetMaximum();
850
851 // - Loop on bins (including underflows/overflows)
852 Int_t bin, binx, biny, binz;
853 Double_t cu=0;
854 Double_t xx[3];
855 Double_t *params = 0;
856 f1->InitArgs(xx,params);
857 for (binz = 0; binz < ncellsz; ++binz) {
858 xx[2] = fZaxis.GetBinCenter(binz);
859 for (biny = 0; biny < ncellsy; ++biny) {
860 xx[1] = fYaxis.GetBinCenter(biny);
861 for (binx = 0; binx < ncellsx; ++binx) {
862 xx[0] = fXaxis.GetBinCenter(binx);
863 if (!f1->IsInside(xx)) continue;
865 bin = binx + ncellsx * (biny + ncellsy * binz);
866 if (integral) {
867 cu = c1*f1->Integral(fXaxis.GetBinLowEdge(binx), fXaxis.GetBinUpEdge(binx), 0.) / fXaxis.GetBinWidth(binx);
868 } else {
869 cu = c1*f1->EvalPar(xx);
870 }
871 if (TF1::RejectedPoint()) continue;
872 AddBinContent(bin,cu);
873 }
874 }
875 }
876
877 return kTRUE;
878}
879
880////////////////////////////////////////////////////////////////////////////////
881/// Performs the operation: `this = this + c1*h1`
882/// If errors are defined (see TH1::Sumw2), errors are also recalculated.
883///
884/// Note that if h1 has Sumw2 set, Sumw2 is automatically called for this
885/// if not already set.
886///
887/// Note also that adding histogram with labels is not supported, histogram will be
888/// added merging them by bin number independently of the labels.
889/// For adding histogram with labels one should use TH1::Merge
890///
891/// SPECIAL CASE (Average/Efficiency histograms)
892/// For histograms representing averages or efficiencies, one should compute the average
893/// of the two histograms and not the sum. One can mark a histogram to be an average
894/// histogram by setting its bit kIsAverage with
895/// myhist.SetBit(TH1::kIsAverage);
896/// Note that the two histograms must have their kIsAverage bit set
897///
898/// IMPORTANT NOTE1: If you intend to use the errors of this histogram later
899/// you should call Sumw2 before making this operation.
900/// This is particularly important if you fit the histogram after TH1::Add
901///
902/// IMPORTANT NOTE2: if h1 has a normalisation factor, the normalisation factor
903/// is used , ie this = this + c1*factor*h1
904/// Use the other TH1::Add function if you do not want this feature
905///
906/// IMPORTANT NOTE3: You should be careful about the statistics of the
907/// returned histogram, whose statistics may be binned or unbinned,
908/// depending on whether c1 is negative, whether TAxis::kAxisRange is true,
909/// and whether TH1::ResetStats has been called on either this or h1.
910/// See TH1::GetStats.
911///
912/// The function return kFALSE if the Add operation failed
913
915{
916 if (!h1) {
917 Error("Add","Attempt to add a non-existing histogram");
918 return kFALSE;
919 }
920
921 // delete buffer if it is there since it will become invalid
922 if (fBuffer) BufferEmpty(1);
923
924 bool useMerge = (c1 == 1. && !this->TestBit(kIsAverage) && !h1->TestBit(kIsAverage) );
925 try {
926 CheckConsistency(this,h1);
927 useMerge = kFALSE;
928 } catch(DifferentNumberOfBins&) {
929 if (useMerge)
930 Info("Add","Attempt to add histograms with different number of bins - trying to use TH1::Merge");
931 else {
932 Error("Add","Attempt to add histograms with different number of bins : nbins h1 = %d , nbins h2 = %d",GetNbinsX(), h1->GetNbinsX());
933 return kFALSE;
934 }
935 } catch(DifferentAxisLimits&) {
936 if (useMerge)
937 Info("Add","Attempt to add histograms with different axis limits - trying to use TH1::Merge");
938 else
939 Warning("Add","Attempt to add histograms with different axis limits");
940 } catch(DifferentBinLimits&) {
941 if (useMerge)
942 Info("Add","Attempt to add histograms with different bin limits - trying to use TH1::Merge");
943 else
944 Warning("Add","Attempt to add histograms with different bin limits");
945 } catch(DifferentLabels&) {
946 // in case of different labels -
947 if (useMerge)
948 Info("Add","Attempt to add histograms with different labels - trying to use TH1::Merge");
949 else
950 Info("Warning","Attempt to add histograms with different labels");
951 }
952
953 if (useMerge) {
954 TList l;
955 l.Add(const_cast<TH1*>(h1));
956 auto iret = Merge(&l);
957 return (iret >= 0);
958 }
959
960 // Create Sumw2 if h1 has Sumw2 set
961 if (fSumw2.fN == 0 && h1->GetSumw2N() != 0) Sumw2();
962
963 // - Add statistics
964 Double_t entries = TMath::Abs( GetEntries() + c1 * h1->GetEntries() );
965
966 // statistics can be preserved only in case of positive coefficients
967 // otherwise with negative c1 (histogram subtraction) one risks to get negative variances
968 Bool_t resetStats = (c1 < 0);
969 Double_t s1[kNstat] = {0};
970 Double_t s2[kNstat] = {0};
971 if (!resetStats) {
972 // need to initialize to zero s1 and s2 since
973 // GetStats fills only used elements depending on dimension and type
974 GetStats(s1);
975 h1->GetStats(s2);
976 }
977
978 SetMinimum();
979 SetMaximum();
980
981 // - Loop on bins (including underflows/overflows)
982 Double_t factor = 1;
983 if (h1->GetNormFactor() != 0) factor = h1->GetNormFactor()/h1->GetSumOfWeights();;
984 Double_t c1sq = c1 * c1;
985 Double_t factsq = factor * factor;
986
987 for (Int_t bin = 0; bin < fNcells; ++bin) {
988 //special case where histograms have the kIsAverage bit set
989 if (this->TestBit(kIsAverage) && h1->TestBit(kIsAverage)) {
990 Double_t y1 = h1->RetrieveBinContent(bin);
991 Double_t y2 = this->RetrieveBinContent(bin);
993 Double_t e2sq = this->GetBinErrorSqUnchecked(bin);
994 Double_t w1 = 1., w2 = 1.;
995
996 // consider all special cases when bin errors are zero
997 // see http://root-forum.cern.ch/viewtopic.php?f=3&t=13299
998 if (e1sq) w1 = 1. / e1sq;
999 else if (h1->fSumw2.fN) {
1000 w1 = 1.E200; // use an arbitrary huge value
1001 if (y1 == 0) {
1002 // use an estimated error from the global histogram scale
1003 double sf = (s2[0] != 0) ? s2[1]/s2[0] : 1;
1004 w1 = 1./(sf*sf);
1005 }
1006 }
1007 if (e2sq) w2 = 1. / e2sq;
1008 else if (fSumw2.fN) {
1009 w2 = 1.E200; // use an arbitrary huge value
1010 if (y2 == 0) {
1011 // use an estimated error from the global histogram scale
1012 double sf = (s1[0] != 0) ? s1[1]/s1[0] : 1;
1013 w2 = 1./(sf*sf);
1014 }
1015 }
1016
1017 double y = (w1*y1 + w2*y2)/(w1 + w2);
1018 UpdateBinContent(bin, y);
1019 if (fSumw2.fN) {
1020 double err2 = 1./(w1 + w2);
1021 if (err2 < 1.E-200) err2 = 0; // to remove arbitrary value when e1=0 AND e2=0
1022 fSumw2.fArray[bin] = err2;
1023 }
1024 } else { // normal case of addition between histograms
1025 AddBinContent(bin, c1 * factor * h1->RetrieveBinContent(bin));
1026 if (fSumw2.fN) fSumw2.fArray[bin] += c1sq * factsq * h1->GetBinErrorSqUnchecked(bin);
1027 }
1028 }
1029
1030 // update statistics (do here to avoid changes by SetBinContent)
1031 if (resetStats) {
1032 // statistics need to be reset in case coefficient are negative
1033 ResetStats();
1034 }
1035 else {
1036 for (Int_t i=0;i<kNstat;i++) {
1037 if (i == 1) s1[i] += c1*c1*s2[i];
1038 else s1[i] += c1*s2[i];
1039 }
1040 PutStats(s1);
1041 SetEntries(entries);
1042 }
1043 return kTRUE;
1044}
1045
1046////////////////////////////////////////////////////////////////////////////////
1047/// Replace contents of this histogram by the addition of h1 and h2.
1048///
1049/// `this = c1*h1 + c2*h2`
1050/// if errors are defined (see TH1::Sumw2), errors are also recalculated
1051///
1052/// Note that if h1 or h2 have Sumw2 set, Sumw2 is automatically called for this
1053/// if not already set.
1054///
1055/// Note also that adding histogram with labels is not supported, histogram will be
1056/// added merging them by bin number independently of the labels.
1057/// For adding histogram ith labels one should use TH1::Merge
1058///
1059/// SPECIAL CASE (Average/Efficiency histograms)
1060/// For histograms representing averages or efficiencies, one should compute the average
1061/// of the two histograms and not the sum. One can mark a histogram to be an average
1062/// histogram by setting its bit kIsAverage with
1063/// myhist.SetBit(TH1::kIsAverage);
1064/// Note that the two histograms must have their kIsAverage bit set
1065///
1066/// IMPORTANT NOTE: If you intend to use the errors of this histogram later
1067/// you should call Sumw2 before making this operation.
1068/// This is particularly important if you fit the histogram after TH1::Add
1069///
1070/// IMPORTANT NOTE2: You should be careful about the statistics of the
1071/// returned histogram, whose statistics may be binned or unbinned,
1072/// depending on whether c1 is negative, whether TAxis::kAxisRange is true,
1073/// and whether TH1::ResetStats has been called on either this or h1.
1074/// See TH1::GetStats.
1075///
1076/// ANOTHER SPECIAL CASE : h1 = h2 and c2 < 0
1077/// do a scaling this = c1 * h1 / (bin Volume)
1078///
1079/// The function returns kFALSE if the Add operation failed
1080
1082{
1083
1084 if (!h1 || !h2) {
1085 Error("Add","Attempt to add a non-existing histogram");
1086 return kFALSE;
1087 }
1088
1089 // delete buffer if it is there since it will become invalid
1090 if (fBuffer) BufferEmpty(1);
1091
1092 Bool_t normWidth = kFALSE;
1093 if (h1 == h2 && c2 < 0) {c2 = 0; normWidth = kTRUE;}
1094
1095 if (h1 != h2) {
1096 bool useMerge = (c1 == 1. && c2 == 1. && !this->TestBit(kIsAverage) && !h1->TestBit(kIsAverage) );
1097
1098 try {
1099 CheckConsistency(h1,h2);
1100 CheckConsistency(this,h1);
1101 useMerge = kFALSE;
1102 } catch(DifferentNumberOfBins&) {
1103 if (useMerge)
1104 Info("Add","Attempt to add histograms with different number of bins - trying to use TH1::Merge");
1105 else {
1106 Error("Add","Attempt to add histograms with different number of bins : nbins h1 = %d , nbins h2 = %d",GetNbinsX(), h1->GetNbinsX());
1107 return kFALSE;
1108 }
1109 } catch(DifferentAxisLimits&) {
1110 if (useMerge)
1111 Info("Add","Attempt to add histograms with different axis limits - trying to use TH1::Merge");
1112 else
1113 Warning("Add","Attempt to add histograms with different axis limits");
1114 } catch(DifferentBinLimits&) {
1115 if (useMerge)
1116 Info("Add","Attempt to add histograms with different bin limits - trying to use TH1::Merge");
1117 else
1118 Warning("Add","Attempt to add histograms with different bin limits");
1119 } catch(DifferentLabels&) {
1120 // in case of different labels -
1121 if (useMerge)
1122 Info("Add","Attempt to add histograms with different labels - trying to use TH1::Merge");
1123 else
1124 Info("Warning","Attempt to add histograms with different labels");
1125 }
1126
1127 if (useMerge) {
1128 TList l;
1129 // why TList takes non-const pointers ????
1130 l.Add(const_cast<TH1*>(h1));
1131 l.Add(const_cast<TH1*>(h2));
1132 Reset("ICE");
1133 auto iret = Merge(&l);
1134 return (iret >= 0);
1135 }
1136 }
1137
1138 // Create Sumw2 if h1 or h2 have Sumw2 set
1139 if (fSumw2.fN == 0 && (h1->GetSumw2N() != 0 || h2->GetSumw2N() != 0)) Sumw2();
1140
1141 // - Add statistics
1142 Double_t nEntries = TMath::Abs( c1*h1->GetEntries() + c2*h2->GetEntries() );
1143
1144 // TODO remove
1145 // statistics can be preserved only in case of positive coefficients
1146 // otherwise with negative c1 (histogram subtraction) one risks to get negative variances
1147 // also in case of scaling with the width we cannot preserve the statistics
1148 Double_t s1[kNstat] = {0};
1149 Double_t s2[kNstat] = {0};
1150 Double_t s3[kNstat];
1151
1152
1153 Bool_t resetStats = (c1*c2 < 0) || normWidth;
1154 if (!resetStats) {
1155 // need to initialize to zero s1 and s2 since
1156 // GetStats fills only used elements depending on dimension and type
1157 h1->GetStats(s1);
1158 h2->GetStats(s2);
1159 for (Int_t i=0;i<kNstat;i++) {
1160 if (i == 1) s3[i] = c1*c1*s1[i] + c2*c2*s2[i];
1161 //else s3[i] = TMath::Abs(c1)*s1[i] + TMath::Abs(c2)*s2[i];
1162 else s3[i] = c1*s1[i] + c2*s2[i];
1163 }
1164 }
1165
1166 SetMinimum();
1167 SetMaximum();
1168
1169 if (normWidth) { // DEPRECATED CASE: belongs to fitting / drawing modules
1170
1171 Int_t nbinsx = GetNbinsX() + 2; // normal bins + underflow, overflow
1172 Int_t nbinsy = GetNbinsY() + 2;
1173 Int_t nbinsz = GetNbinsZ() + 2;
1174
1175 if (fDimension < 2) nbinsy = 1;
1176 if (fDimension < 3) nbinsz = 1;
1177
1178 Int_t bin, binx, biny, binz;
1179 for (binz = 0; binz < nbinsz; ++binz) {
1180 Double_t wz = h1->GetZaxis()->GetBinWidth(binz);
1181 for (biny = 0; biny < nbinsy; ++biny) {
1182 Double_t wy = h1->GetYaxis()->GetBinWidth(biny);
1183 for (binx = 0; binx < nbinsx; ++binx) {
1184 Double_t wx = h1->GetXaxis()->GetBinWidth(binx);
1185 bin = GetBin(binx, biny, binz);
1186 Double_t w = wx*wy*wz;
1187 UpdateBinContent(bin, c1 * h1->RetrieveBinContent(bin) / w);
1188 if (fSumw2.fN) {
1189 Double_t e1 = h1->GetBinError(bin)/w;
1190 fSumw2.fArray[bin] = c1*c1*e1*e1;
1191 }
1192 }
1193 }
1194 }
1195 } else if (h1->TestBit(kIsAverage) && h2->TestBit(kIsAverage)) {
1196 for (Int_t i = 0; i < fNcells; ++i) { // loop on cells (bins including underflow / overflow)
1197 // special case where histograms have the kIsAverage bit set
1199 Double_t y2 = h2->RetrieveBinContent(i);
1201 Double_t e2sq = h2->GetBinErrorSqUnchecked(i);
1202 Double_t w1 = 1., w2 = 1.;
1203
1204 // consider all special cases when bin errors are zero
1205 // see http://root-forum.cern.ch/viewtopic.php?f=3&t=13299
1206 if (e1sq) w1 = 1./ e1sq;
1207 else if (h1->fSumw2.fN) {
1208 w1 = 1.E200; // use an arbitrary huge value
1209 if (y1 == 0 ) { // use an estimated error from the global histogram scale
1210 double sf = (s1[0] != 0) ? s1[1]/s1[0] : 1;
1211 w1 = 1./(sf*sf);
1212 }
1213 }
1214 if (e2sq) w2 = 1./ e2sq;
1215 else if (h2->fSumw2.fN) {
1216 w2 = 1.E200; // use an arbitrary huge value
1217 if (y2 == 0) { // use an estimated error from the global histogram scale
1218 double sf = (s2[0] != 0) ? s2[1]/s2[0] : 1;
1219 w2 = 1./(sf*sf);
1220 }
1221 }
1222
1223 double y = (w1*y1 + w2*y2)/(w1 + w2);
1224 UpdateBinContent(i, y);
1225 if (fSumw2.fN) {
1226 double err2 = 1./(w1 + w2);
1227 if (err2 < 1.E-200) err2 = 0; // to remove arbitrary value when e1=0 AND e2=0
1228 fSumw2.fArray[i] = err2;
1229 }
1230 }
1231 } else { // case of simple histogram addition
1232 Double_t c1sq = c1 * c1;
1233 Double_t c2sq = c2 * c2;
1234 for (Int_t i = 0; i < fNcells; ++i) { // Loop on cells (bins including underflows/overflows)
1236 if (fSumw2.fN) {
1237 fSumw2.fArray[i] = c1sq * h1->GetBinErrorSqUnchecked(i) + c2sq * h2->GetBinErrorSqUnchecked(i);
1238 }
1239 }
1240 }
1241
1242 if (resetStats) {
1243 // statistics need to be reset in case coefficient are negative
1244 ResetStats();
1245 }
1246 else {
1247 // update statistics (do here to avoid changes by SetBinContent) FIXME remove???
1248 PutStats(s3);
1249 SetEntries(nEntries);
1250 }
1251
1252 return kTRUE;
1253}
1254
1255////////////////////////////////////////////////////////////////////////////////
1256/// Increment bin content by 1.
1257
1259{
1260 AbstractMethod("AddBinContent");
1261}
1262
1263////////////////////////////////////////////////////////////////////////////////
1264/// Increment bin content by a weight w.
1265
1267{
1268 AbstractMethod("AddBinContent");
1269}
1270
1271////////////////////////////////////////////////////////////////////////////////
1272/// Sets the flag controlling the automatic add of histograms in memory
1273///
1274/// By default (fAddDirectory = kTRUE), histograms are automatically added
1275/// to the list of objects in memory.
1276/// Note that one histogram can be removed from its support directory
1277/// by calling h->SetDirectory(0) or h->SetDirectory(dir) to add it
1278/// to the list of objects in the directory dir.
1279///
1280/// NOTE that this is a static function. To call it, use;
1281/// TH1::AddDirectory
1282
1284{
1285 fgAddDirectory = add;
1286}
1287
1288////////////////////////////////////////////////////////////////////////////////
1289/// Auxiliary function to get the power of 2 next (larger) or previous (smaller)
1290/// a given x
1291///
1292/// next = kTRUE : next larger
1293/// next = kFALSE : previous smaller
1294///
1295/// Used by the autobin power of 2 algorithm
1296
1298{
1299 Int_t nn;
1300 Double_t f2 = std::frexp(x, &nn);
1301 return ((next && x > 0.) || (!next && x <= 0.)) ? std::ldexp(std::copysign(1., f2), nn)
1302 : std::ldexp(std::copysign(1., f2), --nn);
1303}
1304
1305////////////////////////////////////////////////////////////////////////////////
1306/// Auxiliary function to get the next power of 2 integer value larger then n
1307///
1308/// Used by the autobin power of 2 algorithm
1309
1311{
1312 Int_t nn;
1313 Double_t f2 = std::frexp(n, &nn);
1314 if (TMath::Abs(f2 - .5) > 0.001)
1315 return (Int_t)std::ldexp(1., nn);
1316 return n;
1317}
1318
1319////////////////////////////////////////////////////////////////////////////////
1320/// Buffer-based estimate of the histogram range using the power of 2 algorithm.
1321///
1322/// Used by the autobin power of 2 algorithm.
1323///
1324/// Works on arguments (min and max from fBuffer) and internal inputs: fXmin,
1325/// fXmax, NBinsX (from fXaxis), ...
1326/// Result save internally in fXaxis.
1327///
1328/// Overloaded by TH2 and TH3.
1329///
1330/// Return -1 if internal inputs are inconsistent, 0 otherwise.
1331
1333{
1334 // We need meaningful raw limits
1335 if (xmi >= xma)
1336 return -1;
1337
1339 Double_t xhmi = fXaxis.GetXmin();
1340 Double_t xhma = fXaxis.GetXmax();
1341
1342 // Now adjust
1343 if (TMath::Abs(xhma) > TMath::Abs(xhmi)) {
1344 // Start from the upper limit
1345 xhma = TH1::AutoP2GetPower2(xhma);
1346 xhmi = xhma - TH1::AutoP2GetPower2(xhma - xhmi);
1347 } else {
1348 // Start from the lower limit
1349 xhmi = TH1::AutoP2GetPower2(xhmi, kFALSE);
1350 xhma = xhmi + TH1::AutoP2GetPower2(xhma - xhmi);
1351 }
1352
1353 // Round the bins to the next power of 2; take into account the possible inflation
1354 // of the range
1355 Double_t rr = (xhma - xhmi) / (xma - xmi);
1356 Int_t nb = TH1::AutoP2GetBins((Int_t)(rr * GetNbinsX()));
1357
1358 // Adjust using the same bin width and offsets
1359 Double_t bw = (xhma - xhmi) / nb;
1360 // Bins to left free on each side
1361 Double_t autoside = gEnv->GetValue("Hist.Binning.Auto.Side", 0.05);
1362 Int_t nbside = (Int_t)(nb * autoside);
1363
1364 // Side up
1365 Int_t nbup = (xhma - xma) / bw;
1366 if (nbup % 2 != 0)
1367 nbup++; // Must be even
1368 if (nbup != nbside) {
1369 // Accounts also for both case: larger or smaller
1370 xhma -= bw * (nbup - nbside);
1371 nb -= (nbup - nbside);
1372 }
1373
1374 // Side low
1375 Int_t nblw = (xmi - xhmi) / bw;
1376 if (nblw % 2 != 0)
1377 nblw++; // Must be even
1378 if (nblw != nbside) {
1379 // Accounts also for both case: larger or smaller
1380 xhmi += bw * (nblw - nbside);
1381 nb -= (nblw - nbside);
1382 }
1383
1384 // Set everything and project
1385 SetBins(nb, xhmi, xhma);
1386
1387 // Done
1388 return 0;
1389}
1390
1391/// Fill histogram with all entries in the buffer.
1392///
1393/// - action = -1 histogram is reset and refilled from the buffer (called by THistPainter::Paint)
1394/// - action = 0 histogram is reset and filled from the buffer. When the histogram is filled from the
1395/// buffer the value fBuffer[0] is set to a negative number (= - number of entries)
1396/// When calling with action == 0 the histogram is NOT refilled when fBuffer[0] is < 0
1397/// While when calling with action = -1 the histogram is reset and ALWAYS refilled independently if
1398/// the histogram was filled before. This is needed when drawing the histogram
1399/// - action = 1 histogram is filled and buffer is deleted
1400/// The buffer is automatically deleted when filling the histogram and the entries is
1401/// larger than the buffer size
1402
1404{
1405 // do we need to compute the bin size?
1406 if (!fBuffer) return 0;
1407 Int_t nbentries = (Int_t)fBuffer[0];
1408
1409 // nbentries correspond to the number of entries of histogram
1410
1411 if (nbentries == 0) {
1412 // if action is 1 we delete the buffer
1413 // this will avoid infinite recursion
1414 if (action > 0) {
1415 delete [] fBuffer;
1416 fBuffer = 0;
1417 fBufferSize = 0;
1418 }
1419 return 0;
1420 }
1421 if (nbentries < 0 && action == 0) return 0; // case histogram has been already filled from the buffer
1422
1423 Double_t *buffer = fBuffer;
1424 if (nbentries < 0) {
1425 nbentries = -nbentries;
1426 // a reset might call BufferEmpty() giving an infinite recursion
1427 // Protect it by setting fBuffer = 0
1428 fBuffer=0;
1429 //do not reset the list of functions
1430 Reset("ICES");
1431 fBuffer = buffer;
1432 }
1433 if (CanExtendAllAxes() || (fXaxis.GetXmax() <= fXaxis.GetXmin())) {
1434 //find min, max of entries in buffer
1435 Double_t xmin = fBuffer[2];
1436 Double_t xmax = xmin;
1437 for (Int_t i=1;i<nbentries;i++) {
1438 Double_t x = fBuffer[2*i+2];
1439 if (x < xmin) xmin = x;
1440 if (x > xmax) xmax = x;
1441 }
1442 if (fXaxis.GetXmax() <= fXaxis.GetXmin()) {
1443 Int_t rc = -1;
1445 if ((rc = AutoP2FindLimits(xmin, xmax)) < 0)
1446 Warning("BufferEmpty",
1447 "inconsistency found by power-of-2 autobin algorithm: fallback to standard method");
1448 }
1449 if (rc < 0)
1451 } else {
1452 fBuffer = 0;
1453 Int_t keep = fBufferSize; fBufferSize = 0;
1455 if (xmax >= fXaxis.GetXmax()) ExtendAxis(xmax, &fXaxis);
1456 fBuffer = buffer;
1457 fBufferSize = keep;
1458 }
1459 }
1460
1461 // call DoFillN which will not put entries in the buffer as FillN does
1462 // set fBuffer to zero to avoid re-emptying the buffer from functions called
1463 // by DoFillN (e.g Sumw2)
1464 buffer = fBuffer; fBuffer = 0;
1465 DoFillN(nbentries,&buffer[2],&buffer[1],2);
1466 fBuffer = buffer;
1467
1468 // if action == 1 - delete the buffer
1469 if (action > 0) {
1470 delete [] fBuffer;
1471 fBuffer = 0;
1472 fBufferSize = 0;
1473 } else {
1474 // if number of entries is consistent with buffer - set it negative to avoid
1475 // refilling the histogram every time BufferEmpty(0) is called
1476 // In case it is not consistent, by setting fBuffer[0]=0 is like resetting the buffer
1477 // (it will not be used anymore the next time BufferEmpty is called)
1478 if (nbentries == (Int_t)fEntries)
1479 fBuffer[0] = -nbentries;
1480 else
1481 fBuffer[0] = 0;
1482 }
1483 return nbentries;
1484}
1485
1486////////////////////////////////////////////////////////////////////////////////
1487/// accumulate arguments in buffer. When buffer is full, empty the buffer
1488///
1489/// - `fBuffer[0]` = number of entries in buffer
1490/// - `fBuffer[1]` = w of first entry
1491/// - `fBuffer[2]` = x of first entry
1492
1494{
1495 if (!fBuffer) return -2;
1496 Int_t nbentries = (Int_t)fBuffer[0];
1497
1498
1499 if (nbentries < 0) {
1500 // reset nbentries to a positive value so next time BufferEmpty() is called
1501 // the histogram will be refilled
1502 nbentries = -nbentries;
1503 fBuffer[0] = nbentries;
1504 if (fEntries > 0) {
1505 // set fBuffer to zero to avoid calling BufferEmpty in Reset
1506 Double_t *buffer = fBuffer; fBuffer=0;
1507 Reset("ICES"); // do not reset list of functions
1508 fBuffer = buffer;
1509 }
1510 }
1511 if (2*nbentries+2 >= fBufferSize) {
1512 BufferEmpty(1);
1513 if (!fBuffer)
1514 // to avoid infinite recursion Fill->BufferFill->Fill
1515 return Fill(x,w);
1516 // this cannot happen
1517 R__ASSERT(0);
1518 }
1519 fBuffer[2*nbentries+1] = w;
1520 fBuffer[2*nbentries+2] = x;
1521 fBuffer[0] += 1;
1522 return -2;
1523}
1524
1525////////////////////////////////////////////////////////////////////////////////
1526/// Check bin limits.
1527
1528bool TH1::CheckBinLimits(const TAxis* a1, const TAxis * a2)
1529{
1530 const TArrayD * h1Array = a1->GetXbins();
1531 const TArrayD * h2Array = a2->GetXbins();
1532 Int_t fN = h1Array->fN;
1533 if ( fN != 0 ) {
1534 if ( h2Array->fN != fN ) {
1535 throw DifferentBinLimits();
1536 return false;
1537 }
1538 else {
1539 for ( int i = 0; i < fN; ++i ) {
1540 // for i==fN (nbin+1) a->GetBinWidth() returns last bin width
1541 // we do not need to exclude that case
1542 double binWidth = a1->GetBinWidth(i);
1543 if ( ! TMath::AreEqualAbs( h1Array->GetAt(i), h2Array->GetAt(i), binWidth*1E-10 ) ) {
1544 throw DifferentBinLimits();
1545 return false;
1546 }
1547 }
1548 }
1549 }
1550
1551 return true;
1552}
1553
1554////////////////////////////////////////////////////////////////////////////////
1555/// Check that axis have same labels.
1556
1557bool TH1::CheckBinLabels(const TAxis* a1, const TAxis * a2)
1558{
1559 THashList *l1 = a1->GetLabels();
1560 THashList *l2 = a2->GetLabels();
1561
1562 if (!l1 && !l2 )
1563 return true;
1564 if (!l1 || !l2 ) {
1565 throw DifferentLabels();
1566 return false;
1567 }
1568 // check now labels sizes are the same
1569 if (l1->GetSize() != l2->GetSize() ) {
1570 throw DifferentLabels();
1571 return false;
1572 }
1573 for (int i = 1; i <= a1->GetNbins(); ++i) {
1574 TString label1 = a1->GetBinLabel(i);
1575 TString label2 = a2->GetBinLabel(i);
1576 if (label1 != label2) {
1577 throw DifferentLabels();
1578 return false;
1579 }
1580 }
1581
1582 return true;
1583}
1584
1585////////////////////////////////////////////////////////////////////////////////
1586/// Check that the axis limits of the histograms are the same.
1587/// If a first and last bin is passed the axis is compared between the given range
1588
1589bool TH1::CheckAxisLimits(const TAxis *a1, const TAxis *a2 )
1590{
1591 double firstBin = a1->GetBinWidth(1);
1592 double lastBin = a1->GetBinWidth( a1->GetNbins() );
1593 if ( ! TMath::AreEqualAbs(a1->GetXmin(), a2->GetXmin(), firstBin* 1.E-10) ||
1594 ! TMath::AreEqualAbs(a1->GetXmax(), a2->GetXmax(), lastBin*1.E-10) ) {
1595 throw DifferentAxisLimits();
1596 return false;
1597 }
1598 return true;
1599}
1600
1601////////////////////////////////////////////////////////////////////////////////
1602/// Check that the axis are the same
1603
1604bool TH1::CheckEqualAxes(const TAxis *a1, const TAxis *a2 )
1605{
1606 if (a1->GetNbins() != a2->GetNbins() ) {
1607 //throw DifferentNumberOfBins();
1608 ::Info("CheckEqualAxes","Axes have different number of bins : nbin1 = %d nbin2 = %d",a1->GetNbins(),a2->GetNbins() );
1609 return false;
1610 }
1611 try {
1612 CheckAxisLimits(a1,a2);
1613 } catch (DifferentAxisLimits&) {
1614 ::Info("CheckEqualAxes","Axes have different limits");
1615 return false;
1616 }
1617 try {
1618 CheckBinLimits(a1,a2);
1619 } catch (DifferentBinLimits&) {
1620 ::Info("CheckEqualAxes","Axes have different bin limits");
1621 return false;
1622 }
1623
1624 // check labels
1625 try {
1626 CheckBinLabels(a1,a2);
1627 } catch (DifferentLabels&) {
1628 ::Info("CheckEqualAxes","Axes have different labels");
1629 return false;
1630 }
1631
1632 return true;
1633}
1634
1635////////////////////////////////////////////////////////////////////////////////
1636/// Check that two sub axis are the same.
1637/// The limits are defined by first bin and last bin
1638/// N.B. no check is done in this case for variable bins
1639
1640bool TH1::CheckConsistentSubAxes(const TAxis *a1, Int_t firstBin1, Int_t lastBin1, const TAxis * a2, Int_t firstBin2, Int_t lastBin2 )
1641{
1642 // By default is assumed that no bins are given for the second axis
1643 Int_t nbins1 = lastBin1-firstBin1 + 1;
1644 Double_t xmin1 = a1->GetBinLowEdge(firstBin1);
1645 Double_t xmax1 = a1->GetBinUpEdge(lastBin1);
1646
1647 Int_t nbins2 = a2->GetNbins();
1648 Double_t xmin2 = a2->GetXmin();
1649 Double_t xmax2 = a2->GetXmax();
1650
1651 if (firstBin2 < lastBin2) {
1652 // in this case assume no bins are given for the second axis
1653 nbins2 = lastBin1-firstBin1 + 1;
1654 xmin2 = a1->GetBinLowEdge(firstBin1);
1655 xmax2 = a1->GetBinUpEdge(lastBin1);
1656 }
1657
1658 if (nbins1 != nbins2 ) {
1659 ::Info("CheckConsistentSubAxes","Axes have different number of bins");
1660 return false;
1661 }
1662
1663 Double_t firstBin = a1->GetBinWidth(firstBin1);
1664 Double_t lastBin = a1->GetBinWidth(lastBin1);
1665 if ( ! TMath::AreEqualAbs(xmin1,xmin2,1.E-10 * firstBin) ||
1666 ! TMath::AreEqualAbs(xmax1,xmax2,1.E-10 * lastBin) ) {
1667 ::Info("CheckConsistentSubAxes","Axes have different limits");
1668 return false;
1669 }
1670
1671 return true;
1672}
1673
1674////////////////////////////////////////////////////////////////////////////////
1675/// Check histogram compatibility.
1676
1677bool TH1::CheckConsistency(const TH1* h1, const TH1* h2)
1678{
1679 if (h1 == h2) return true;
1680
1681 if (h1->GetDimension() != h2->GetDimension() ) {
1682 throw DifferentDimension();
1683 return false;
1684 }
1685 Int_t dim = h1->GetDimension();
1686
1687 // returns kTRUE if number of bins and bin limits are identical
1688 Int_t nbinsx = h1->GetNbinsX();
1689 Int_t nbinsy = h1->GetNbinsY();
1690 Int_t nbinsz = h1->GetNbinsZ();
1691
1692 // Check whether the histograms have the same number of bins.
1693 if (nbinsx != h2->GetNbinsX() ||
1694 (dim > 1 && nbinsy != h2->GetNbinsY()) ||
1695 (dim > 2 && nbinsz != h2->GetNbinsZ()) ) {
1696 throw DifferentNumberOfBins();
1697 return false;
1698 }
1699
1700 bool ret = true;
1701
1702 // check axis limits
1703 ret &= CheckAxisLimits(h1->GetXaxis(), h2->GetXaxis());
1704 if (dim > 1) ret &= CheckAxisLimits(h1->GetYaxis(), h2->GetYaxis());
1705 if (dim > 2) ret &= CheckAxisLimits(h1->GetZaxis(), h2->GetZaxis());
1706
1707 // check bin limits
1708 ret &= CheckBinLimits(h1->GetXaxis(), h2->GetXaxis());
1709 if (dim > 1) ret &= CheckBinLimits(h1->GetYaxis(), h2->GetYaxis());
1710 if (dim > 2) ret &= CheckBinLimits(h1->GetZaxis(), h2->GetZaxis());
1711
1712 // check labels if histograms are both not empty
1713 if ( !h1->IsEmpty() && !h2->IsEmpty() ) {
1714 ret &= CheckBinLabels(h1->GetXaxis(), h2->GetXaxis());
1715 if (dim > 1) ret &= CheckBinLabels(h1->GetYaxis(), h2->GetYaxis());
1716 if (dim > 2) ret &= CheckBinLabels(h1->GetZaxis(), h2->GetZaxis());
1717 }
1718
1719 return ret;
1720}
1721
1722////////////////////////////////////////////////////////////////////////////////
1723/// \f$ \chi^{2} \f$ test for comparing weighted and unweighted histograms
1724///
1725/// Function: Returns p-value. Other return values are specified by the 3rd parameter
1726///
1727/// \param[in] h2 the second histogram
1728/// \param[in] option
1729/// - "UU" = experiment experiment comparison (unweighted-unweighted)
1730/// - "UW" = experiment MC comparison (unweighted-weighted). Note that
1731/// the first histogram should be unweighted
1732/// - "WW" = MC MC comparison (weighted-weighted)
1733/// - "NORM" = to be used when one or both of the histograms is scaled
1734/// but the histogram originally was unweighted
1735/// - by default underflows and overflows are not included:
1736/// * "OF" = overflows included
1737/// * "UF" = underflows included
1738/// - "P" = print chi2, ndf, p_value, igood
1739/// - "CHI2" = returns chi2 instead of p-value
1740/// - "CHI2/NDF" = returns \f$ \chi^{2} \f$/ndf
1741/// \param[in] res not empty - computes normalized residuals and returns them in this array
1742///
1743/// The current implementation is based on the papers \f$ \chi^{2} \f$ test for comparison
1744/// of weighted and unweighted histograms" in Proceedings of PHYSTAT05 and
1745/// "Comparison weighted and unweighted histograms", arXiv:physics/0605123
1746/// by N.Gagunashvili. This function has been implemented by Daniel Haertl in August 2006.
1747///
1748/// #### Introduction:
1749///
1750/// A frequently used technique in data analysis is the comparison of
1751/// histograms. First suggested by Pearson [1] the \f$ \chi^{2} \f$ test of
1752/// homogeneity is used widely for comparing usual (unweighted) histograms.
1753/// This paper describes the implementation modified \f$ \chi^{2} \f$ tests
1754/// for comparison of weighted and unweighted histograms and two weighted
1755/// histograms [2] as well as usual Pearson's \f$ \chi^{2} \f$ test for
1756/// comparison two usual (unweighted) histograms.
1757///
1758/// #### Overview:
1759///
1760/// Comparison of two histograms expect hypotheses that two histograms
1761/// represent identical distributions. To make a decision p-value should
1762/// be calculated. The hypotheses of identity is rejected if the p-value is
1763/// lower then some significance level. Traditionally significance levels
1764/// 0.1, 0.05 and 0.01 are used. The comparison procedure should include an
1765/// analysis of the residuals which is often helpful in identifying the
1766/// bins of histograms responsible for a significant overall \f$ \chi^{2} \f$ value.
1767/// Residuals are the difference between bin contents and expected bin
1768/// contents. Most convenient for analysis are the normalized residuals. If
1769/// hypotheses of identity are valid then normalized residuals are
1770/// approximately independent and identically distributed random variables
1771/// having N(0,1) distribution. Analysis of residuals expect test of above
1772/// mentioned properties of residuals. Notice that indirectly the analysis
1773/// of residuals increase the power of \f$ \chi^{2} \f$ test.
1774///
1775/// #### Methods of comparison:
1776///
1777/// \f$ \chi^{2} \f$ test for comparison two (unweighted) histograms:
1778/// Let us consider two histograms with the same binning and the number
1779/// of bins equal to r. Let us denote the number of events in the ith bin
1780/// in the first histogram as ni and as mi in the second one. The total
1781/// number of events in the first histogram is equal to:
1782/// \f[
1783/// N = \sum_{i=1}^{r} n_{i}
1784/// \f]
1785/// and
1786/// \f[
1787/// M = \sum_{i=1}^{r} m_{i}
1788/// \f]
1789/// in the second histogram. The hypothesis of identity (homogeneity) [3]
1790/// is that the two histograms represent random values with identical
1791/// distributions. It is equivalent that there exist r constants p1,...,pr,
1792/// such that
1793/// \f[
1794///\sum_{i=1}^{r} p_{i}=1
1795/// \f]
1796/// and the probability of belonging to the ith bin for some measured value
1797/// in both experiments is equal to pi. The number of events in the ith
1798/// bin is a random variable with a distribution approximated by a Poisson
1799/// probability distribution
1800/// \f[
1801///\frac{e^{-Np_{i}}(Np_{i})^{n_{i}}}{n_{i}!}
1802/// \f]
1803///for the first histogram and with distribution
1804/// \f[
1805///\frac{e^{-Mp_{i}}(Mp_{i})^{m_{i}}}{m_{i}!}
1806/// \f]
1807/// for the second histogram. If the hypothesis of homogeneity is valid,
1808/// then the maximum likelihood estimator of pi, i=1,...,r, is
1809/// \f[
1810///\hat{p}_{i}= \frac{n_{i}+m_{i}}{N+M}
1811/// \f]
1812/// and then
1813/// \f[
1814/// X^{2} = \sum_{i=1}^{r}\frac{(n_{i}-N\hat{p}_{i})^{2}}{N\hat{p}_{i}} + \sum_{i=1}^{r}\frac{(m_{i}-M\hat{p}_{i})^{2}}{M\hat{p}_{i}} =\frac{1}{MN} \sum_{i=1}^{r}\frac{(Mn_{i}-Nm_{i})^{2}}{n_{i}+m_{i}}
1815/// \f]
1816/// has approximately a \f$ \chi^{2}_{(r-1)} \f$ distribution [3].
1817/// The comparison procedure can include an analysis of the residuals which
1818/// is often helpful in identifying the bins of histograms responsible for
1819/// a significant overall \f$ \chi^{2} \f$ value. Most convenient for
1820/// analysis are the adjusted (normalized) residuals [4]
1821/// \f[
1822/// r_{i} = \frac{n_{i}-N\hat{p}_{i}}{\sqrt{N\hat{p}_{i}}\sqrt{(1-N/(N+M))(1-(n_{i}+m_{i})/(N+M))}}
1823/// \f]
1824/// If hypotheses of homogeneity are valid then residuals ri are
1825/// approximately independent and identically distributed random variables
1826/// having N(0,1) distribution. The application of the \f$ \chi^{2} \f$ test has
1827/// restrictions related to the value of the expected frequencies Npi,
1828/// Mpi, i=1,...,r. A conservative rule formulated in [5] is that all the
1829/// expectations must be 1 or greater for both histograms. In practical
1830/// cases when expected frequencies are not known the estimated expected
1831/// frequencies \f$ M\hat{p}_{i}, N\hat{p}_{i}, i=1,...,r \f$ can be used.
1832///
1833/// #### Unweighted and weighted histograms comparison:
1834///
1835/// A simple modification of the ideas described above can be used for the
1836/// comparison of the usual (unweighted) and weighted histograms. Let us
1837/// denote the number of events in the ith bin in the unweighted
1838/// histogram as ni and the common weight of events in the ith bin of the
1839/// weighted histogram as wi. The total number of events in the
1840/// unweighted histogram is equal to
1841///\f[
1842/// N = \sum_{i=1}^{r} n_{i}
1843///\f]
1844/// and the total weight of events in the weighted histogram is equal to
1845///\f[
1846/// W = \sum_{i=1}^{r} w_{i}
1847///\f]
1848/// Let us formulate the hypothesis of identity of an unweighted histogram
1849/// to a weighted histogram so that there exist r constants p1,...,pr, such
1850/// that
1851///\f[
1852/// \sum_{i=1}^{r} p_{i} = 1
1853///\f]
1854/// for the unweighted histogram. The weight wi is a random variable with a
1855/// distribution approximated by the normal probability distribution
1856/// \f$ N(Wp_{i},\sigma_{i}^{2}) \f$ where \f$ \sigma_{i}^{2} \f$ is the variance of the weight wi.
1857/// If we replace the variance \f$ \sigma_{i}^{2} \f$
1858/// with estimate \f$ s_{i}^{2} \f$ (sum of squares of weights of
1859/// events in the ith bin) and the hypothesis of identity is valid, then the
1860/// maximum likelihood estimator of pi,i=1,...,r, is
1861///\f[
1862/// \hat{p}_{i} = \frac{Ww_{i}-Ns_{i}^{2}+\sqrt{(Ww_{i}-Ns_{i}^{2})^{2}+4W^{2}s_{i}^{2}n_{i}}}{2W^{2}}
1863///\f]
1864/// We may then use the test statistic
1865///\f[
1866/// X^{2} = \sum_{i=1}^{r} \frac{(n_{i}-N\hat{p}_{i})^{2}}{N\hat{p}_{i}} + \sum_{i=1}^{r} \frac{(w_{i}-W\hat{p}_{i})^{2}}{s_{i}^{2}}
1867///\f]
1868/// and it has approximately a \f$ \sigma^{2}_{(r-1)} \f$ distribution [2]. This test, as well
1869/// as the original one [3], has a restriction on the expected frequencies. The
1870/// expected frequencies recommended for the weighted histogram is more than 25.
1871/// The value of the minimal expected frequency can be decreased down to 10 for
1872/// the case when the weights of the events are close to constant. In the case
1873/// of a weighted histogram if the number of events is unknown, then we can
1874/// apply this recommendation for the equivalent number of events as
1875///\f[
1876/// n_{i}^{equiv} = \frac{ w_{i}^{2} }{ s_{i}^{2} }
1877///\f]
1878/// The minimal expected frequency for an unweighted histogram must be 1. Notice
1879/// that any usual (unweighted) histogram can be considered as a weighted
1880/// histogram with events that have constant weights equal to 1.
1881/// The variance \f$ z_{i}^{2} \f$ of the difference between the weight wi
1882/// and the estimated expectation value of the weight is approximately equal to:
1883///\f[
1884/// z_{i}^{2} = Var(w_{i}-W\hat{p}_{i}) = N\hat{p}_{i}(1-N\hat{p}_{i})\left(\frac{Ws_{i}^{2}}{\sqrt{(Ns_{i}^{2}-w_{i}W)^{2}+4W^{2}s_{i}^{2}n_{i}}}\right)^{2}+\frac{s_{i}^{2}}{4}\left(1+\frac{Ns_{i}^{2}-w_{i}W}{\sqrt{(Ns_{i}^{2}-w_{i}W)^{2}+4W^{2}s_{i}^{2}n_{i}}}\right)^{2}
1885///\f]
1886/// The residuals
1887///\f[
1888/// r_{i} = \frac{w_{i}-W\hat{p}_{i}}{z_{i}}
1889///\f]
1890/// have approximately a normal distribution with mean equal to 0 and standard
1891/// deviation equal to 1.
1892///
1893/// #### Two weighted histograms comparison:
1894///
1895/// Let us denote the common weight of events of the ith bin in the first
1896/// histogram as w1i and as w2i in the second one. The total weight of events
1897/// in the first histogram is equal to
1898///\f[
1899/// W_{1} = \sum_{i=1}^{r} w_{1i}
1900///\f]
1901/// and
1902///\f[
1903/// W_{2} = \sum_{i=1}^{r} w_{2i}
1904///\f]
1905/// in the second histogram. Let us formulate the hypothesis of identity of
1906/// weighted histograms so that there exist r constants p1,...,pr, such that
1907///\f[
1908/// \sum_{i=1}^{r} p_{i} = 1
1909///\f]
1910/// and also expectation value of weight w1i equal to W1pi and expectation value
1911/// of weight w2i equal to W2pi. Weights in both the histograms are random
1912/// variables with distributions which can be approximated by a normal
1913/// probability distribution \f$ N(W_{1}p_{i},\sigma_{1i}^{2}) \f$ for the first histogram
1914/// and by a distribution \f$ N(W_{2}p_{i},\sigma_{2i}^{2}) \f$ for the second.
1915/// Here \f$ \sigma_{1i}^{2} \f$ and \f$ \sigma_{2i}^{2} \f$ are the variances
1916/// of w1i and w2i with estimators \f$ s_{1i}^{2} \f$ and \f$ s_{2i}^{2} \f$ respectively.
1917/// If the hypothesis of identity is valid, then the maximum likelihood and
1918/// Least Square Method estimator of pi,i=1,...,r, is
1919///\f[
1920/// \hat{p}_{i} = \frac{w_{1i}W_{1}/s_{1i}^{2}+w_{2i}W_{2} /s_{2i}^{2}}{W_{1}^{2}/s_{1i}^{2}+W_{2}^{2}/s_{2i}^{2}}
1921///\f]
1922/// We may then use the test statistic
1923///\f[
1924/// X^{2} = \sum_{i=1}^{r} \frac{(w_{1i}-W_{1}\hat{p}_{i})^{2}}{s_{1i}^{2}} + \sum_{i=1}^{r} \frac{(w_{2i}-W_{2}\hat{p}_{i})^{2}}{s_{2i}^{2}} = \sum_{i=1}^{r} \frac{(W_{1}w_{2i}-W_{2}w_{1i})^{2}}{W_{1}^{2}s_{2i}^{2}+W_{2}^{2}s_{1i}^{2}}
1925///\f]
1926/// and it has approximately a \f$ \chi^{2}_{(r-1)} \f$ distribution [2].
1927/// The normalized or studentised residuals [6]
1928///\f[
1929/// r_{i} = \frac{w_{1i}-W_{1}\hat{p}_{i}}{s_{1i}\sqrt{1 - \frac{1}{(1+W_{2}^{2}s_{1i}^{2}/W_{1}^{2}s_{2i}^{2})}}}
1930///\f]
1931/// have approximately a normal distribution with mean equal to 0 and standard
1932/// deviation 1. A recommended minimal expected frequency is equal to 10 for
1933/// the proposed test.
1934///
1935/// #### Numerical examples:
1936///
1937/// The method described herein is now illustrated with an example.
1938/// We take a distribution
1939///\f[
1940/// \phi(x) = \frac{2}{(x-10)^{2}+1} + \frac{1}{(x-14)^{2}+1} (1)
1941///\f]
1942/// defined on the interval [4,16]. Events distributed according to the formula
1943/// (1) are simulated to create the unweighted histogram. Uniformly distributed
1944/// events are simulated for the weighted histogram with weights calculated by
1945/// formula (1). Each histogram has the same number of bins: 20. Fig.1 shows
1946/// the result of comparison of the unweighted histogram with 200 events
1947/// (minimal expected frequency equal to one) and the weighted histogram with
1948/// 500 events (minimal expected frequency equal to 25)
1949/// Begin_Macro
1950/// ../../../tutorials/math/chi2test.C
1951/// End_Macro
1952/// Fig 1. An example of comparison of the unweighted histogram with 200 events
1953/// and the weighted histogram with 500 events:
1954/// 1. unweighted histogram;
1955/// 2. weighted histogram;
1956/// 3. normalized residuals plot;
1957/// 4. normal Q-Q plot of residuals.
1958///
1959/// The value of the test statistic \f$ \chi^{2} \f$ is equal to
1960/// 21.09 with p-value equal to 0.33, therefore the hypothesis of identity of
1961/// the two histograms can be accepted for 0.05 significant level. The behavior
1962/// of the normalized residuals plot (see Fig. 1c) and the normal Q-Q plot
1963/// (see Fig. 1d) of residuals are regular and we cannot identify the outliers
1964/// or bins with a big influence on \f$ \chi^{2} \f$.
1965///
1966/// The second example presents the same two histograms but 17 events was added
1967/// to content of bin number 15 in unweighted histogram. Fig.2 shows the result
1968/// of comparison of the unweighted histogram with 217 events (minimal expected
1969/// frequency equal to one) and the weighted histogram with 500 events (minimal
1970/// expected frequency equal to 25)
1971/// Begin_Macro
1972/// ../../../tutorials/math/chi2test.C(17)
1973/// End_Macro
1974/// Fig 2. An example of comparison of the unweighted histogram with 217 events
1975/// and the weighted histogram with 500 events:
1976/// 1. unweighted histogram;
1977/// 2. weighted histogram;
1978/// 3. normalized residuals plot;
1979/// 4. normal Q-Q plot of residuals.
1980///
1981/// The value of the test statistic \f$ \chi^{2} \f$ is equal to
1982/// 32.33 with p-value equal to 0.029, therefore the hypothesis of identity of
1983/// the two histograms is rejected for 0.05 significant level. The behavior of
1984/// the normalized residuals plot (see Fig. 2c) and the normal Q-Q plot (see
1985/// Fig. 2d) of residuals are not regular and we can identify the outlier or
1986/// bin with a big influence on \f$ \chi^{2} \f$.
1987///
1988/// #### References:
1989///
1990/// - [1] Pearson, K., 1904. On the Theory of Contingency and Its Relation to
1991/// Association and Normal Correlation. Drapers' Co. Memoirs, Biometric
1992/// Series No. 1, London.
1993/// - [2] Gagunashvili, N., 2006. \f$ \sigma^{2} \f$ test for comparison
1994/// of weighted and unweighted histograms. Statistical Problems in Particle
1995/// Physics, Astrophysics and Cosmology, Proceedings of PHYSTAT05,
1996/// Oxford, UK, 12-15 September 2005, Imperial College Press, London, 43-44.
1997/// Gagunashvili,N., Comparison of weighted and unweighted histograms,
1998/// arXiv:physics/0605123, 2006.
1999/// - [3] Cramer, H., 1946. Mathematical methods of statistics.
2000/// Princeton University Press, Princeton.
2001/// - [4] Haberman, S.J., 1973. The analysis of residuals in cross-classified tables.
2002/// Biometrics 29, 205-220.
2003/// - [5] Lewontin, R.C. and Felsenstein, J., 1965. The robustness of homogeneity
2004/// test in 2xN tables. Biometrics 21, 19-33.
2005/// - [6] Seber, G.A.F., Lee, A.J., 2003, Linear Regression Analysis.
2006/// John Wiley & Sons Inc., New York.
2007
2008Double_t TH1::Chi2Test(const TH1* h2, Option_t *option, Double_t *res) const
2009{
2010 Double_t chi2 = 0;
2011 Int_t ndf = 0, igood = 0;
2012
2013 TString opt = option;
2014 opt.ToUpper();
2015
2016 Double_t prob = Chi2TestX(h2,chi2,ndf,igood,option,res);
2017
2018 if(opt.Contains("P")) {
2019 printf("Chi2 = %f, Prob = %g, NDF = %d, igood = %d\n", chi2,prob,ndf,igood);
2020 }
2021 if(opt.Contains("CHI2/NDF")) {
2022 if (ndf == 0) return 0;
2023 return chi2/ndf;
2024 }
2025 if(opt.Contains("CHI2")) {
2026 return chi2;
2027 }
2028
2029 return prob;
2030}
2031
2032////////////////////////////////////////////////////////////////////////////////
2033/// The computation routine of the Chisquare test. For the method description,
2034/// see Chi2Test() function.
2035///
2036/// \return p-value
2037/// \param[in] h2 the second histogram
2038/// \param[in] option
2039/// - "UU" = experiment experiment comparison (unweighted-unweighted)
2040/// - "UW" = experiment MC comparison (unweighted-weighted). Note that the first
2041/// histogram should be unweighted
2042/// - "WW" = MC MC comparison (weighted-weighted)
2043/// - "NORM" = if one or both histograms is scaled
2044/// - "OF" = overflows included
2045/// - "UF" = underflows included
2046/// by default underflows and overflows are not included
2047/// \param[out] igood test output
2048/// - igood=0 - no problems
2049/// - For unweighted unweighted comparison
2050/// - igood=1'There is a bin in the 1st histogram with less than 1 event'
2051/// - igood=2'There is a bin in the 2nd histogram with less than 1 event'
2052/// - igood=3'when the conditions for igood=1 and igood=2 are satisfied'
2053/// - For unweighted weighted comparison
2054/// - igood=1'There is a bin in the 1st histogram with less then 1 event'
2055/// - igood=2'There is a bin in the 2nd histogram with less then 10 effective number of events'
2056/// - igood=3'when the conditions for igood=1 and igood=2 are satisfied'
2057/// - For weighted weighted comparison
2058/// - igood=1'There is a bin in the 1st histogram with less then 10 effective
2059/// number of events'
2060/// - igood=2'There is a bin in the 2nd histogram with less then 10 effective
2061/// number of events'
2062/// - igood=3'when the conditions for igood=1 and igood=2 are satisfied'
2063/// \param[out] chi2 chisquare of the test
2064/// \param[out] ndf number of degrees of freedom (important, when both histograms have the same empty bins)
2065/// \param[out] res normalized residuals for further analysis
2066
2067Double_t TH1::Chi2TestX(const TH1* h2, Double_t &chi2, Int_t &ndf, Int_t &igood, Option_t *option, Double_t *res) const
2068{
2069
2070 Int_t i_start, i_end;
2071 Int_t j_start, j_end;
2072 Int_t k_start, k_end;
2073
2074 Double_t sum1 = 0.0, sumw1 = 0.0;
2075 Double_t sum2 = 0.0, sumw2 = 0.0;
2076
2077 chi2 = 0.0;
2078 ndf = 0;
2079
2080 TString opt = option;
2081 opt.ToUpper();
2082
2083 if (fBuffer) const_cast<TH1*>(this)->BufferEmpty();
2084
2085 const TAxis *xaxis1 = GetXaxis();
2086 const TAxis *xaxis2 = h2->GetXaxis();
2087 const TAxis *yaxis1 = GetYaxis();
2088 const TAxis *yaxis2 = h2->GetYaxis();
2089 const TAxis *zaxis1 = GetZaxis();
2090 const TAxis *zaxis2 = h2->GetZaxis();
2091
2092 Int_t nbinx1 = xaxis1->GetNbins();
2093 Int_t nbinx2 = xaxis2->GetNbins();
2094 Int_t nbiny1 = yaxis1->GetNbins();
2095 Int_t nbiny2 = yaxis2->GetNbins();
2096 Int_t nbinz1 = zaxis1->GetNbins();
2097 Int_t nbinz2 = zaxis2->GetNbins();
2098
2099 //check dimensions
2100 if (this->GetDimension() != h2->GetDimension() ){
2101 Error("Chi2TestX","Histograms have different dimensions.");
2102 return 0.0;
2103 }
2104
2105 //check number of channels
2106 if (nbinx1 != nbinx2) {
2107 Error("Chi2TestX","different number of x channels");
2108 }
2109 if (nbiny1 != nbiny2) {
2110 Error("Chi2TestX","different number of y channels");
2111 }
2112 if (nbinz1 != nbinz2) {
2113 Error("Chi2TestX","different number of z channels");
2114 }
2115
2116 //check for ranges
2117 i_start = j_start = k_start = 1;
2118 i_end = nbinx1;
2119 j_end = nbiny1;
2120 k_end = nbinz1;
2121
2122 if (xaxis1->TestBit(TAxis::kAxisRange)) {
2123 i_start = xaxis1->GetFirst();
2124 i_end = xaxis1->GetLast();
2125 }
2126 if (yaxis1->TestBit(TAxis::kAxisRange)) {
2127 j_start = yaxis1->GetFirst();
2128 j_end = yaxis1->GetLast();
2129 }
2130 if (zaxis1->TestBit(TAxis::kAxisRange)) {
2131 k_start = zaxis1->GetFirst();
2132 k_end = zaxis1->GetLast();
2133 }
2134
2135
2136 if (opt.Contains("OF")) {
2137 if (GetDimension() == 3) k_end = ++nbinz1;
2138 if (GetDimension() >= 2) j_end = ++nbiny1;
2139 if (GetDimension() >= 1) i_end = ++nbinx1;
2140 }
2141
2142 if (opt.Contains("UF")) {
2143 if (GetDimension() == 3) k_start = 0;
2144 if (GetDimension() >= 2) j_start = 0;
2145 if (GetDimension() >= 1) i_start = 0;
2146 }
2147
2148 ndf = (i_end - i_start + 1) * (j_end - j_start + 1) * (k_end - k_start + 1) - 1;
2149
2150 Bool_t comparisonUU = opt.Contains("UU");
2151 Bool_t comparisonUW = opt.Contains("UW");
2152 Bool_t comparisonWW = opt.Contains("WW");
2153 Bool_t scaledHistogram = opt.Contains("NORM");
2154
2155 if (scaledHistogram && !comparisonUU) {
2156 Info("Chi2TestX", "NORM option should be used together with UU option. It is ignored");
2157 }
2158
2159 // look at histo global bin content and effective entries
2160 Stat_t s[kNstat];
2161 GetStats(s);// s[1] sum of squares of weights, s[0] sum of weights
2162 Double_t sumBinContent1 = s[0];
2163 Double_t effEntries1 = (s[1] ? s[0] * s[0] / s[1] : 0.0);
2164
2165 h2->GetStats(s);// s[1] sum of squares of weights, s[0] sum of weights
2166 Double_t sumBinContent2 = s[0];
2167 Double_t effEntries2 = (s[1] ? s[0] * s[0] / s[1] : 0.0);
2168
2169 if (!comparisonUU && !comparisonUW && !comparisonWW ) {
2170 // deduce automatically from type of histogram
2171 if (TMath::Abs(sumBinContent1 - effEntries1) < 1) {
2172 if ( TMath::Abs(sumBinContent2 - effEntries2) < 1) comparisonUU = true;
2173 else comparisonUW = true;
2174 }
2175 else comparisonWW = true;
2176 }
2177 // check unweighted histogram
2178 if (comparisonUW) {
2179 if (TMath::Abs(sumBinContent1 - effEntries1) >= 1) {
2180 Warning("Chi2TestX","First histogram is not unweighted and option UW has been requested");
2181 }
2182 }
2183 if ( (!scaledHistogram && comparisonUU) ) {
2184 if ( ( TMath::Abs(sumBinContent1 - effEntries1) >= 1) || (TMath::Abs(sumBinContent2 - effEntries2) >= 1) ) {
2185 Warning("Chi2TestX","Both histograms are not unweighted and option UU has been requested");
2186 }
2187 }
2188
2189
2190 //get number of events in histogram
2191 if (comparisonUU && scaledHistogram) {
2192 for (Int_t i = i_start; i <= i_end; ++i) {
2193 for (Int_t j = j_start; j <= j_end; ++j) {
2194 for (Int_t k = k_start; k <= k_end; ++k) {
2195
2196 Int_t bin = GetBin(i, j, k);
2197
2198 Double_t cnt1 = RetrieveBinContent(bin);
2199 Double_t cnt2 = h2->RetrieveBinContent(bin);
2200 Double_t e1sq = GetBinErrorSqUnchecked(bin);
2201 Double_t e2sq = h2->GetBinErrorSqUnchecked(bin);
2202
2203 if (e1sq > 0.0) cnt1 = TMath::Floor(cnt1 * cnt1 / e1sq + 0.5); // avoid rounding errors
2204 else cnt1 = 0.0;
2205
2206 if (e2sq > 0.0) cnt2 = TMath::Floor(cnt2 * cnt2 / e2sq + 0.5); // avoid rounding errors
2207 else cnt2 = 0.0;
2208
2209 // sum contents
2210 sum1 += cnt1;
2211 sum2 += cnt2;
2212 sumw1 += e1sq;
2213 sumw2 += e2sq;
2214 }
2215 }
2216 }
2217 if (sumw1 <= 0.0 || sumw2 <= 0.0) {
2218 Error("Chi2TestX", "Cannot use option NORM when one histogram has all zero errors");
2219 return 0.0;
2220 }
2221
2222 } else {
2223 for (Int_t i = i_start; i <= i_end; ++i) {
2224 for (Int_t j = j_start; j <= j_end; ++j) {
2225 for (Int_t k = k_start; k <= k_end; ++k) {
2226
2227 Int_t bin = GetBin(i, j, k);
2228
2229 sum1 += RetrieveBinContent(bin);
2230 sum2 += h2->RetrieveBinContent(bin);
2231
2232 if ( comparisonWW ) sumw1 += GetBinErrorSqUnchecked(bin);
2233 if ( comparisonUW || comparisonWW ) sumw2 += h2->GetBinErrorSqUnchecked(bin);
2234 }
2235 }
2236 }
2237 }
2238 //checks that the histograms are not empty
2239 if (sum1 == 0.0 || sum2 == 0.0) {
2240 Error("Chi2TestX","one histogram is empty");
2241 return 0.0;
2242 }
2243
2244 if ( comparisonWW && ( sumw1 <= 0.0 && sumw2 <= 0.0 ) ){
2245 Error("Chi2TestX","Hist1 and Hist2 have both all zero errors\n");
2246 return 0.0;
2247 }
2248
2249 //THE TEST
2250 Int_t m = 0, n = 0;
2251
2252 //Experiment - experiment comparison
2253 if (comparisonUU) {
2254 Double_t sum = sum1 + sum2;
2255 for (Int_t i = i_start; i <= i_end; ++i) {
2256 for (Int_t j = j_start; j <= j_end; ++j) {
2257 for (Int_t k = k_start; k <= k_end; ++k) {
2258
2259 Int_t bin = GetBin(i, j, k);
2260
2261 Double_t cnt1 = RetrieveBinContent(bin);
2262 Double_t cnt2 = h2->RetrieveBinContent(bin);
2263
2264 if (scaledHistogram) {
2265 // scale bin value to effective bin entries
2266 Double_t e1sq = GetBinErrorSqUnchecked(bin);
2267 Double_t e2sq = h2->GetBinErrorSqUnchecked(bin);
2268
2269 if (e1sq > 0) cnt1 = TMath::Floor(cnt1 * cnt1 / e1sq + 0.5); // avoid rounding errors
2270 else cnt1 = 0;
2271
2272 if (e2sq > 0) cnt2 = TMath::Floor(cnt2 * cnt2 / e2sq + 0.5); // avoid rounding errors
2273 else cnt2 = 0;
2274 }
2275
2276 if (Int_t(cnt1) == 0 && Int_t(cnt2) == 0) --ndf; // no data means one degree of freedom less
2277 else {
2278
2279 Double_t cntsum = cnt1 + cnt2;
2280 Double_t nexp1 = cntsum * sum1 / sum;
2281 //Double_t nexp2 = binsum*sum2/sum;
2282
2283 if (res) res[i - i_start] = (cnt1 - nexp1) / TMath::Sqrt(nexp1);
2284
2285 if (cnt1 < 1) ++m;
2286 if (cnt2 < 1) ++n;
2287
2288 //Habermann correction for residuals
2289 Double_t correc = (1. - sum1 / sum) * (1. - cntsum / sum);
2290 if (res) res[i - i_start] /= TMath::Sqrt(correc);
2291
2292 Double_t delta = sum2 * cnt1 - sum1 * cnt2;
2293 chi2 += delta * delta / cntsum;
2294 }
2295 }
2296 }
2297 }
2298 chi2 /= sum1 * sum2;
2299
2300 // flag error only when of the two histogram is zero
2301 if (m) {
2302 igood += 1;
2303 Info("Chi2TestX","There is a bin in h1 with less than 1 event.\n");
2304 }
2305 if (n) {
2306 igood += 2;
2307 Info("Chi2TestX","There is a bin in h2 with less than 1 event.\n");
2308 }
2309
2310 Double_t prob = TMath::Prob(chi2,ndf);
2311 return prob;
2312
2313 }
2314
2315 // unweighted - weighted comparison
2316 // case of error = 0 and content not zero is treated without problems by excluding second chi2 sum
2317 // and can be considered as a data-theory comparison
2318 if ( comparisonUW ) {
2319 for (Int_t i = i_start; i <= i_end; ++i) {
2320 for (Int_t j = j_start; j <= j_end; ++j) {
2321 for (Int_t k = k_start; k <= k_end; ++k) {
2322
2323 Int_t bin = GetBin(i, j, k);
2324
2325 Double_t cnt1 = RetrieveBinContent(bin);
2326 Double_t cnt2 = h2->RetrieveBinContent(bin);
2327 Double_t e2sq = h2->GetBinErrorSqUnchecked(bin);
2328
2329 // case both histogram have zero bin contents
2330 if (cnt1 * cnt1 == 0 && cnt2 * cnt2 == 0) {
2331 --ndf; //no data means one degree of freedom less
2332 continue;
2333 }
2334
2335 // case weighted histogram has zero bin content and error
2336 if (cnt2 * cnt2 == 0 && e2sq == 0) {
2337 if (sumw2 > 0) {
2338 // use as approximated error as 1 scaled by a scaling ratio
2339 // estimated from the total sum weight and sum weight squared
2340 e2sq = sumw2 / sum2;
2341 }
2342 else {
2343 // return error because infinite discrepancy here:
2344 // bin1 != 0 and bin2 =0 in a histogram with all errors zero
2345 Error("Chi2TestX","Hist2 has in bin (%d,%d,%d) zero content and zero errors\n", i, j, k);
2346 chi2 = 0; return 0;
2347 }
2348 }
2349
2350 if (cnt1 < 1) m++;
2351 if (e2sq > 0 && cnt2 * cnt2 / e2sq < 10) n++;
2352
2353 Double_t var1 = sum2 * cnt2 - sum1 * e2sq;
2354 Double_t var2 = var1 * var1 + 4. * sum2 * sum2 * cnt1 * e2sq;
2355
2356 // if cnt1 is zero and cnt2 = 1 and sum1 = sum2 var1 = 0 && var2 == 0
2357 // approximate by incrementing cnt1
2358 // LM (this need to be fixed for numerical errors)
2359 while (var1 * var1 + cnt1 == 0 || var1 + var2 == 0) {
2360 sum1++;
2361 cnt1++;
2362 var1 = sum2 * cnt2 - sum1 * e2sq;
2363 var2 = var1 * var1 + 4. * sum2 * sum2 * cnt1 * e2sq;
2364 }
2365 var2 = TMath::Sqrt(var2);
2366
2367 while (var1 + var2 == 0) {
2368 sum1++;
2369 cnt1++;
2370 var1 = sum2 * cnt2 - sum1 * e2sq;
2371 var2 = var1 * var1 + 4. * sum2 * sum2 * cnt1 * e2sq;
2372 while (var1 * var1 + cnt1 == 0 || var1 + var2 == 0) {
2373 sum1++;
2374 cnt1++;
2375 var1 = sum2 * cnt2 - sum1 * e2sq;
2376 var2 = var1 * var1 + 4. * sum2 * sum2 * cnt1 * e2sq;
2377 }
2378 var2 = TMath::Sqrt(var2);
2379 }
2380
2381 Double_t probb = (var1 + var2) / (2. * sum2 * sum2);
2382
2383 Double_t nexp1 = probb * sum1;
2384 Double_t nexp2 = probb * sum2;
2385
2386 Double_t delta1 = cnt1 - nexp1;
2387 Double_t delta2 = cnt2 - nexp2;
2388
2389 chi2 += delta1 * delta1 / nexp1;
2390
2391 if (e2sq > 0) {
2392 chi2 += delta2 * delta2 / e2sq;
2393 }
2394
2395 if (res) {
2396 if (e2sq > 0) {
2397 Double_t temp1 = sum2 * e2sq / var2;
2398 Double_t temp2 = 1.0 + (sum1 * e2sq - sum2 * cnt2) / var2;
2399 temp2 = temp1 * temp1 * sum1 * probb * (1.0 - probb) + temp2 * temp2 * e2sq / 4.0;
2400 // invert sign here
2401 res[i - i_start] = - delta2 / TMath::Sqrt(temp2);
2402 }
2403 else
2404 res[i - i_start] = delta1 / TMath::Sqrt(nexp1);
2405 }
2406 }
2407 }
2408 }
2409
2410 if (m) {
2411 igood += 1;
2412 Info("Chi2TestX","There is a bin in h1 with less than 1 event.\n");
2413 }
2414 if (n) {
2415 igood += 2;
2416 Info("Chi2TestX","There is a bin in h2 with less than 10 effective events.\n");
2417 }
2418
2419 Double_t prob = TMath::Prob(chi2, ndf);
2420
2421 return prob;
2422 }
2423
2424 // weighted - weighted comparison
2425 if (comparisonWW) {
2426 for (Int_t i = i_start; i <= i_end; ++i) {
2427 for (Int_t j = j_start; j <= j_end; ++j) {
2428 for (Int_t k = k_start; k <= k_end; ++k) {
2429
2430 Int_t bin = GetBin(i, j, k);
2431 Double_t cnt1 = RetrieveBinContent(bin);
2432 Double_t cnt2 = h2->RetrieveBinContent(bin);
2433 Double_t e1sq = GetBinErrorSqUnchecked(bin);
2434 Double_t e2sq = h2->GetBinErrorSqUnchecked(bin);
2435
2436 // case both histogram have zero bin contents
2437 // (use square of content to avoid numerical errors)
2438 if (cnt1 * cnt1 == 0 && cnt2 * cnt2 == 0) {
2439 --ndf; //no data means one degree of freedom less
2440 continue;
2441 }
2442
2443 if (e1sq == 0 && e2sq == 0) {
2444 // cannot treat case of booth histogram have zero zero errors
2445 Error("Chi2TestX","h1 and h2 both have bin %d,%d,%d with all zero errors\n", i,j,k);
2446 chi2 = 0; return 0;
2447 }
2448
2449 Double_t sigma = sum1 * sum1 * e2sq + sum2 * sum2 * e1sq;
2450 Double_t delta = sum2 * cnt1 - sum1 * cnt2;
2451 chi2 += delta * delta / sigma;
2452
2453 if (res) {
2454 Double_t temp = cnt1 * sum1 * e2sq + cnt2 * sum2 * e1sq;
2455 Double_t probb = temp / sigma;
2456 Double_t z = 0;
2457 if (e1sq > e2sq) {
2458 Double_t d1 = cnt1 - sum1 * probb;
2459 Double_t s1 = e1sq * ( 1. - e2sq * sum1 * sum1 / sigma );
2460 z = d1 / TMath::Sqrt(s1);
2461 }
2462 else {
2463 Double_t d2 = cnt2 - sum2 * probb;
2464 Double_t s2 = e2sq * ( 1. - e1sq * sum2 * sum2 / sigma );
2465 z = -d2 / TMath::Sqrt(s2);
2466 }
2467 res[i - i_start] = z;
2468 }
2469
2470 if (e1sq > 0 && cnt1 * cnt1 / e1sq < 10) m++;
2471 if (e2sq > 0 && cnt2 * cnt2 / e2sq < 10) n++;
2472 }
2473 }
2474 }
2475 if (m) {
2476 igood += 1;
2477 Info("Chi2TestX","There is a bin in h1 with less than 10 effective events.\n");
2478 }
2479 if (n) {
2480 igood += 2;
2481 Info("Chi2TestX","There is a bin in h2 with less than 10 effective events.\n");
2482 }
2483 Double_t prob = TMath::Prob(chi2, ndf);
2484 return prob;
2485 }
2486 return 0;
2487}
2488////////////////////////////////////////////////////////////////////////////////
2489/// Compute and return the chisquare of this histogram with respect to a function
2490/// The chisquare is computed by weighting each histogram point by the bin error
2491/// By default the full range of the histogram is used.
2492/// Use option "R" for restricting the chisquare calculation to the given range of the function
2493/// Use option "L" for using the chisquare based on the poisson likelihood (Baker-Cousins Chisquare)
2494
2495Double_t TH1::Chisquare(TF1 * func, Option_t *option) const
2496{
2497 if (!func) {
2498 Error("Chisquare","Function pointer is Null - return -1");
2499 return -1;
2500 }
2501
2502 TString opt(option); opt.ToUpper();
2503 bool useRange = opt.Contains("R");
2504 bool usePL = opt.Contains("L");
2505
2506 return ROOT::Fit::Chisquare(*this, *func, useRange, usePL);
2507}
2508
2509////////////////////////////////////////////////////////////////////////////////
2510/// Remove all the content from the underflow and overflow bins, without changing the number of entries
2511/// After calling this method, every undeflow and overflow bins will have content 0.0
2512/// The Sumw2 is also cleared, since there is no more content in the bins
2513
2515{
2516 for (Int_t bin = 0; bin < fNcells; ++bin)
2517 if (IsBinUnderflow(bin) || IsBinOverflow(bin)) {
2518 UpdateBinContent(bin, 0.0);
2519 if (fSumw2.fN) fSumw2.fArray[bin] = 0.0;
2520 }
2521}
2522
2523////////////////////////////////////////////////////////////////////////////////
2524/// Compute integral (cumulative sum of bins)
2525/// The result stored in fIntegral is used by the GetRandom functions.
2526/// This function is automatically called by GetRandom when the fIntegral
2527/// array does not exist or when the number of entries in the histogram
2528/// has changed since the previous call to GetRandom.
2529/// The resulting integral is normalized to 1
2530/// If the routine is called with the onlyPositive flag set an error will
2531/// be produced in case of negative bin content and a NaN value returned
2532
2534{
2535 if (fBuffer) BufferEmpty();
2536
2537 // delete previously computed integral (if any)
2538 if (fIntegral) delete [] fIntegral;
2539
2540 // - Allocate space to store the integral and compute integral
2541 Int_t nbinsx = GetNbinsX();
2542 Int_t nbinsy = GetNbinsY();
2543 Int_t nbinsz = GetNbinsZ();
2544 Int_t nbins = nbinsx * nbinsy * nbinsz;
2545
2546 fIntegral = new Double_t[nbins + 2];
2547 Int_t ibin = 0; fIntegral[ibin] = 0;
2548
2549 for (Int_t binz=1; binz <= nbinsz; ++binz) {
2550 for (Int_t biny=1; biny <= nbinsy; ++biny) {
2551 for (Int_t binx=1; binx <= nbinsx; ++binx) {
2552 ++ibin;
2553 Double_t y = RetrieveBinContent(GetBin(binx, biny, binz));
2554 if (onlyPositive && y < 0) {
2555 Error("ComputeIntegral","Bin content is negative - return a NaN value");
2556 fIntegral[nbins] = TMath::QuietNaN();
2557 break;
2558 }
2559 fIntegral[ibin] = fIntegral[ibin - 1] + y;
2560 }
2561 }
2562 }
2563
2564 // - Normalize integral to 1
2565 if (fIntegral[nbins] == 0 ) {
2566 Error("ComputeIntegral", "Integral = zero"); return 0;
2567 }
2568 for (Int_t bin=1; bin <= nbins; ++bin) fIntegral[bin] /= fIntegral[nbins];
2569 fIntegral[nbins+1] = fEntries;
2570 return fIntegral[nbins];
2571}
2572
2573////////////////////////////////////////////////////////////////////////////////
2574/// Return a pointer to the array of bins integral.
2575/// if the pointer fIntegral is null, TH1::ComputeIntegral is called
2576/// The array dimension is the number of bins in the histograms
2577/// including underflow and overflow (fNCells)
2578/// the last value integral[fNCells] is set to the number of entries of
2579/// the histogram
2580
2582{
2583 if (!fIntegral) ComputeIntegral();
2584 return fIntegral;
2585}
2586
2587////////////////////////////////////////////////////////////////////////////////
2588/// Return a pointer to a histogram containing the cumulative content.
2589/// The cumulative can be computed both in the forward (default) or backward
2590/// direction; the name of the new histogram is constructed from
2591/// the name of this histogram with the suffix "suffix" appended provided
2592/// by the user. If not provided a default suffix="_cumulative" is used.
2593///
2594/// The cumulative distribution is formed by filling each bin of the
2595/// resulting histogram with the sum of that bin and all previous
2596/// (forward == kTRUE) or following (forward = kFALSE) bins.
2597///
2598/// Note: while cumulative distributions make sense in one dimension, you
2599/// may not be getting what you expect in more than 1D because the concept
2600/// of a cumulative distribution is much trickier to define; make sure you
2601/// understand the order of summation before you use this method with
2602/// histograms of dimension >= 2.
2603///
2604/// Note 2: By default the cumulative is computed from bin 1 to Nbins
2605/// If an axis range is set, values between the minimum and maximum of the range
2606/// are set.
2607/// Setting an axis range can also be used for including underflow and overflow in
2608/// the cumulative (e.g. by setting h->GetXaxis()->SetRange(0, h->GetNbinsX()+1); )
2610
2611TH1 *TH1::GetCumulative(Bool_t forward, const char* suffix) const
2612{
2613 const Int_t firstX = fXaxis.GetFirst();
2614 const Int_t lastX = fXaxis.GetLast();
2615 const Int_t firstY = (fDimension > 1) ? fYaxis.GetFirst() : 1;
2616 const Int_t lastY = (fDimension > 1) ? fYaxis.GetLast() : 1;
2617 const Int_t firstZ = (fDimension > 1) ? fZaxis.GetFirst() : 1;
2618 const Int_t lastZ = (fDimension > 1) ? fZaxis.GetLast() : 1;
2619
2620 TH1* hintegrated = (TH1*) Clone(fName + suffix);
2621 hintegrated->Reset();
2622 Double_t sum = 0.;
2623 Double_t esum = 0;
2624 if (forward) { // Forward computation
2625 for (Int_t binz = firstZ; binz <= lastZ; ++binz) {
2626 for (Int_t biny = firstY; biny <= lastY; ++biny) {
2627 for (Int_t binx = firstX; binx <= lastX; ++binx) {
2628 const Int_t bin = hintegrated->GetBin(binx, biny, binz);
2629 sum += RetrieveBinContent(bin);
2630 hintegrated->AddBinContent(bin, sum);
2631 if (fSumw2.fN) {
2632 esum += GetBinErrorSqUnchecked(bin);
2633 fSumw2.fArray[bin] = esum;
2634 }
2635 }
2636 }
2637 }
2638 } else { // Backward computation
2639 for (Int_t binz = lastZ; binz >= firstZ; --binz) {
2640 for (Int_t biny = lastY; biny >= firstY; --biny) {
2641 for (Int_t binx = lastX; binx >= firstX; --binx) {
2642 const Int_t bin = hintegrated->GetBin(binx, biny, binz);
2643 sum += RetrieveBinContent(bin);
2644 hintegrated->AddBinContent(bin, sum);
2645 if (fSumw2.fN) {
2646 esum += GetBinErrorSqUnchecked(bin);
2647 fSumw2.fArray[bin] = esum;
2648 }
2649 }
2650 }
2651 }
2652 }
2653 return hintegrated;
2654}
2655
2656////////////////////////////////////////////////////////////////////////////////
2657/// Copy this histogram structure to newth1.
2658///
2659/// Note that this function does not copy the list of associated functions.
2660/// Use TObject::Clone to make a full copy of a histogram.
2661///
2662/// Note also that the histogram it will be created in gDirectory (if AddDirectoryStatus()=true)
2663/// or will not be added to any directory if AddDirectoryStatus()=false
2664/// independently of the current directory stored in the original histogram
2665
2666void TH1::Copy(TObject &obj) const
2667{
2668 if (((TH1&)obj).fDirectory) {
2669 // We are likely to change the hash value of this object
2670 // with TNamed::Copy, to keep things correct, we need to
2671 // clean up its existing entries.
2672 ((TH1&)obj).fDirectory->Remove(&obj);
2673 ((TH1&)obj).fDirectory = 0;
2674 }
2675 TNamed::Copy(obj);
2676 ((TH1&)obj).fDimension = fDimension;
2677 ((TH1&)obj).fNormFactor= fNormFactor;
2678 ((TH1&)obj).fNcells = fNcells;
2679 ((TH1&)obj).fBarOffset = fBarOffset;
2680 ((TH1&)obj).fBarWidth = fBarWidth;
2681 ((TH1&)obj).fOption = fOption;
2682 ((TH1&)obj).fBinStatErrOpt = fBinStatErrOpt;
2683 ((TH1&)obj).fBufferSize= fBufferSize;
2684 // copy the Buffer
2685 // delete first a previously existing buffer
2686 if (((TH1&)obj).fBuffer != 0) {
2687 delete [] ((TH1&)obj).fBuffer;
2688 ((TH1&)obj).fBuffer = 0;
2689 }
2690 if (fBuffer) {
2691 Double_t *buf = new Double_t[fBufferSize];
2692 for (Int_t i=0;i<fBufferSize;i++) buf[i] = fBuffer[i];
2693 // obj.fBuffer has been deleted before
2694 ((TH1&)obj).fBuffer = buf;
2695 }
2696
2697
2698 TArray* a = dynamic_cast<TArray*>(&obj);
2699 if (a) a->Set(fNcells);
2700 for (Int_t i = 0; i < fNcells; i++) ((TH1&)obj).UpdateBinContent(i, RetrieveBinContent(i));
2701
2702 ((TH1&)obj).fEntries = fEntries;
2703
2704 // which will call BufferEmpty(0) and set fBuffer[0] to a Maybe one should call
2705 // assignment operator on the TArrayD
2706
2707 ((TH1&)obj).fTsumw = fTsumw;
2708 ((TH1&)obj).fTsumw2 = fTsumw2;
2709 ((TH1&)obj).fTsumwx = fTsumwx;
2710 ((TH1&)obj).fTsumwx2 = fTsumwx2;
2711 ((TH1&)obj).fMaximum = fMaximum;
2712 ((TH1&)obj).fMinimum = fMinimum;
2713
2714 TAttLine::Copy(((TH1&)obj));
2715 TAttFill::Copy(((TH1&)obj));
2716 TAttMarker::Copy(((TH1&)obj));
2717 fXaxis.Copy(((TH1&)obj).fXaxis);
2718 fYaxis.Copy(((TH1&)obj).fYaxis);
2719 fZaxis.Copy(((TH1&)obj).fZaxis);
2720 ((TH1&)obj).fXaxis.SetParent(&obj);
2721 ((TH1&)obj).fYaxis.SetParent(&obj);
2722 ((TH1&)obj).fZaxis.SetParent(&obj);
2723 fContour.Copy(((TH1&)obj).fContour);
2724 fSumw2.Copy(((TH1&)obj).fSumw2);
2725 // fFunctions->Copy(((TH1&)obj).fFunctions);
2726 // when copying an histogram if the AddDirectoryStatus() is true it
2727 // will be added to gDirectory independently of the fDirectory stored.
2728 // and if the AddDirectoryStatus() is false it will not be added to
2729 // any directory (fDirectory = 0)
2730 if (fgAddDirectory && gDirectory) {
2731 gDirectory->Append(&obj);
2732 ((TH1&)obj).fFunctions->UseRWLock();
2733 ((TH1&)obj).fDirectory = gDirectory;
2734 } else
2735 ((TH1&)obj).fDirectory = 0;
2736
2737}
2738
2739////////////////////////////////////////////////////////////////////////////////
2740/// Make a complete copy of the underlying object. If 'newname' is set,
2741/// the copy's name will be set to that name.
2742
2743TObject* TH1::Clone(const char* newname) const
2744{
2745 TH1* obj = (TH1*)IsA()->GetNew()(0);
2746 Copy(*obj);
2747
2748 // Now handle the parts that Copy doesn't do
2749 if(fFunctions) {
2750 // The Copy above might have published 'obj' to the ListOfCleanups.
2751 // Clone can call RecursiveRemove, for example via TCheckHashRecursiveRemoveConsistency
2752 // when dictionary information is initialized, so we need to
2753 // keep obj->fFunction valid during its execution and
2754 // protect the update with the write lock.
2755
2756 // Reset stats parent - else cloning the stats will clone this histogram, too.
2757 auto oldstats = dynamic_cast<TVirtualPaveStats*>(fFunctions->FindObject("stats"));
2758 TObject *oldparent = nullptr;
2759 if (oldstats) {
2760 oldparent = oldstats->GetParent();
2761 oldstats->SetParent(nullptr);
2762 }
2763
2764 auto newlist = (TList*)fFunctions->Clone();
2765
2766 if (oldstats)
2767 oldstats->SetParent(oldparent);
2768 auto newstats = dynamic_cast<TVirtualPaveStats*>(obj->fFunctions->FindObject("stats"));
2769 if (newstats)
2770 newstats->SetParent(obj);
2771
2772 auto oldlist = obj->fFunctions;
2773 {
2775 obj->fFunctions = newlist;
2776 }
2777 delete oldlist;
2778 }
2779 if(newname && strlen(newname) ) {
2780 obj->SetName(newname);
2781 }
2782 return obj;
2783}
2784
2785////////////////////////////////////////////////////////////////////////////////
2786/// Perform the automatic addition of the histogram to the given directory
2787///
2788/// Note this function is called in place when the semantic requires
2789/// this object to be added to a directory (I.e. when being read from
2790/// a TKey or being Cloned)
2791
2793{
2794 Bool_t addStatus = TH1::AddDirectoryStatus();
2795 if (addStatus) {
2796 SetDirectory(dir);
2797 if (dir) {
2799 }
2800 }
2801}
2802
2803////////////////////////////////////////////////////////////////////////////////
2804/// Compute distance from point px,py to a line.
2805///
2806/// Compute the closest distance of approach from point px,py to elements
2807/// of a histogram.
2808/// The distance is computed in pixels units.
2809///
2810/// #### Algorithm:
2811/// Currently, this simple model computes the distance from the mouse
2812/// to the histogram contour only.
2813
2815{
2816 if (!fPainter) return 9999;
2817 return fPainter->DistancetoPrimitive(px,py);
2818}
2819
2820////////////////////////////////////////////////////////////////////////////////
2821/// Performs the operation: `this = this/(c1*f1)`
2822/// if errors are defined (see TH1::Sumw2), errors are also recalculated.
2823///
2824/// Only bins inside the function range are recomputed.
2825/// IMPORTANT NOTE: If you intend to use the errors of this histogram later
2826/// you should call Sumw2 before making this operation.
2827/// This is particularly important if you fit the histogram after TH1::Divide
2828///
2829/// The function return kFALSE if the divide operation failed
2830
2832{
2833 if (!f1) {
2834 Error("Divide","Attempt to divide by a non-existing function");
2835 return kFALSE;
2836 }
2837
2838 // delete buffer if it is there since it will become invalid
2839 if (fBuffer) BufferEmpty(1);
2840
2841 Int_t nx = GetNbinsX() + 2; // normal bins + uf / of
2842 Int_t ny = GetNbinsY() + 2;
2843 Int_t nz = GetNbinsZ() + 2;
2844 if (fDimension < 2) ny = 1;
2845 if (fDimension < 3) nz = 1;
2846
2847
2848 SetMinimum();
2849 SetMaximum();
2850
2851 // - Loop on bins (including underflows/overflows)
2852 Int_t bin, binx, biny, binz;
2853 Double_t cu, w;
2854 Double_t xx[3];
2855 Double_t *params = 0;
2856 f1->InitArgs(xx,params);
2857 for (binz = 0; binz < nz; ++binz) {
2858 xx[2] = fZaxis.GetBinCenter(binz);
2859 for (biny = 0; biny < ny; ++biny) {
2860 xx[1] = fYaxis.GetBinCenter(biny);
2861 for (binx = 0; binx < nx; ++binx) {
2862 xx[0] = fXaxis.GetBinCenter(binx);
2863 if (!f1->IsInside(xx)) continue;
2865 bin = binx + nx * (biny + ny * binz);
2866 cu = c1 * f1->EvalPar(xx);
2867 if (TF1::RejectedPoint()) continue;
2868 if (cu) w = RetrieveBinContent(bin) / cu;
2869 else w = 0;
2870 UpdateBinContent(bin, w);
2871 if (fSumw2.fN) {
2872 if (cu != 0) fSumw2.fArray[bin] = GetBinErrorSqUnchecked(bin) / (cu * cu);
2873 else fSumw2.fArray[bin] = 0;
2874 }
2875 }
2876 }
2877 }
2878 ResetStats();
2879 return kTRUE;
2880}
2881
2882////////////////////////////////////////////////////////////////////////////////
2883/// Divide this histogram by h1.
2884///
2885/// `this = this/h1`
2886/// if errors are defined (see TH1::Sumw2), errors are also recalculated.
2887/// Note that if h1 has Sumw2 set, Sumw2 is automatically called for this
2888/// if not already set.
2889/// The resulting errors are calculated assuming uncorrelated histograms.
2890/// See the other TH1::Divide that gives the possibility to optionally
2891/// compute binomial errors.
2892///
2893/// IMPORTANT NOTE: If you intend to use the errors of this histogram later
2894/// you should call Sumw2 before making this operation.
2895/// This is particularly important if you fit the histogram after TH1::Scale
2896///
2897/// The function return kFALSE if the divide operation failed
2898
2899Bool_t TH1::Divide(const TH1 *h1)
2900{
2901 if (!h1) {
2902 Error("Divide", "Input histogram passed does not exist (NULL).");
2903 return kFALSE;
2904 }
2905
2906 // delete buffer if it is there since it will become invalid
2907 if (fBuffer) BufferEmpty(1);
2908
2909 try {
2910 CheckConsistency(this,h1);
2911 } catch(DifferentNumberOfBins&) {
2912 Error("Divide","Cannot divide histograms with different number of bins");
2913 return kFALSE;
2914 } catch(DifferentAxisLimits&) {
2915 Warning("Divide","Dividing histograms with different axis limits");
2916 } catch(DifferentBinLimits&) {
2917 Warning("Divide","Dividing histograms with different bin limits");
2918 } catch(DifferentLabels&) {
2919 Warning("Divide","Dividing histograms with different labels");
2920 }
2921
2922 // Create Sumw2 if h1 has Sumw2 set
2923 if (fSumw2.fN == 0 && h1->GetSumw2N() != 0) Sumw2();
2924
2925 // - Loop on bins (including underflows/overflows)
2926 for (Int_t i = 0; i < fNcells; ++i) {
2929 if (c1) UpdateBinContent(i, c0 / c1);
2930 else UpdateBinContent(i, 0);
2931
2932 if(fSumw2.fN) {
2933 if (c1 == 0) { fSumw2.fArray[i] = 0; continue; }
2934 Double_t c1sq = c1 * c1;
2935 fSumw2.fArray[i] = (GetBinErrorSqUnchecked(i) * c1sq + h1->GetBinErrorSqUnchecked(i) * c0 * c0) / (c1sq * c1sq);
2936 }
2937 }
2938 ResetStats();
2939 return kTRUE;
2940}
2941
2942////////////////////////////////////////////////////////////////////////////////
2943/// Replace contents of this histogram by the division of h1 by h2.
2944///
2945/// `this = c1*h1/(c2*h2)`
2946///
2947/// If errors are defined (see TH1::Sumw2), errors are also recalculated
2948/// Note that if h1 or h2 have Sumw2 set, Sumw2 is automatically called for this
2949/// if not already set.
2950/// The resulting errors are calculated assuming uncorrelated histograms.
2951/// However, if option ="B" is specified, Binomial errors are computed.
2952/// In this case c1 and c2 do not make real sense and they are ignored.
2953///
2954/// IMPORTANT NOTE: If you intend to use the errors of this histogram later
2955/// you should call Sumw2 before making this operation.
2956/// This is particularly important if you fit the histogram after TH1::Divide
2957///
2958/// Please note also that in the binomial case errors are calculated using standard
2959/// binomial statistics, which means when b1 = b2, the error is zero.
2960/// If you prefer to have efficiency errors not going to zero when the efficiency is 1, you must
2961/// use the function TGraphAsymmErrors::BayesDivide, which will return an asymmetric and non-zero lower
2962/// error for the case b1=b2.
2963///
2964/// The function return kFALSE if the divide operation failed
2965
2966Bool_t TH1::Divide(const TH1 *h1, const TH1 *h2, Double_t c1, Double_t c2, Option_t *option)
2967{
2968
2969 TString opt = option;
2970 opt.ToLower();
2971 Bool_t binomial = kFALSE;
2972 if (opt.Contains("b")) binomial = kTRUE;
2973 if (!h1 || !h2) {
2974 Error("Divide", "At least one of the input histograms passed does not exist (NULL).");
2975 return kFALSE;
2976 }
2977
2978 // delete buffer if it is there since it will become invalid
2979 if (fBuffer) BufferEmpty(1);
2980
2981 try {
2982 CheckConsistency(h1,h2);
2983 CheckConsistency(this,h1);
2984 } catch(DifferentNumberOfBins&) {
2985 Error("Divide","Cannot divide histograms with different number of bins");
2986 return kFALSE;
2987 } catch(DifferentAxisLimits&) {
2988 Warning("Divide","Dividing histograms with different axis limits");
2989 } catch(DifferentBinLimits&) {
2990 Warning("Divide","Dividing histograms with different bin limits");
2991 } catch(DifferentLabels&) {
2992 Warning("Divide","Dividing histograms with different labels");
2993 }
2994
2995
2996 if (!c2) {
2997 Error("Divide","Coefficient of dividing histogram cannot be zero");
2998 return kFALSE;
2999 }
3000
3001 // Create Sumw2 if h1 or h2 have Sumw2 set, or if binomial errors are explicitly requested
3002 if (fSumw2.fN == 0 && (h1->GetSumw2N() != 0 || h2->GetSumw2N() != 0 || binomial)) Sumw2();
3003
3004 SetMinimum();
3005 SetMaximum();
3006
3007 // - Loop on bins (including underflows/overflows)
3008 for (Int_t i = 0; i < fNcells; ++i) {
3010 Double_t b2 = h2->RetrieveBinContent(i);
3011 if (b2) UpdateBinContent(i, c1 * b1 / (c2 * b2));
3012 else UpdateBinContent(i, 0);
3013
3014 if (fSumw2.fN) {
3015 if (b2 == 0) { fSumw2.fArray[i] = 0; continue; }
3016 Double_t b1sq = b1 * b1; Double_t b2sq = b2 * b2;
3017 Double_t c1sq = c1 * c1; Double_t c2sq = c2 * c2;
3019 Double_t e2sq = h2->GetBinErrorSqUnchecked(i);
3020 if (binomial) {
3021 if (b1 != b2) {
3022 // in the case of binomial statistics c1 and c2 must be 1 otherwise it does not make sense
3023 // c1 and c2 are ignored
3024 //fSumw2.fArray[bin] = TMath::Abs(w*(1-w)/(c2*b2));//this is the formula in Hbook/Hoper1
3025 //fSumw2.fArray[bin] = TMath::Abs(w*(1-w)/b2); // old formula from G. Flucke
3026 // formula which works also for weighted histogram (see http://root-forum.cern.ch/viewtopic.php?t=3753 )
3027 fSumw2.fArray[i] = TMath::Abs( ( (1. - 2.* b1 / b2) * e1sq + b1sq * e2sq / b2sq ) / b2sq );
3028 } else {
3029 //in case b1=b2 error is zero
3030 //use TGraphAsymmErrors::BayesDivide for getting the asymmetric error not equal to zero
3031 fSumw2.fArray[i] = 0;
3032 }
3033 } else {
3034 fSumw2.fArray[i] = c1sq * c2sq * (e1sq * b2sq + e2sq * b1sq) / (c2sq * c2sq * b2sq * b2sq);
3035 }
3036 }
3037 }
3038 ResetStats();
3039 if (binomial)
3040 // in case of binomial division use denominator for number of entries
3041 SetEntries ( h2->GetEntries() );
3042
3043 return kTRUE;
3044}
3045
3046////////////////////////////////////////////////////////////////////////////////
3047/// Draw this histogram with options.
3048///
3049/// Histograms are drawn via the THistPainter class. Each histogram has
3050/// a pointer to its own painter (to be usable in a multithreaded program).
3051/// The same histogram can be drawn with different options in different pads.
3052/// When a histogram drawn in a pad is deleted, the histogram is
3053/// automatically removed from the pad or pads where it was drawn.
3054/// If a histogram is drawn in a pad, then filled again, the new status
3055/// of the histogram will be automatically shown in the pad next time
3056/// the pad is updated. One does not need to redraw the histogram.
3057/// To draw the current version of a histogram in a pad, one can use
3058/// `h->DrawCopy();`
3059/// This makes a clone of the histogram. Once the clone is drawn, the original
3060/// histogram may be modified or deleted without affecting the aspect of the
3061/// clone.
3062/// By default, TH1::Draw clears the current pad.
3063///
3064/// One can use TH1::SetMaximum and TH1::SetMinimum to force a particular
3065/// value for the maximum or the minimum scale on the plot.
3066///
3067/// TH1::UseCurrentStyle can be used to change all histogram graphics
3068/// attributes to correspond to the current selected style.
3069/// This function must be called for each histogram.
3070/// In case one reads and draws many histograms from a file, one can force
3071/// the histograms to inherit automatically the current graphics style
3072/// by calling before gROOT->ForceStyle();
3073///
3074/// See the THistPainter class for a description of all the drawing options.
3075
3076void TH1::Draw(Option_t *option)
3077{
3078 TString opt1 = option; opt1.ToLower();
3079 TString opt2 = option;
3080 Int_t index = opt1.Index("same");
3081
3082 // Check if the string "same" is part of a TCutg name.
3083 if (index>=0) {
3084 Int_t indb = opt1.Index("[");
3085 if (indb>=0) {
3086 Int_t indk = opt1.Index("]");
3087 if (index>indb && index<indk) index = -1;
3088 }
3089 }
3090
3091 // If there is no pad or an empty pad the "same" option is ignored.
3092 if (gPad) {
3093 if (!gPad->IsEditable()) gROOT->MakeDefCanvas();
3094 if (index>=0) {
3095 if (gPad->GetX1() == 0 && gPad->GetX2() == 1 &&
3096 gPad->GetY1() == 0 && gPad->GetY2() == 1 &&
3097 gPad->GetListOfPrimitives()->GetSize()==0) opt2.Remove(index,4);
3098 } else {
3099 //the following statement is necessary in case one attempts to draw
3100 //a temporary histogram already in the current pad
3101 if (TestBit(kCanDelete)) gPad->GetListOfPrimitives()->Remove(this);
3102 gPad->Clear();
3103 }
3104 gPad->IncrementPaletteColor(1, opt1);
3105 } else {
3106 if (index>=0) opt2.Remove(index,4);
3107 }
3108
3109 AppendPad(opt2.Data());
3110}
3111
3112////////////////////////////////////////////////////////////////////////////////
3113/// Copy this histogram and Draw in the current pad.
3114///
3115/// Once the histogram is drawn into the pad, any further modification
3116/// using graphics input will be made on the copy of the histogram,
3117/// and not to the original object.
3118/// By default a postfix "_copy" is added to the histogram name. Pass an empty postfix in case
3119/// you want to draw a histogram with the same name
3120///
3121/// See Draw for the list of options
3122
3123TH1 *TH1::DrawCopy(Option_t *option, const char * name_postfix) const
3124{
3125 TString opt = option;
3126 opt.ToLower();
3127 if (gPad && !opt.Contains("same")) gPad->Clear();
3128 TString newName = (name_postfix) ? TString::Format("%s%s",GetName(),name_postfix) : "";
3129 TH1 *newth1 = (TH1 *)Clone(newName);
3130 newth1->SetDirectory(0);
3131 newth1->SetBit(kCanDelete);
3132 if (gPad) gPad->IncrementPaletteColor(1, opt);
3133
3134 newth1->AppendPad(option);
3135 return newth1;
3136}
3137
3138////////////////////////////////////////////////////////////////////////////////
3139/// Draw a normalized copy of this histogram.
3140///
3141/// A clone of this histogram is normalized to norm and drawn with option.
3142/// A pointer to the normalized histogram is returned.
3143/// The contents of the histogram copy are scaled such that the new
3144/// sum of weights (excluding under and overflow) is equal to norm.
3145/// Note that the returned normalized histogram is not added to the list
3146/// of histograms in the current directory in memory.
3147/// It is the user's responsibility to delete this histogram.
3148/// The kCanDelete bit is set for the returned object. If a pad containing
3149/// this copy is cleared, the histogram will be automatically deleted.
3150///
3151/// See Draw for the list of options
3152
3153TH1 *TH1::DrawNormalized(Option_t *option, Double_t norm) const
3154{
3156 if (sum == 0) {
3157 Error("DrawNormalized","Sum of weights is null. Cannot normalize histogram: %s",GetName());
3158 return 0;
3159 }
3160 Bool_t addStatus = TH1::AddDirectoryStatus();
3162 TH1 *h = (TH1*)Clone();
3164 // in case of drawing with error options - scale correctly the error
3165 TString opt(option); opt.ToUpper();
3166 if (fSumw2.fN == 0) {
3167 h->Sumw2();
3168 // do not use in this case the "Error option " for drawing which is enabled by default since the normalized histogram has now errors
3169 if (opt.IsNull() || opt == "SAME") opt += "HIST";
3170 }
3171 h->Scale(norm/sum);
3172 if (TMath::Abs(fMaximum+1111) > 1e-3) h->SetMaximum(fMaximum*norm/sum);
3173 if (TMath::Abs(fMinimum+1111) > 1e-3) h->SetMinimum(fMinimum*norm/sum);
3174 h->Draw(opt);
3175 TH1::AddDirectory(addStatus);
3176 return h;
3177}
3178
3179////////////////////////////////////////////////////////////////////////////////
3180/// Display a panel with all histogram drawing options.
3181///
3182/// See class TDrawPanelHist for example
3183
3184void TH1::DrawPanel()
3185{
3186 if (!fPainter) {Draw(); if (gPad) gPad->Update();}
3187 if (fPainter) fPainter->DrawPanel();
3188}
3189
3190////////////////////////////////////////////////////////////////////////////////
3191/// Evaluate function f1 at the center of bins of this histogram.
3192///
3193/// - If option "R" is specified, the function is evaluated only
3194/// for the bins included in the function range.
3195/// - If option "A" is specified, the value of the function is added to the
3196/// existing bin contents
3197/// - If option "S" is specified, the value of the function is used to
3198/// generate a value, distributed according to the Poisson
3199/// distribution, with f1 as the mean.
3200
3201void TH1::Eval(TF1 *f1, Option_t *option)
3202{
3203 Double_t x[3];
3204 Int_t range, stat, add;
3205 if (!f1) return;
3206
3207 TString opt = option;
3208 opt.ToLower();
3209 if (opt.Contains("a")) add = 1;
3210 else add = 0;
3211 if (opt.Contains("s")) stat = 1;
3212 else stat = 0;
3213 if (opt.Contains("r")) range = 1;
3214 else range = 0;
3215
3216 // delete buffer if it is there since it will become invalid
3217 if (fBuffer) BufferEmpty(1);
3218
3219 Int_t nbinsx = fXaxis.GetNbins();
3220 Int_t nbinsy = fYaxis.GetNbins();
3221 Int_t nbinsz = fZaxis.GetNbins();
3222 if (!add) Reset();
3223
3224 for (Int_t binz = 1; binz <= nbinsz; ++binz) {
3225 x[2] = fZaxis.GetBinCenter(binz);
3226 for (Int_t biny = 1; biny <= nbinsy; ++biny) {
3227 x[1] = fYaxis.GetBinCenter(biny);
3228 for (Int_t binx = 1; binx <= nbinsx; ++binx) {
3229 Int_t bin = GetBin(binx,biny,binz);
3230 x[0] = fXaxis.GetBinCenter(binx);
3231 if (range && !f1->IsInside(x)) continue;
3232 Double_t fu = f1->Eval(x[0], x[1], x[2]);
3233 if (stat) fu = gRandom->PoissonD(fu);
3234 AddBinContent(bin, fu);
3235 if (fSumw2.fN) fSumw2.fArray[bin] += TMath::Abs(fu);
3236 }
3237 }
3238 }
3239}
3240
3241////////////////////////////////////////////////////////////////////////////////
3242/// Execute action corresponding to one event.
3243///
3244/// This member function is called when a histogram is clicked with the locator
3245///
3246/// If Left button clicked on the bin top value, then the content of this bin
3247/// is modified according to the new position of the mouse when it is released.
3248
3250{
3251 if (fPainter) fPainter->ExecuteEvent(event, px, py);
3252}
3253
3254////////////////////////////////////////////////////////////////////////////////
3255/// This function allows to do discrete Fourier transforms of TH1 and TH2.
3256/// Available transform types and flags are described below.
3257///
3258/// To extract more information about the transform, use the function
3259/// TVirtualFFT::GetCurrentTransform() to get a pointer to the current
3260/// transform object.
3261///
3262/// \param[out] h_output histogram for the output. If a null pointer is passed, a new histogram is created
3263/// and returned, otherwise, the provided histogram is used and should be big enough
3264/// \param[in] option option parameters consists of 3 parts:
3265/// - option on what to return
3266/// - "RE" - returns a histogram of the real part of the output
3267/// - "IM" - returns a histogram of the imaginary part of the output
3268/// - "MAG"- returns a histogram of the magnitude of the output
3269/// - "PH" - returns a histogram of the phase of the output
3270/// - option of transform type
3271/// - "R2C" - real to complex transforms - default
3272/// - "R2HC" - real to halfcomplex (special format of storing output data,
3273/// results the same as for R2C)
3274/// - "DHT" - discrete Hartley transform
3275/// real to real transforms (sine and cosine):
3276/// - "R2R_0", "R2R_1", "R2R_2", "R2R_3" - discrete cosine transforms of types I-IV
3277/// - "R2R_4", "R2R_5", "R2R_6", "R2R_7" - discrete sine transforms of types I-IV
3278/// To specify the type of each dimension of a 2-dimensional real to real
3279/// transform, use options of form "R2R_XX", for example, "R2R_02" for a transform,
3280/// which is of type "R2R_0" in 1st dimension and "R2R_2" in the 2nd.
3281/// - option of transform flag
3282/// - "ES" (from "estimate") - no time in preparing the transform, but probably sub-optimal
3283/// performance
3284/// - "M" (from "measure") - some time spend in finding the optimal way to do the transform
3285/// - "P" (from "patient") - more time spend in finding the optimal way to do the transform
3286/// - "EX" (from "exhaustive") - the most optimal way is found
3287/// This option should be chosen depending on how many transforms of the same size and
3288/// type are going to be done. Planning is only done once, for the first transform of this
3289/// size and type. Default is "ES".
3290///
3291/// Examples of valid options: "Mag R2C M" "Re R2R_11" "Im R2C ES" "PH R2HC EX"
3292
3293TH1* TH1::FFT(TH1* h_output, Option_t *option)
3294{
3295
3296 Int_t ndim[3];
3297 ndim[0] = this->GetNbinsX();
3298 ndim[1] = this->GetNbinsY();
3299 ndim[2] = this->GetNbinsZ();
3300
3301 TVirtualFFT *fft;
3302 TString opt = option;
3303 opt.ToUpper();
3304 if (!opt.Contains("2R")){
3305 if (!opt.Contains("2C") && !opt.Contains("2HC") && !opt.Contains("DHT")) {
3306 //no type specified, "R2C" by default
3307 opt.Append("R2C");
3308 }
3309 fft = TVirtualFFT::FFT(this->GetDimension(), ndim, opt.Data());
3310 }
3311 else {
3312 //find the kind of transform
3313 Int_t ind = opt.Index("R2R", 3);
3314 Int_t *kind = new Int_t[2];
3315 char t;
3316 t = opt[ind+4];
3317 kind[0] = atoi(&t);
3318 if (h_output->GetDimension()>1) {
3319 t = opt[ind+5];
3320 kind[1] = atoi(&t);
3321 }
3322 fft = TVirtualFFT::SineCosine(this->GetDimension(), ndim, kind, option);
3323 delete [] kind;
3324 }
3325
3326 if (!fft) return 0;
3327 Int_t in=0;
3328 for (Int_t binx = 1; binx<=ndim[0]; binx++) {
3329 for (Int_t biny=1; biny<=ndim[1]; biny++) {
3330 for (Int_t binz=1; binz<=ndim[2]; binz++) {
3331 fft->SetPoint(in, this->GetBinContent(binx, biny, binz));
3332 in++;
3333 }
3334 }
3335 }
3336 fft->Transform();
3337 h_output = TransformHisto(fft, h_output, option);
3338 return h_output;
3339}
3340
3341////////////////////////////////////////////////////////////////////////////////
3342/// Increment bin with abscissa X by 1.
3343///
3344/// if x is less than the low-edge of the first bin, the Underflow bin is incremented
3345/// if x is equal to or greater than the upper edge of last bin, the Overflow bin is incremented
3346///
3347/// If the storage of the sum of squares of weights has been triggered,
3348/// via the function Sumw2, then the sum of the squares of weights is incremented
3349/// by 1 in the bin corresponding to x.
3350///
3351/// The function returns the corresponding bin number which has its content incremented by 1
3352
3354{
3355 if (fBuffer) return BufferFill(x,1);
3356
3357 Int_t bin;
3358 fEntries++;
3359 bin =fXaxis.FindBin(x);
3360 if (bin <0) return -1;
3361 AddBinContent(bin);
3362 if (fSumw2.fN) ++fSumw2.fArray[bin];
3363 if (bin == 0 || bin > fXaxis.GetNbins()) {
3364 if (!GetStatOverflowsBehaviour()) return -1;
3365 }
3366 ++fTsumw;
3367 ++fTsumw2;
3368 fTsumwx += x;
3369 fTsumwx2 += x*x;
3370 return bin;
3371}
3372
3373////////////////////////////////////////////////////////////////////////////////
3374/// Increment bin with abscissa X with a weight w.
3375///
3376/// if x is less than the low-edge of the first bin, the Underflow bin is incremented
3377/// if x is equal to or greater than the upper edge of last bin, the Overflow bin is incremented
3378///
3379/// If the weight is not equal to 1, the storage of the sum of squares of
3380/// weights is automatically triggered and the sum of the squares of weights is incremented
3381/// by \f$ w^2 \f$ in the bin corresponding to x.
3382///
3383/// The function returns the corresponding bin number which has its content incremented by w
3384
3386{
3387
3388 if (fBuffer) return BufferFill(x,w);
3389
3390 Int_t bin;
3391 fEntries++;
3392 bin =fXaxis.FindBin(x);
3393 if (bin <0) return -1;
3394 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW) ) Sumw2(); // must be called before AddBinContent
3395 if (fSumw2.fN) fSumw2.fArray[bin] += w*w;
3396 AddBinContent(bin, w);
3397 if (bin == 0 || bin > fXaxis.GetNbins()) {
3398 if (!GetStatOverflowsBehaviour()) return -1;
3399 }
3400 Double_t z= w;
3401 fTsumw += z;
3402 fTsumw2 += z*z;
3403 fTsumwx += z*x;
3404 fTsumwx2 += z*x*x;
3405 return bin;
3406}
3407
3408////////////////////////////////////////////////////////////////////////////////
3409/// Increment bin with namex with a weight w
3410///
3411/// if x is less than the low-edge of the first bin, the Underflow bin is incremented
3412/// if x is equal to or greater than the upper edge of last bin, the Overflow bin is incremented
3413///
3414/// If the weight is not equal to 1, the storage of the sum of squares of
3415/// weights is automatically triggered and the sum of the squares of weights is incremented
3416/// by \f$ w^2 \f$ in the bin corresponding to x.
3417///
3418/// The function returns the corresponding bin number which has its content
3419/// incremented by w.
3420
3421Int_t TH1::Fill(const char *namex, Double_t w)
3422{
3423 Int_t bin;
3424 fEntries++;
3425 bin =fXaxis.FindBin(namex);
3426 if (bin <0) return -1;
3427 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW)) Sumw2();
3428 if (fSumw2.fN) fSumw2.fArray[bin] += w*w;
3429 AddBinContent(bin, w);
3430 if (bin == 0 || bin > fXaxis.GetNbins()) return -1;
3431 Double_t z= w;
3432 fTsumw += z;
3433 fTsumw2 += z*z;
3434 // this make sense if the histogram is not expanding (the x axis cannot be extended)
3435 if (!fXaxis.CanExtend() || !fXaxis.IsAlphanumeric()) {
3437 fTsumwx += z*x;
3438 fTsumwx2 += z*x*x;
3439 }
3440 return bin;
3441}
3442
3443////////////////////////////////////////////////////////////////////////////////
3444/// Fill this histogram with an array x and weights w.
3445///
3446/// \param[in] ntimes number of entries in arrays x and w (array size must be ntimes*stride)
3447/// \param[in] x array of values to be histogrammed
3448/// \param[in] w array of weighs
3449/// \param[in] stride step size through arrays x and w
3450///
3451/// If the weight is not equal to 1, the storage of the sum of squares of
3452/// weights is automatically triggered and the sum of the squares of weights is incremented
3453/// by \f$ w^2 \f$ in the bin corresponding to x.
3454/// if w is NULL each entry is assumed a weight=1
3455
3456void TH1::FillN(Int_t ntimes, const Double_t *x, const Double_t *w, Int_t stride)
3457{
3458 //If a buffer is activated, fill buffer
3459 if (fBuffer) {
3460 ntimes *= stride;
3461 Int_t i = 0;
3462 for (i=0;i<ntimes;i+=stride) {
3463 if (!fBuffer) break; // buffer can be deleted in BufferFill when is empty
3464 if (w) BufferFill(x[i],w[i]);
3465 else BufferFill(x[i], 1.);
3466 }
3467 // fill the remaining entries if the buffer has been deleted
3468 if (i < ntimes && fBuffer==0) {
3469 auto weights = w ? &w[i] : nullptr;
3470 DoFillN((ntimes-i)/stride,&x[i],weights,stride);
3471 }
3472 return;
3473 }
3474 // call internal method
3475 DoFillN(ntimes, x, w, stride);
3476}
3477
3478////////////////////////////////////////////////////////////////////////////////
3479/// Internal method to fill histogram content from a vector
3480/// called directly by TH1::BufferEmpty
3481
3482void TH1::DoFillN(Int_t ntimes, const Double_t *x, const Double_t *w, Int_t stride)
3483{
3484 Int_t bin,i;
3485
3486 fEntries += ntimes;
3487 Double_t ww = 1;
3488 Int_t nbins = fXaxis.GetNbins();
3489 ntimes *= stride;
3490 for (i=0;i<ntimes;i+=stride) {
3491 bin =fXaxis.FindBin(x[i]);
3492 if (bin <0) continue;
3493 if (w) ww = w[i];
3494 if (!fSumw2.fN && ww != 1.0 && !TestBit(TH1::kIsNotW)) Sumw2();
3495 if (fSumw2.fN) fSumw2.fArray[bin] += ww*ww;
3496 AddBinContent(bin, ww);
3497 if (bin == 0 || bin > nbins) {
3498 if (!GetStatOverflowsBehaviour()) continue;
3499 }
3500 Double_t z= ww;
3501 fTsumw += z;
3502 fTsumw2 += z*z;
3503 fTsumwx += z*x[i];
3504 fTsumwx2 += z*x[i]*x[i];
3505 }
3506}
3507
3508////////////////////////////////////////////////////////////////////////////////
3509/// Fill histogram following distribution in function fname.
3510///
3511/// @param fname : Function name used for filling the histogram
3512/// @param ntimes : number of times the histogram is filled
3513/// @param rng : (optional) Random number generator used to sample
3514///
3515///
3516/// The distribution contained in the function fname (TF1) is integrated
3517/// over the channel contents for the bin range of this histogram.
3518/// It is normalized to 1.
3519///
3520/// Getting one random number implies:
3521/// - Generating a random number between 0 and 1 (say r1)
3522/// - Look in which bin in the normalized integral r1 corresponds to
3523/// - Fill histogram channel
3524/// ntimes random numbers are generated
3525///
3526/// One can also call TF1::GetRandom to get a random variate from a function.
3527
3528void TH1::FillRandom(const char *fname, Int_t ntimes, TRandom * rng)
3529{
3530 Int_t bin, binx, ibin, loop;
3531 Double_t r1, x;
3532 // - Search for fname in the list of ROOT defined functions
3533 TF1 *f1 = (TF1*)gROOT->GetFunction(fname);
3534 if (!f1) { Error("FillRandom", "Unknown function: %s",fname); return; }
3535
3536 // - Allocate temporary space to store the integral and compute integral
3537
3538 TAxis * xAxis = &fXaxis;
3539
3540 // in case axis of histogram is not defined use the function axis
3541 if (fXaxis.GetXmax() <= fXaxis.GetXmin()) {
3543 f1->GetRange(xmin,xmax);
3544 Info("FillRandom","Using function axis and range [%g,%g]",xmin, xmax);
3545 xAxis = f1->GetHistogram()->GetXaxis();
3546 }
3547
3548 Int_t first = xAxis->GetFirst();
3549 Int_t last = xAxis->GetLast();
3550 Int_t nbinsx = last-first+1;
3551
3552 Double_t *integral = new Double_t[nbinsx+1];
3553 integral[0] = 0;
3554 for (binx=1;binx<=nbinsx;binx++) {
3555 Double_t fint = f1->Integral(xAxis->GetBinLowEdge(binx+first-1),xAxis->GetBinUpEdge(binx+first-1), 0.);
3556 integral[binx] = integral[binx-1] + fint;
3557 }
3558
3559 // - Normalize integral to 1
3560 if (integral[nbinsx] == 0 ) {
3561 delete [] integral;
3562 Error("FillRandom", "Integral = zero"); return;
3563 }
3564 for (bin=1;bin<=nbinsx;bin++) integral[bin] /= integral[nbinsx];
3565
3566 // --------------Start main loop ntimes
3567 for (loop=0;loop<ntimes;loop++) {
3568 r1 = (rng) ? rng->Rndm() : gRandom->Rndm();
3569 ibin = TMath::BinarySearch(nbinsx,&integral[0],r1);
3570 //binx = 1 + ibin;
3571 //x = xAxis->GetBinCenter(binx); //this is not OK when SetBuffer is used
3572 x = xAxis->GetBinLowEdge(ibin+first)
3573 +xAxis->GetBinWidth(ibin+first)*(r1-integral[ibin])/(integral[ibin+1] - integral[ibin]);
3574 Fill(x);
3575 }
3576 delete [] integral;
3577}
3578
3579////////////////////////////////////////////////////////////////////////////////
3580/// Fill histogram following distribution in histogram h.
3581///
3582/// @param h : Histogram pointer used for sampling random number
3583/// @param ntimes : number of times the histogram is filled
3584/// @param rng : (optional) Random number generator used for sampling
3585///
3586/// The distribution contained in the histogram h (TH1) is integrated
3587/// over the channel contents for the bin range of this histogram.
3588/// It is normalized to 1.
3589///
3590/// Getting one random number implies:
3591/// - Generating a random number between 0 and 1 (say r1)
3592/// - Look in which bin in the normalized integral r1 corresponds to
3593/// - Fill histogram channel ntimes random numbers are generated
3594///
3595/// SPECIAL CASE when the target histogram has the same binning as the source.
3596/// in this case we simply use a poisson distribution where
3597/// the mean value per bin = bincontent/integral.
3598
3599void TH1::FillRandom(TH1 *h, Int_t ntimes, TRandom * rng)
3600{
3601 if (!h) { Error("FillRandom", "Null histogram"); return; }
3602 if (fDimension != h->GetDimension()) {
3603 Error("FillRandom", "Histograms with different dimensions"); return;
3604 }
3605 if (std::isnan(h->ComputeIntegral(true))) {
3606 Error("FillRandom", "Histograms contains negative bins, does not represent probabilities");
3607 return;
3608 }
3609
3610 //in case the target histogram has the same binning and ntimes much greater
3611 //than the number of bins we can use a fast method
3613 Int_t last = fXaxis.GetLast();
3614 Int_t nbins = last-first+1;
3615 if (ntimes > 10*nbins) {
3616 try {
3617 CheckConsistency(this,h);
3618 Double_t sumw = h->Integral(first,last);
3619 if (sumw == 0) return;
3620 Double_t sumgen = 0;
3621 for (Int_t bin=first;bin<=last;bin++) {
3622 Double_t mean = h->RetrieveBinContent(bin)*ntimes/sumw;
3623 Double_t cont = (rng) ? rng->Poisson(mean) : gRandom->Poisson(mean);
3624 sumgen += cont;
3625 AddBinContent(bin,cont);
3626 if (fSumw2.fN) fSumw2.fArray[bin] += cont;
3627 }
3628
3629 // fix for the fluctuations in the total number n
3630 // since we use Poisson instead of multinomial
3631 // add a correction to have ntimes as generated entries
3632 Int_t i;
3633 if (sumgen < ntimes) {
3634 // add missing entries
3635 for (i = Int_t(sumgen+0.5); i < ntimes; ++i)
3636 {
3637 Double_t x = h->GetRandom();
3638 Fill(x);
3639 }
3640 }
3641 else if (sumgen > ntimes) {
3642 // remove extra entries
3643 i = Int_t(sumgen+0.5);
3644 while( i > ntimes) {
3645 Double_t x = h->GetRandom(rng);
3646 Int_t ibin = fXaxis.FindBin(x);
3648 // skip in case bin is empty
3649 if (y > 0) {
3650 SetBinContent(ibin, y-1.);
3651 i--;
3652 }
3653 }
3654 }
3655
3656 ResetStats();
3657 return;
3658 }
3659 catch(std::exception&) {} // do nothing
3660 }
3661 // case of different axis and not too large ntimes
3662
3663 if (h->ComputeIntegral() ==0) return;
3664 Int_t loop;
3665 Double_t x;
3666 for (loop=0;loop<ntimes;loop++) {
3667 x = h->GetRandom();
3668 Fill(x);
3669 }
3670}
3671
3672////////////////////////////////////////////////////////////////////////////////
3673/// Return Global bin number corresponding to x,y,z
3674///
3675/// 2-D and 3-D histograms are represented with a one dimensional
3676/// structure. This has the advantage that all existing functions, such as
3677/// GetBinContent, GetBinError, GetBinFunction work for all dimensions.
3678/// This function tries to extend the axis if the given point belongs to an
3679/// under-/overflow bin AND if CanExtendAllAxes() is true.
3680///
3681/// See also TH1::GetBin, TAxis::FindBin and TAxis::FindFixBin
3682
3684{
3685 if (GetDimension() < 2) {
3686 return fXaxis.FindBin(x);
3687 }
3688 if (GetDimension() < 3) {
3689 Int_t nx = fXaxis.GetNbins()+2;
3690 Int_t binx = fXaxis.FindBin(x);
3691 Int_t biny = fYaxis.FindBin(y);
3692 return binx + nx*biny;
3693 }
3694 if (GetDimension() < 4) {
3695 Int_t nx = fXaxis.GetNbins()+2;
3696 Int_t ny = fYaxis.GetNbins()+2;
3697 Int_t binx = fXaxis.FindBin(x);
3698 Int_t biny = fYaxis.FindBin(y);
3699 Int_t binz = fZaxis.FindBin(z);
3700 return binx + nx*(biny +ny*binz);
3701 }
3702 return -1;
3703}
3704
3705////////////////////////////////////////////////////////////////////////////////
3706/// Return Global bin number corresponding to x,y,z.
3707///
3708/// 2-D and 3-D histograms are represented with a one dimensional
3709/// structure. This has the advantage that all existing functions, such as
3710/// GetBinContent, GetBinError, GetBinFunction work for all dimensions.
3711/// This function DOES NOT try to extend the axis if the given point belongs
3712/// to an under-/overflow bin.
3713///
3714/// See also TH1::GetBin, TAxis::FindBin and TAxis::FindFixBin
3715
3717{
3718 if (GetDimension() < 2) {
3719 return fXaxis.FindFixBin(x);
3720 }
3721 if (GetDimension() < 3) {
3722 Int_t nx = fXaxis.GetNbins()+2;
3723 Int_t binx = fXaxis.FindFixBin(x);
3724 Int_t biny = fYaxis.FindFixBin(y);
3725 return binx + nx*biny;
3726 }
3727 if (GetDimension() < 4) {
3728 Int_t nx = fXaxis.GetNbins()+2;
3729 Int_t ny = fYaxis.GetNbins()+2;
3730 Int_t binx = fXaxis.FindFixBin(x);
3731 Int_t biny = fYaxis.FindFixBin(y);
3732 Int_t binz = fZaxis.FindFixBin(z);
3733 return binx + nx*(biny +ny*binz);
3734 }
3735 return -1;
3736}
3737
3738////////////////////////////////////////////////////////////////////////////////
3739/// Find first bin with content > threshold for axis (1=x, 2=y, 3=z)
3740/// if no bins with content > threshold is found the function returns -1.
3741/// The search will occur between the specified first and last bin. Specifying
3742/// the value of the last bin to search to less than zero will search until the
3743/// last defined bin.
3744
3745Int_t TH1::FindFirstBinAbove(Double_t threshold, Int_t axis, Int_t firstBin, Int_t lastBin) const
3746{
3747 if (fBuffer) ((TH1*)this)->BufferEmpty();
3748
3749 if (axis < 1 || (axis > 1 && GetDimension() == 1 ) ||
3750 ( axis > 2 && GetDimension() == 2 ) || ( axis > 3 && GetDimension() > 3 ) ) {
3751 Warning("FindFirstBinAbove","Invalid axis number : %d, axis x assumed\n",axis);
3752 axis = 1;
3753 }
3754 if (firstBin < 1) {
3755 firstBin = 1;
3756 }
3757 Int_t nbinsx = fXaxis.GetNbins();
3758 Int_t nbinsy = (GetDimension() > 1 ) ? fYaxis.GetNbins() : 1;
3759 Int_t nbinsz = (GetDimension() > 2 ) ? fZaxis.GetNbins() : 1;
3760
3761 if (axis == 1) {
3762 if (lastBin < 0 || lastBin > fXaxis.GetNbins()) {
3763 lastBin = fXaxis.GetNbins();
3764 }
3765 for (Int_t binx = firstBin; binx <= lastBin; binx++) {
3766 for (Int_t biny = 1; biny <= nbinsy; biny++) {
3767 for (Int_t binz = 1; binz <= nbinsz; binz++) {
3768 if (RetrieveBinContent(GetBin(binx,biny,binz)) > threshold) return binx;
3769 }
3770 }
3771 }
3772 }
3773 else if (axis == 2) {
3774 if (lastBin < 0 || lastBin > fYaxis.GetNbins()) {
3775 lastBin = fYaxis.GetNbins();
3776 }
3777 for (Int_t biny = firstBin; biny <= lastBin; biny++) {
3778 for (Int_t binx = 1; binx <= nbinsx; binx++) {
3779 for (Int_t binz = 1; binz <= nbinsz; binz++) {
3780 if (RetrieveBinContent(GetBin(binx,biny,binz)) > threshold) return biny;
3781 }
3782 }
3783 }
3784 }
3785 else if (axis == 3) {
3786 if (lastBin < 0 || lastBin > fZaxis.GetNbins()) {
3787 lastBin = fZaxis.GetNbins();
3788 }
3789 for (Int_t binz = firstBin; binz <= lastBin; binz++) {
3790 for (Int_t binx = 1; binx <= nbinsx; binx++) {
3791 for (Int_t biny = 1; biny <= nbinsy; biny++) {
3792 if (RetrieveBinContent(GetBin(binx,biny,binz)) > threshold) return binz;
3793 }
3794 }
3795 }
3796 }
3797
3798 return -1;
3799}
3800
3801////////////////////////////////////////////////////////////////////////////////
3802/// Find last bin with content > threshold for axis (1=x, 2=y, 3=z)
3803/// if no bins with content > threshold is found the function returns -1.
3804/// The search will occur between the specified first and last bin. Specifying
3805/// the value of the last bin to search to less than zero will search until the
3806/// last defined bin.
3807
3808Int_t TH1::FindLastBinAbove(Double_t threshold, Int_t axis, Int_t firstBin, Int_t lastBin) const
3809{
3810 if (fBuffer) ((TH1*)this)->BufferEmpty();
3811
3812
3813 if (axis < 1 || ( axis > 1 && GetDimension() == 1 ) ||
3814 ( axis > 2 && GetDimension() == 2 ) || ( axis > 3 && GetDimension() > 3) ) {
3815 Warning("FindFirstBinAbove","Invalid axis number : %d, axis x assumed\n",axis);
3816 axis = 1;
3817 }
3818 if (firstBin < 1) {
3819 firstBin = 1;
3820 }
3821 Int_t nbinsx = fXaxis.GetNbins();
3822 Int_t nbinsy = (GetDimension() > 1 ) ? fYaxis.GetNbins() : 1;
3823 Int_t nbinsz = (GetDimension() > 2 ) ? fZaxis.GetNbins() : 1;
3824
3825 if (axis == 1) {
3826 if (lastBin < 0 || lastBin > fXaxis.GetNbins()) {
3827 lastBin = fXaxis.GetNbins();
3828 }
3829 for (Int_t binx = lastBin; binx >= firstBin; binx--) {
3830 for (Int_t biny = 1; biny <= nbinsy; biny++) {
3831 for (Int_t binz = 1; binz <= nbinsz; binz++) {
3832 if (RetrieveBinContent(GetBin(binx, biny, binz)) > threshold) return binx;
3833 }
3834 }
3835 }
3836 }
3837 else if (axis == 2) {
3838 if (lastBin < 0 || lastBin > fYaxis.GetNbins()) {
3839 lastBin = fYaxis.GetNbins();
3840 }
3841 for (Int_t biny = lastBin; biny >= firstBin; biny--) {
3842 for (Int_t binx = 1; binx <= nbinsx; binx++) {
3843 for (Int_t binz = 1; binz <= nbinsz; binz++) {
3844 if (RetrieveBinContent(GetBin(binx, biny, binz)) > threshold) return biny;
3845 }
3846 }
3847 }
3848 }
3849 else if (axis == 3) {
3850 if (lastBin < 0 || lastBin > fZaxis.GetNbins()) {
3851 lastBin = fZaxis.GetNbins();
3852 }
3853 for (Int_t binz = lastBin; binz >= firstBin; binz--) {
3854 for (Int_t binx = 1; binx <= nbinsx; binx++) {
3855 for (Int_t biny = 1; biny <= nbinsy; biny++) {
3856 if (RetrieveBinContent(GetBin(binx, biny, binz)) > threshold) return binz;
3857 }
3858 }
3859 }
3860 }
3861
3862 return -1;
3863}
3864
3865////////////////////////////////////////////////////////////////////////////////
3866/// Search object named name in the list of functions.
3867
3868TObject *TH1::FindObject(const char *name) const
3869{
3870 if (fFunctions) return fFunctions->FindObject(name);
3871 return 0;
3872}
3873
3874////////////////////////////////////////////////////////////////////////////////
3875/// Search object obj in the list of functions.
3876
3877TObject *TH1::FindObject(const TObject *obj) const
3878{
3879 if (fFunctions) return fFunctions->FindObject(obj);
3880 return 0;
3881}
3882
3883////////////////////////////////////////////////////////////////////////////////
3884/// Fit histogram with function fname.
3885///
3886/// fname is the name of an already predefined function created by TF1 or TF2
3887/// Predefined functions such as gaus, expo and poln are automatically
3888/// created by ROOT.
3889/// fname can also be a formula, accepted by the linear fitter (linear parts divided
3890/// by "++" sign), for example "x++sin(x)" for fitting "[0]*x+[1]*sin(x)"
3891///
3892/// This function finds a pointer to the TF1 object with name fname
3893/// and calls TH1::Fit(TF1 *f1,...)
3894
3895TFitResultPtr TH1::Fit(const char *fname ,Option_t *option ,Option_t *goption, Double_t xxmin, Double_t xxmax)
3896{
3897 char *linear;
3898 linear= (char*)strstr(fname, "++");
3899 Int_t ndim=GetDimension();
3900 if (linear){
3901 if (ndim<2){
3902 TF1 f1(fname, fname, xxmin, xxmax);
3903 return Fit(&f1,option,goption,xxmin,xxmax);
3904 }
3905 else if (ndim<3){
3906 TF2 f2(fname, fname);
3907 return Fit(&f2,option,goption,xxmin,xxmax);
3908 }
3909 else{
3910 TF3 f3(fname, fname);
3911 return Fit(&f3,option,goption,xxmin,xxmax);
3912 }
3913 }
3914 else{
3915 TF1 * f1 = (TF1*)gROOT->GetFunction(fname);
3916 if (!f1) { Printf("Unknown function: %s",fname); return -1; }
3917 return Fit(f1,option,goption,xxmin,xxmax);
3918 }
3919}
3920
3921////////////////////////////////////////////////////////////////////////////////
3922/// Fit histogram with function f1.
3923///
3924/// \param[in] option fit options is given in parameter option.
3925/// - "W" Ignore the bin uncertainties when fitting using the default least square (chi2) method but skip empty bins
3926/// - "WW" Ignore the bin uncertainties when fitting using the default least square (chi2) method and include also the empty bins
3927/// - "I" Use integral of function in bin, normalized by the bin volume,
3928/// instead of value at bin center
3929/// - "L" Use Loglikelihood method (default is chisquare method)
3930/// - "WL" Use Loglikelihood method and bin contents are not integer,
3931/// i.e. histogram is weighted (must have Sumw2() set)
3932/// -"MULTI" Use Loglikelihood method based on multi-nomial distribution.
3933/// In this case function must be normalized and one fits only the function shape (a not extended binned
3934/// likelihood fit)
3935/// - "P" Use Pearson chi2 (using expected errors instead of observed errors)
3936/// - "U" Use a User specified fitting algorithm (via SetFCN)
3937/// - "Q" Quiet mode (minimum printing)
3938/// - "V" Verbose mode (default is between Q and V)
3939/// - "E" Perform better Errors estimation using Minos technique
3940/// - "B" User defined parameter settings are used for predefined functions
3941/// like "gaus", "expo", "poln", "landau".
3942/// Use this option when you want to fix one or more parameters for these functions.
3943/// - "M" More. Improve fit results.
3944/// It uses the IMPROVE command of TMinuit (see TMinuit::mnimpr).
3945/// This algorithm attempts to improve the found local minimum by searching for a
3946/// better one.
3947/// - "R" Use the Range specified in the function range
3948/// - "N" Do not store the graphics function, do not draw
3949/// - "0" Do not plot the result of the fit. By default the fitted function
3950/// is drawn unless the option"N" above is specified.
3951/// - "+" Add this new fitted function to the list of fitted functions
3952/// (by default, any previous function is deleted)
3953/// - "C" In case of linear fitting, don't calculate the chisquare
3954/// (saves time)
3955/// - "F" If fitting a polN, switch to minuit fitter
3956/// - "S" The result of the fit is returned in the TFitResultPtr
3957/// (see below Access to the Fit Result)
3958/// \param[in] goption specify a list of graphics options. See TH1::Draw for a complete list of these options.
3959/// \param[in] xxmin range
3960/// \param[in] xxmax range
3961///
3962/// In order to use the Range option, one must first create a function
3963/// with the expression to be fitted. For example, if your histogram
3964/// has a defined range between -4 and 4 and you want to fit a gaussian
3965/// only in the interval 1 to 3, you can do:
3966///
3967/// ~~~ {.cpp}
3968/// TF1 *f1 = new TF1("f1", "gaus", 1, 3);
3969/// histo->Fit("f1", "R");
3970/// ~~~
3971///
3972/// ## Setting initial conditions
3973/// Parameters must be initialized before invoking the Fit function.
3974/// The setting of the parameter initial values is automatic for the
3975/// predefined functions : poln, expo, gaus, landau. One can however disable
3976/// this automatic computation by specifying the option "B".
3977/// Note that if a predefined function is defined with an argument,
3978/// eg, gaus(0), expo(1), you must specify the initial values for
3979/// the parameters.
3980/// You can specify boundary limits for some or all parameters via
3981///
3982/// ~~~ {.cpp}
3983/// f1->SetParLimits(p_number, parmin, parmax);
3984/// ~~~
3985///
3986/// if parmin>=parmax, the parameter is fixed
3987/// Note that you are not forced to fix the limits for all parameters.
3988/// For example, if you fit a function with 6 parameters, you can do:
3989///
3990/// ~~~ {.cpp}
3991/// func->SetParameters(0, 3.1, 1.e-6, -8, 0, 100);
3992/// func->SetParLimits(3, -10, -4);
3993/// func->FixParameter(4, 0);
3994/// func->SetParLimits(5, 1, 1);
3995/// ~~~
3996///
3997/// With this setup, parameters 0->2 can vary freely
3998/// Parameter 3 has boundaries [-10,-4] with initial value -8
3999/// Parameter 4 is fixed to 0
4000/// Parameter 5 is fixed to 100.
4001/// When the lower limit and upper limit are equal, the parameter is fixed.
4002/// However to fix a parameter to 0, one must call the FixParameter function.
4003///
4004///
4005/// #### Changing the fitting objective function
4006///
4007/// By default a chi square function is used for fitting. When option "L" (or "LL") is used
4008/// a Poisson likelihood function (see note below) is used.
4009/// Using option "MULTI" a multinomial likelihood fit is used. In this case the function normalization is not fitted
4010/// but only the function shape. Therefore the provided function must be normalized.
4011/// The functions are defined in the header Fit/Chi2Func.h or Fit/PoissonLikelihoodFCN and they
4012/// are implemented using the routines FitUtil::EvaluateChi2 or FitUtil::EvaluatePoissonLogL in
4013/// the file math/mathcore/src/FitUtil.cxx.
4014/// To specify a User defined fitting function, specify option "U" and
4015/// call the following functions:
4016///
4017/// ~~~ {.cpp}
4018/// TVirtualFitter::Fitter(myhist)->SetFCN(MyFittingFunction)
4019/// ~~~
4020///
4021/// where MyFittingFunction is of type:
4022///
4023/// ~~~ {.cpp}
4024/// extern void MyFittingFunction(Int_t &npar, Double_t *gin, Double_t &f, Double_t *u, Int_t flag);
4025/// ~~~
4026///
4027/// #### Chi2 Fits
4028///
4029/// By default a chi2 (least-square) fit is performed on the histogram. The so-called modified least-square method
4030/// is used where the residual for each bin is computed using as error the observed value (the bin error)
4031///
4032/// \f[
4033/// Chi2 = \sum{ \left(\frac{y(i) - f(x(i) | p )}{e(i)} \right)^2 }
4034/// \f]
4035///
4036/// where y(i) is the bin content for each bin i, x(i) is the bin center and e(i) is the bin error (sqrt(y(i) for
4037/// an un-weighted histogram. Bins with zero errors are excluded from the fit. See also later the note on the treatment
4038/// of empty bins. When using option "I" the residual is computed not using the function value at the bin center, f
4039/// (x(i) | p), but the integral of the function in the bin, Integral{ f(x|p)dx } divided by the bin volume
4040///
4041/// #### Likelihood Fits
4042///
4043/// When using option "L" a likelihood fit is used instead of the default chi2 square fit.
4044/// The likelihood is built assuming a Poisson probability density function for each bin.
4045/// The negative log-likelihood to be minimized is
4046///
4047/// \f[
4048/// NLL = \sum{ log Poisson ( y(i) | f(x(i) | p ) ) }
4049/// \f]
4050///
4051/// The exact likelihood used is the Poisson likelihood described in this paper:
4052/// S. Baker and R. D. Cousins, “Clarification of the use of chi-square and likelihood functions in fits to histograms,”
4053/// Nucl. Instrum. Meth. 221 (1984) 437.
4054///
4055/// This method can then be used only when the bin content represents counts (i.e. errors are sqrt(N) ).
4056/// The likelihood method has the advantage of treating correctly bins with low statistics. In case of high
4057/// statistics/bin the distribution of the bin content becomes a normal distribution and the likelihood and chi2 fit
4058/// give the same result.
4059///
4060/// The likelihood method, although a bit slower, it is therefore the recommended method in case of low
4061/// bin statistics, where the chi2 method may give incorrect results, in particular when there are
4062/// several empty bins (see also below).
4063/// In case of a weighted histogram, it is possible to perform a likelihood fit by using the
4064/// option "WL". Note a weighted histogram is a histogram which has been filled with weights and it
4065/// contains the sum of the weight square ( TH1::Sumw2() has been called). The bin error for a weighted
4066/// histogram is the square root of the sum of the weight square.
4067///
4068/// #### Treatment of Empty Bins
4069///
4070/// Empty bins, which have the content equal to zero AND error equal to zero,
4071/// are excluded by default from the chisquare fit, but they are considered in the likelihood fit.
4072/// since they affect the likelihood if the function value in these bins is not negligible.
4073/// When using option "WW" these bins will be considered in the chi2 fit with an error of 1.
4074/// Note that if the histogram is having bins with zero content and non zero-errors they are considered as
4075/// any other bins in the fit. Instead bins with zero error and non-zero content are excluded in the chi2 fit.
4076/// A likelihood fit should also not be performed on such a histogram, since we are assuming a wrong pdf for each bin.
4077/// In general, one should not fit a histogram with non-empty bins and zero errors, apart if all the bins have zero
4078/// errors. In this case one could use the option "w", which gives a weight=1 for each bin (unweighted least-square
4079/// fit).
4080/// Note that in case of histogram with no errors (chi2 fit with option W or W1) the resulting fitted parameter errors
4081/// are corrected by the obtained chi2 value using this expression: errorp *= sqrt(chisquare/(ndf-1))
4082///
4083/// #### Fitting a histogram of dimension N with a function of dimension N-1
4084///
4085/// It is possible to fit a TH2 with a TF1 or a TH3 with a TF2.
4086/// In this case the option "Integral" is not allowed and each cell has
4087/// equal weight. Also in this case the obtained parameter error are corrected as in the case when the
4088/// option "W" is used (see above)
4089///
4090/// #### Associated functions
4091///
4092/// One or more object (typically a TF1*) can be added to the list
4093/// of functions (fFunctions) associated to each histogram.
4094/// When TH1::Fit is invoked, the fitted function is added to this list.
4095/// Given a histogram h, one can retrieve an associated function
4096/// with:
4097///
4098/// ~~~ {.cpp}
4099/// TF1 *myfunc = h->GetFunction("myfunc");
4100/// ~~~
4101///
4102/// #### Access to the fit result
4103///
4104/// The function returns a TFitResultPtr which can hold a pointer to a TFitResult object.
4105/// By default the TFitResultPtr contains only the status of the fit which is return by an
4106/// automatic conversion of the TFitResultPtr to an integer. One can write in this case directly:
4107///
4108/// ~~~ {.cpp}
4109/// Int_t fitStatus = h->Fit(myFunc)
4110/// ~~~
4111///
4112/// If the option "S" is instead used, TFitResultPtr contains the TFitResult and behaves as a smart
4113/// pointer to it. For example one can do:
4114///
4115/// ~~~ {.cpp}
4116/// TFitResultPtr r = h->Fit(myFunc,"S");
4117/// TMatrixDSym cov = r->GetCovarianceMatrix(); // to access the covariance matrix
4118/// Double_t chi2 = r->Chi2(); // to retrieve the fit chi2
4119/// Double_t par0 = r->Parameter(0); // retrieve the value for the parameter 0
4120/// Double_t err0 = r->ParError(0); // retrieve the error for the parameter 0
4121/// r->Print("V"); // print full information of fit including covariance matrix
4122/// r->Write(); // store the result in a file
4123/// ~~~
4124///
4125/// The fit parameters, error and chi2 (but not covariance matrix) can be retrieved also
4126/// from the fitted function.
4127/// If the histogram is made persistent, the list of
4128/// associated functions is also persistent. Given a pointer (see above)
4129/// to an associated function myfunc, one can retrieve the function/fit
4130/// parameters with calls such as:
4131///
4132/// ~~~ {.cpp}
4133/// Double_t chi2 = myfunc->GetChisquare();
4134/// Double_t par0 = myfunc->GetParameter(0); //value of 1st parameter
4135/// Double_t err0 = myfunc->GetParError(0); //error on first parameter
4136/// ~~~
4137///
4138/// #### Access to the fit status
4139///
4140/// The status of the fit can be obtained converting the TFitResultPtr to an integer
4141/// independently if the fit option "S" is used or not:
4142///
4143/// ~~~ {.cpp}
4144/// TFitResultPtr r = h->Fit(myFunc,opt);
4145/// Int_t fitStatus = r;
4146/// ~~~
4147///
4148/// The fitStatus is 0 if the fit is OK (i.e no error occurred).
4149/// The value of the fit status code is negative in case of an error not connected with the
4150/// minimization procedure, for example when a wrong function is used.
4151/// Otherwise the return value is the one returned from the minimization procedure.
4152/// When TMinuit (default case) or Minuit2 are used as minimizer the status returned is :
4153/// `fitStatus = migradResult + 10*minosResult + 100*hesseResult + 1000*improveResult`.
4154/// TMinuit will return 0 (for migrad, minos, hesse or improve) in case of success and 4 in
4155/// case of error (see the documentation of TMinuit::mnexcm). So for example, for an error
4156/// only in Minos but not in Migrad a fitStatus of 40 will be returned.
4157/// Minuit2 will return also 0 in case of success and different values in migrad minos or
4158/// hesse depending on the error. See in this case the documentation of
4159/// Minuit2Minimizer::Minimize for the migradResult, Minuit2Minimizer::GetMinosError for the
4160/// minosResult and Minuit2Minimizer::Hesse for the hesseResult.
4161/// If other minimizers are used see their specific documentation for the status code returned.
4162/// For example in the case of Fumili, for the status returned see TFumili::Minimize.
4163///
4164/// #### Excluding points
4165///
4166/// Use TF1::RejectPoint inside your fitting function to exclude points
4167/// within a certain range from the fit. Example:
4168///
4169/// ~~~ {.cpp}
4170/// Double_t fline(Double_t *x, Double_t *par)
4171/// {
4172/// if (x[0] > 2.5 && x[0] < 3.5) {
4173/// TF1::RejectPoint();
4174/// return 0;
4175/// }
4176/// return par[0] + par[1]*x[0];
4177/// }
4178///
4179/// void exclude() {
4180/// TF1 *f1 = new TF1("f1", "[0] +[1]*x +gaus(2)", 0, 5);
4181/// f1->SetParameters(6, -1,5, 3, 0.2);
4182/// TH1F *h = new TH1F("h", "background + signal", 100, 0, 5);
4183/// h->FillRandom("f1", 2000);
4184/// TF1 *fline = new TF1("fline", fline, 0, 5, 2);
4185/// fline->SetParameters(2, -1);
4186/// h->Fit("fline", "l");
4187/// }
4188/// ~~~
4189///
4190/// #### Warning when using the option "0"
4191///
4192/// When selecting the option "0", the fitted function is added to
4193/// the list of functions of the histogram, but it is not drawn.
4194/// You can undo what you disabled in the following way:
4195///
4196/// ~~~ {.cpp}
4197/// h.Fit("myFunction", "0"); // fit, store function but do not draw
4198/// h.Draw(); function is not drawn
4199/// const Int_t kNotDraw = 1<<9;
4200/// h.GetFunction("myFunction")->ResetBit(kNotDraw);
4201/// h.Draw(); // function is visible again
4202/// ~~~
4203///
4204/// #### Access to the Minimizer information during fitting
4205///
4206/// This function calls, the ROOT::Fit::FitObject function implemented in HFitImpl.cxx
4207/// which uses the ROOT::Fit::Fitter class. The Fitter class creates the objective function
4208/// (e.g. chi2 or likelihood) and uses an implementation of the Minimizer interface for minimizing
4209/// the function.
4210/// The default minimizer is Minuit (class TMinuitMinimizer which calls TMinuit).
4211/// The default can be set in the resource file in etc/system.rootrc. For example
4212///
4213/// ~~~ {.cpp}
4214/// Root.Fitter: Minuit2
4215/// ~~~
4216///
4217/// A different fitter can also be set via ROOT::Math::MinimizerOptions::SetDefaultMinimizer
4218/// (or TVirtualFitter::SetDefaultFitter).
4219/// For example ROOT::Math::MinimizerOptions::SetDefaultMinimizer("GSLMultiMin","BFGS");
4220/// will set the usage of the BFGS algorithm of the GSL multi-dimensional minimization
4221/// (implemented in libMathMore). ROOT::Math::MinimizerOptions can be used also to set other
4222/// default options, like maximum number of function calls, minimization tolerance or print
4223/// level. See the documentation of this class.
4224///
4225/// For fitting linear functions (containing the "++" sign" and polN functions,
4226/// the linear fitter is automatically initialized.
4227
4228TFitResultPtr TH1::Fit(TF1 *f1 ,Option_t *option ,Option_t *goption, Double_t xxmin, Double_t xxmax)
4229{
4230 // implementation of Fit method is in file hist/src/HFitImpl.cxx
4231 Foption_t fitOption;
4233
4234 // create range and minimizer options with default values
4235 ROOT::Fit::DataRange range(xxmin,xxmax);
4237
4238 // need to empty the buffer before
4239 // (t.b.d. do a ML unbinned fit with buffer data)
4240 if (fBuffer) BufferEmpty();
4241
4242 return ROOT::Fit::FitObject(this, f1 , fitOption , minOption, goption, range);
4243}
4244
4245////////////////////////////////////////////////////////////////////////////////
4246/// Display a panel with all histogram fit options.
4247///
4248/// See class TFitPanel for example
4249
4250void TH1::FitPanel()
4251{
4252 if (!gPad)
4253 gROOT->MakeDefCanvas();
4254
4255 if (!gPad) {
4256 Error("FitPanel", "Unable to create a default canvas");
4257 return;
4258 }
4259
4260
4261 // use plugin manager to create instance of TFitEditor
4262 TPluginHandler *handler = gROOT->GetPluginManager()->FindHandler("TFitEditor");
4263 if (handler && handler->LoadPlugin() != -1) {
4264 if (handler->ExecPlugin(2, gPad, this) == 0)
4265 Error("FitPanel", "Unable to create the FitPanel");
4266 }
4267 else
4268 Error("FitPanel", "Unable to find the FitPanel plug-in");
4269}
4270
4271////////////////////////////////////////////////////////////////////////////////
4272/// Return a histogram containing the asymmetry of this histogram with h2,
4273/// where the asymmetry is defined as:
4274///
4275/// ~~~ {.cpp}
4276/// Asymmetry = (h1 - h2)/(h1 + h2) where h1 = this
4277/// ~~~
4278///
4279/// works for 1D, 2D, etc. histograms
4280/// c2 is an optional argument that gives a relative weight between the two
4281/// histograms, and dc2 is the error on this weight. This is useful, for example,
4282/// when forming an asymmetry between two histograms from 2 different data sets that
4283/// need to be normalized to each other in some way. The function calculates
4284/// the errors assuming Poisson statistics on h1 and h2 (that is, dh = sqrt(h)).
4285///
4286/// example: assuming 'h1' and 'h2' are already filled
4287///
4288/// ~~~ {.cpp}
4289/// h3 = h1->GetAsymmetry(h2)
4290/// ~~~
4291///
4292/// then 'h3' is created and filled with the asymmetry between 'h1' and 'h2';
4293/// h1 and h2 are left intact.
4294///
4295/// Note that it is the user's responsibility to manage the created histogram.
4296/// The name of the returned histogram will be `Asymmetry_nameOfh1-nameOfh2`
4297///
4298/// code proposed by Jason Seely (seely@mit.edu) and adapted by R.Brun
4299///
4300/// clone the histograms so top and bottom will have the
4301/// correct dimensions:
4302/// Sumw2 just makes sure the errors will be computed properly
4303/// when we form sums and ratios below.
4304
4306{
4307 TH1 *h1 = this;
4308 TString name = TString::Format("Asymmetry_%s-%s",h1->GetName(),h2->GetName() );
4309 TH1 *asym = (TH1*)Clone(name);
4310
4311 // set also the title
4312 TString title = TString::Format("(%s - %s)/(%s+%s)",h1->GetName(),h2->GetName(),h1->GetName(),h2->GetName() );
4313 asym->SetTitle(title);
4314
4315 asym->Sumw2();
4316 Bool_t addStatus = TH1::AddDirectoryStatus();
4318 TH1 *top = (TH1*)asym->Clone();
4319 TH1 *bottom = (TH1*)asym->Clone();
4320 TH1::AddDirectory(addStatus);
4321
4322 // form the top and bottom of the asymmetry, and then divide:
4323 top->Add(h1,h2,1,-c2);
4324 bottom->Add(h1,h2,1,c2);
4325 asym->Divide(top,bottom);
4326
4327 Int_t xmax = asym->GetNbinsX();
4328 Int_t ymax = asym->GetNbinsY();
4329 Int_t zmax = asym->GetNbinsZ();
4330
4331 if (h1->fBuffer) h1->BufferEmpty(1);
4332 if (h2->fBuffer) h2->BufferEmpty(1);
4333 if (bottom->fBuffer) bottom->BufferEmpty(1);
4334
4335 // now loop over bins to calculate the correct errors
4336 // the reason this error calculation looks complex is because of c2
4337 for(Int_t i=1; i<= xmax; i++){
4338 for(Int_t j=1; j<= ymax; j++){
4339 for(Int_t k=1; k<= zmax; k++){
4340 Int_t bin = GetBin(i, j, k);
4341 // here some bin contents are written into variables to make the error
4342 // calculation a little more legible:
4344 Double_t b = h2->RetrieveBinContent(bin);
4345 Double_t bot = bottom->RetrieveBinContent(bin);
4346
4347 // make sure there are some events, if not, then the errors are set = 0
4348 // automatically.
4349 //if(bot < 1){} was changed to the next line from recommendation of Jason Seely (28 Nov 2005)
4350 if(bot < 1e-6){}
4351 else{
4352 // computation of errors by Christos Leonidopoulos
4353 Double_t dasq = h1->GetBinErrorSqUnchecked(bin);
4354 Double_t dbsq = h2->GetBinErrorSqUnchecked(bin);
4355 Double_t error = 2*TMath::Sqrt(a*a*c2*c2*dbsq + c2*c2*b*b*dasq+a*a*b*b*dc2*dc2)/(bot*bot);
4356 asym->SetBinError(i,j,k,error);
4357 }
4358 }
4359 }
4360 }
4361 delete top;
4362 delete bottom;
4363
4364 return asym;
4365}
4366
4367////////////////////////////////////////////////////////////////////////////////
4368/// Static function
4369/// return the default buffer size for automatic histograms
4370/// the parameter fgBufferSize may be changed via SetDefaultBufferSize
4371
4373{
4374 return fgBufferSize;
4375}
4376
4377////////////////////////////////////////////////////////////////////////////////
4378/// Return kTRUE if TH1::Sumw2 must be called when creating new histograms.
4379/// see TH1::SetDefaultSumw2.
4380
4382{
4383 return fgDefaultSumw2;
4384}
4385
4386////////////////////////////////////////////////////////////////////////////////
4387/// Return the current number of entries.
4388
4390{
4391 if (fBuffer) {
4392 Int_t nentries = (Int_t) fBuffer[0];
4393 if (nentries > 0) return nentries;
4394 }
4395
4396 return fEntries;
4397}
4398
4399////////////////////////////////////////////////////////////////////////////////
4400/// Number of effective entries of the histogram.
4401///
4402/// \f[
4403/// neff = \frac{(\sum Weights )^2}{(\sum Weight^2 )}
4404/// \f]
4405///
4406/// In case of an unweighted histogram this number is equivalent to the
4407/// number of entries of the histogram.
4408/// For a weighted histogram, this number corresponds to the hypothetical number of unweighted entries
4409/// a histogram would need to have the same statistical power as this weighted histogram.
4410/// Note: The underflow/overflow are included if one has set the TH1::StatOverFlows flag
4411/// and if the statistics has been computed at filling time.
4412/// If a range is set in the histogram the number is computed from the given range.
4413
4415{
4416 Stat_t s[kNstat];
4417 this->GetStats(s);// s[1] sum of squares of weights, s[0] sum of weights
4418 return (s[1] ? s[0]*s[0]/s[1] : TMath::Abs(s[0]) );
4419}
4420
4421////////////////////////////////////////////////////////////////////////////////
4422/// Set highlight (enable/disable) mode for the histogram
4423/// by default highlight mode is disable
4424
4425void TH1::SetHighlight(Bool_t set)
4426{
4427 if (IsHighlight() == set) return;
4428 if (fDimension > 2) {
4429 Info("SetHighlight", "Supported only 1-D or 2-D histograms");
4430 return;
4431 }
4432
4433 if (!fPainter) {
4434 Info("SetHighlight", "Need to draw histogram first");
4435 return;
4436 }
4437 SetBit(kIsHighlight, set);
4439}
4440
4441////////////////////////////////////////////////////////////////////////////////
4442/// Redefines TObject::GetObjectInfo.
4443/// Displays the histogram info (bin number, contents, integral up to bin
4444/// corresponding to cursor position px,py
4445
4446char *TH1::GetObjectInfo(Int_t px, Int_t py) const
4447{
4448 return ((TH1*)this)->GetPainter()->GetObjectInfo(px,py);
4449}
4450
4451////////////////////////////////////////////////////////////////////////////////
4452/// Return pointer to painter.
4453/// If painter does not exist, it is created
4454
4456{
4457 if (!fPainter) {
4458 TString opt = option;
4459 opt.ToLower();
4460 if (opt.Contains("gl") || gStyle->GetCanvasPreferGL()) {
4461 //try to create TGLHistPainter
4462 TPluginHandler *handler = gROOT->GetPluginManager()->FindHandler("TGLHistPainter");
4463
4464 if (handler && handler->LoadPlugin() != -1)
4465 fPainter = reinterpret_cast<TVirtualHistPainter *>(handler->ExecPlugin(1, this));
4466 }
4467 }
4468
4470
4471 return fPainter;
4472}
4473
4474////////////////////////////////////////////////////////////////////////////////
4475/// Compute Quantiles for this histogram
4476/// Quantile x_q of a probability distribution Function F is defined as
4477///
4478/// ~~~ {.cpp}
4479/// F(x_q) = q with 0 <= q <= 1.
4480/// ~~~
4481///
4482/// For instance the median x_0.5 of a distribution is defined as that value
4483/// of the random variable for which the distribution function equals 0.5:
4484///
4485/// ~~~ {.cpp}
4486/// F(x_0.5) = Probability(x < x_0.5) = 0.5
4487/// ~~~
4488///
4489/// code from Eddy Offermann, Renaissance
4490///
4491/// \param[in] nprobSum maximum size of array q and size of array probSum (if given)
4492/// \param[in] probSum array of positions where quantiles will be computed.
4493/// - if probSum is null, probSum will be computed internally and will
4494/// have a size = number of bins + 1 in h. it will correspond to the
4495/// quantiles calculated at the lowest edge of the histogram (quantile=0) and
4496/// all the upper edges of the bins.
4497/// - if probSum is not null, it is assumed to contain at least nprobSum values.
4498/// \param[out] q array q filled with nq quantiles
4499/// \return value nq (<=nprobSum) with the number of quantiles computed
4500///
4501/// Note that the Integral of the histogram is automatically recomputed
4502/// if the number of entries is different of the number of entries when
4503/// the integral was computed last time. In case you do not use the Fill
4504/// functions to fill your histogram, but SetBinContent, you must call
4505/// TH1::ComputeIntegral before calling this function.
4506///
4507/// Getting quantiles q from two histograms and storing results in a TGraph,
4508/// a so-called QQ-plot
4509///
4510/// ~~~ {.cpp}
4511/// TGraph *gr = new TGraph(nprob);
4512/// h1->GetQuantiles(nprob,gr->GetX());
4513/// h2->GetQuantiles(nprob,gr->GetY());
4514/// gr->Draw("alp");
4515/// ~~~
4516///
4517/// Example:
4518///
4519/// ~~~ {.cpp}
4520/// void quantiles() {
4521/// // demo for quantiles
4522/// const Int_t nq = 20;
4523/// TH1F *h = new TH1F("h","demo quantiles",100,-3,3);
4524/// h->FillRandom("gaus",5000);
4525///
4526/// Double_t xq[nq]; // position where to compute the quantiles in [0,1]
4527/// Double_t yq[nq]; // array to contain the quantiles
4528/// for (Int_t i=0;i<nq;i++) xq[i] = Float_t(i+1)/nq;
4529/// h->GetQuantiles(nq,yq,xq);
4530///
4531/// //show the original histogram in the top pad
4532/// TCanvas *c1 = new TCanvas("c1","demo quantiles",10,10,700,900);
4533/// c1->Divide(1,2);
4534/// c1->cd(1);
4535/// h->Draw();
4536///
4537/// // show the quantiles in the bottom pad
4538/// c1->cd(2);
4539/// gPad->SetGrid();
4540/// TGraph *gr = new TGraph(nq,xq,yq);
4541/// gr->SetMarkerStyle(21);
4542/// gr->Draw("alp");
4543/// }
4544/// ~~~
4545
4546Int_t TH1::GetQuantiles(Int_t nprobSum, Double_t *q, const Double_t *probSum)
4547{
4548 if (GetDimension() > 1) {
4549 Error("GetQuantiles","Only available for 1-d histograms");
4550 return 0;
4551 }
4552
4553 const Int_t nbins = GetXaxis()->GetNbins();
4554 if (!fIntegral) ComputeIntegral();
4555 if (fIntegral[nbins+1] != fEntries) ComputeIntegral();
4556
4557 Int_t i, ibin;
4558 Double_t *prob = (Double_t*)probSum;
4559 Int_t nq = nprobSum;
4560 if (probSum == 0) {
4561 nq = nbins+1;
4562 prob = new Double_t[nq];
4563 prob[0] = 0;
4564 for (i=1;i<nq;i++) {
4565 prob[i] = fIntegral[i]/fIntegral[nbins];
4566 }
4567 }
4568
4569 for (i = 0; i < nq; i++) {
4570 ibin = TMath::BinarySearch(nbins,fIntegral,prob[i]);
4571 while (ibin < nbins-1 && fIntegral[ibin+1] == prob[i]) {
4572 if (fIntegral[ibin+2] == prob[i]) ibin++;
4573 else break;
4574 }
4575 q[i] = GetBinLowEdge(ibin+1);
4576 const Double_t dint = fIntegral[ibin+1]-fIntegral[ibin];
4577 if (dint > 0) q[i] += GetBinWidth(ibin+1)*(prob[i]-fIntegral[ibin])/dint;
4578 }
4579
4580 if (!probSum) delete [] prob;
4581 return nq;
4582}
4583
4584////////////////////////////////////////////////////////////////////////////////
4585/// Decode string choptin and fill fitOption structure.
4586
4587Int_t TH1::FitOptionsMake(Option_t *choptin, Foption_t &fitOption)
4588{
4590 return 1;
4591}
4592
4593////////////////////////////////////////////////////////////////////////////////
4594/// Compute Initial values of parameters for a gaussian.
4595
4596void H1InitGaus()
4597{
4598 Double_t allcha, sumx, sumx2, x, val, stddev, mean;
4599 Int_t bin;
4600 const Double_t sqrtpi = 2.506628;
4601
4602 // - Compute mean value and StdDev of the histogram in the given range
4604 TH1 *curHist = (TH1*)hFitter->GetObjectFit();
4605 Int_t hxfirst = hFitter->GetXfirst();
4606 Int_t hxlast = hFitter->GetXlast();
4607 Double_t valmax = curHist->GetBinContent(hxfirst);
4608 Double_t binwidx = curHist->GetBinWidth(hxfirst);
4609 allcha = sumx = sumx2 = 0;
4610 for (bin=hxfirst;bin<=hxlast;bin++) {
4611 x = curHist->GetBinCenter(bin);
4612 val = TMath::Abs(curHist->GetBinContent(bin));
4613 if (val > valmax) valmax = val;
4614 sumx += val*x;
4615 sumx2 += val*x*x;
4616 allcha += val;
4617 }
4618 if (allcha == 0) return;
4619 mean = sumx/allcha;
4620 stddev = sumx2/allcha - mean*mean;
4621 if (stddev > 0) stddev = TMath::Sqrt(stddev);
4622 else stddev = 0;
4623 if (stddev == 0) stddev = binwidx*(hxlast-hxfirst+1)/4;
4624 //if the distribution is really gaussian, the best approximation
4625 //is binwidx*allcha/(sqrtpi*stddev)
4626 //However, in case of non-gaussian tails, this underestimates
4627 //the normalisation constant. In this case the maximum value
4628 //is a better approximation.
4629 //We take the average of both quantities
4630 Double_t constant = 0.5*(valmax+binwidx*allcha/(sqrtpi*stddev));
4631
4632 //In case the mean value is outside the histo limits and
4633 //the StdDev is bigger than the range, we take
4634 // mean = center of bins
4635 // stddev = half range
4636 Double_t xmin = curHist->GetXaxis()->GetXmin();
4637 Double_t xmax = curHist->GetXaxis()->GetXmax();
4638 if ((mean < xmin || mean > xmax) && stddev > (xmax-xmin)) {
4639 mean = 0.5*(xmax+xmin);
4640 stddev = 0.5*(xmax-xmin);
4641 }
4642 TF1 *f1 = (TF1*)hFitter->GetUserFunc();
4643 f1->SetParameter(0,constant);
4644 f1->SetParameter(1,mean);
4645 f1->SetParameter(2,stddev);
4646 f1->SetParLimits(2,0,10*stddev);
4647}
4648
4649////////////////////////////////////////////////////////////////////////////////
4650/// Compute Initial values of parameters for an exponential.
4651
4652void H1InitExpo()
4653{
4654 Double_t constant, slope;
4655 Int_t ifail;
4657 Int_t hxfirst = hFitter->GetXfirst();
4658 Int_t hxlast = hFitter->GetXlast();
4659 Int_t nchanx = hxlast - hxfirst + 1;
4660
4661 H1LeastSquareLinearFit(-nchanx, constant, slope, ifail);
4662
4663 TF1 *f1 = (TF1*)hFitter->GetUserFunc();
4664 f1->SetParameter(0,constant);
4665 f1->SetParameter(1,slope);
4666
4667}
4668
4669////////////////////////////////////////////////////////////////////////////////
4670/// Compute Initial values of parameters for a polynom.
4671
4672void H1InitPolynom()
4673{
4674 Double_t fitpar[25];
4675
4677 TF1 *f1 = (TF1*)hFitter->GetUserFunc();
4678 Int_t hxfirst = hFitter->GetXfirst();
4679 Int_t hxlast = hFitter->GetXlast();
4680 Int_t nchanx = hxlast - hxfirst + 1;
4681 Int_t npar = f1->GetNpar();
4682
4683 if (nchanx <=1 || npar == 1) {
4684 TH1 *curHist = (TH1*)hFitter->GetObjectFit();
4685 fitpar[0] = curHist->GetSumOfWeights()/Double_t(nchanx);
4686 } else {
4687 H1LeastSquareFit( nchanx, npar, fitpar);
4688 }
4689 for (Int_t i=0;i<npar;i++) f1->SetParameter(i, fitpar[i]);
4690}
4691
4692////////////////////////////////////////////////////////////////////////////////
4693/// Least squares lpolynomial fitting without weights.
4694///
4695/// \param[in] n number of points to fit
4696/// \param[in] m number of parameters
4697/// \param[in] a array of parameters
4698///
4699/// based on CERNLIB routine LSQ: Translated to C++ by Rene Brun
4700/// (E.Keil. revised by B.Schorr, 23.10.1981.)
4701
4703{
4704 const Double_t zero = 0.;
4705 const Double_t one = 1.;
4706 const Int_t idim = 20;
4707
4708 Double_t b[400] /* was [20][20] */;
4709 Int_t i, k, l, ifail;
4710 Double_t power;
4711 Double_t da[20], xk, yk;
4712
4713 if (m <= 2) {
4714 H1LeastSquareLinearFit(n, a[0], a[1], ifail);
4715 return;
4716 }
4717 if (m > idim || m > n) return;
4718 b[0] = Double_t(n);
4719 da[0] = zero;
4720 for (l = 2; l <= m; ++l) {
4721 b[l-1] = zero;
4722 b[m + l*20 - 21] = zero;
4723 da[l-1] = zero;
4724 }
4726 TH1 *curHist = (TH1*)hFitter->GetObjectFit();
4727 Int_t hxfirst = hFitter->GetXfirst();
4728 Int_t hxlast = hFitter->GetXlast();
4729 for (k = hxfirst; k <= hxlast; ++k) {
4730 xk = curHist->GetBinCenter(k);
4731 yk = curHist->GetBinContent(k);
4732 power = one;
4733 da[0] += yk;
4734 for (l = 2; l <= m; ++l) {
4735 power *= xk;
4736 b[l-1] += power;
4737 da[l-1] += power*yk;
4738 }
4739 for (l = 2; l <= m; ++l) {
4740 power *= xk;
4741 b[m + l*20 - 21] += power;
4742 }
4743 }
4744 for (i = 3; i <= m; ++i) {
4745 for (k = i; k <= m; ++k) {
4746 b[k - 1 + (i-1)*20 - 21] = b[k + (i-2)*20 - 21];
4747 }
4748 }
4749 H1LeastSquareSeqnd(m, b, idim, ifail, 1, da);
4750
4751 for (i=0; i<m; ++i) a[i] = da[i];
4752
4753}
4754
4755////////////////////////////////////////////////////////////////////////////////
4756/// Least square linear fit without weights.
4757///
4758/// extracted from CERNLIB LLSQ: Translated to C++ by Rene Brun
4759/// (added to LSQ by B. Schorr, 15.02.1982.)
4760
4761void H1LeastSquareLinearFit(Int_t ndata, Double_t &a0, Double_t &a1, Int_t &ifail)
4762{
4763 Double_t xbar, ybar, x2bar;
4764 Int_t i, n;
4765 Double_t xybar;
4766 Double_t fn, xk, yk;
4767 Double_t det;
4768
4769 n = TMath::Abs(ndata);
4770 ifail = -2;
4771 xbar = ybar = x2bar = xybar = 0;
4773 TH1 *curHist = (TH1*)hFitter->GetObjectFit();
4774 Int_t hxfirst = hFitter->GetXfirst();
4775 Int_t hxlast = hFitter->GetXlast();
4776 for (i = hxfirst; i <= hxlast; ++i) {
4777 xk = curHist->GetBinCenter(i);
4778 yk = curHist->GetBinContent(i);
4779 if (ndata < 0) {
4780 if (yk <= 0) yk = 1e-9;
4781 yk = TMath::Log(yk);
4782 }
4783 xbar += xk;
4784 ybar += yk;
4785 x2bar += xk*xk;
4786 xybar += xk*yk;
4787 }
4788 fn = Double_t(n);
4789 det = fn*x2bar - xbar*xbar;
4790 ifail = -1;
4791 if (det <= 0) {
4792 a0 = ybar/fn;
4793 a1 = 0;
4794 return;
4795 }
4796 ifail = 0;
4797 a0 = (x2bar*ybar - xbar*xybar) / det;
4798 a1 = (fn*xybar - xbar*ybar) / det;
4799
4800}
4801
4802////////////////////////////////////////////////////////////////////////////////
4803/// Extracted from CERN Program library routine DSEQN.
4804///
4805/// Translated to C++ by Rene Brun
4806
4807void H1LeastSquareSeqnd(Int_t n, Double_t *a, Int_t idim, Int_t &ifail, Int_t k, Double_t *b)
4808{
4809 Int_t a_dim1, a_offset, b_dim1, b_offset;
4810 Int_t nmjp1, i, j, l;
4811 Int_t im1, jp1, nm1, nmi;
4812 Double_t s1, s21, s22;
4813 const Double_t one = 1.;
4814
4815 /* Parameter adjustments */
4816 b_dim1 = idim;
4817 b_offset = b_dim1 + 1;
4818 b -= b_offset;
4819 a_dim1 = idim;
4820 a_offset = a_dim1 + 1;
4821 a -= a_offset;
4822
4823 if (idim < n) return;
4824
4825 ifail = 0;
4826 for (j = 1; j <= n; ++j) {
4827 if (a[j + j*a_dim1] <= 0) { ifail = -1; return; }
4828 a[j + j*a_dim1] = one / a[j + j*a_dim1];
4829 if (j == n) continue;
4830 jp1 = j + 1;
4831 for (l = jp1; l <= n; ++l) {
4832 a[j + l*a_dim1] = a[j + j*a_dim1] * a[l + j*a_dim1];
4833 s1 = -a[l + (j+1)*a_dim1];
4834 for (i = 1; i <= j; ++i) { s1 = a[l + i*a_dim1] * a[i + (j+1)*a_dim1] + s1; }
4835 a[l + (j+1)*a_dim1] = -s1;
4836 }
4837 }
4838 if (k <= 0) return;
4839
4840 for (l = 1; l <= k; ++l) {
4841 b[l*b_dim1 + 1] = a[a_dim1 + 1]*b[l*b_dim1 + 1];
4842 }
4843 if (n == 1) return;
4844 for (l = 1; l <= k; ++l) {
4845 for (i = 2; i <= n; ++i) {
4846 im1 = i - 1;
4847 s21 = -b[i + l*b_dim1];
4848 for (j = 1; j <= im1; ++j) {
4849 s21 = a[i + j*a_dim1]*b[j + l*b_dim1] + s21;
4850 }
4851 b[i + l*b_dim1] = -a[i + i*a_dim1]*s21;
4852 }
4853 nm1 = n - 1;
4854 for (i = 1; i <= nm1; ++i) {
4855 nmi = n - i;
4856 s22 = -b[nmi + l*b_dim1];
4857 for (j = 1; j <= i; ++j) {
4858 nmjp1 = n - j + 1;
4859 s22 = a[nmi + nmjp1*a_dim1]*b[nmjp1 + l*b_dim1] + s22;
4860 }
4861 b[nmi + l*b_dim1] = -s22;
4862 }
4863 }
4864}
4865
4866////////////////////////////////////////////////////////////////////////////////
4867/// Return Global bin number corresponding to binx,y,z.
4868///
4869/// 2-D and 3-D histograms are represented with a one dimensional
4870/// structure.
4871/// This has the advantage that all existing functions, such as
4872/// GetBinContent, GetBinError, GetBinFunction work for all dimensions.
4873///
4874/// In case of a TH1x, returns binx directly.
4875/// see TH1::GetBinXYZ for the inverse transformation.
4876///
4877/// Convention for numbering bins
4878///
4879/// For all histogram types: nbins, xlow, xup
4880///
4881/// - bin = 0; underflow bin
4882/// - bin = 1; first bin with low-edge xlow INCLUDED
4883/// - bin = nbins; last bin with upper-edge xup EXCLUDED
4884/// - bin = nbins+1; overflow bin
4885///
4886/// In case of 2-D or 3-D histograms, a "global bin" number is defined.
4887/// For example, assuming a 3-D histogram with binx,biny,binz, the function
4888///
4889/// ~~~ {.cpp}
4890/// Int_t bin = h->GetBin(binx,biny,binz);
4891/// ~~~
4892///
4893/// returns a global/linearized bin number. This global bin is useful
4894/// to access the bin information independently of the dimension.
4895
4896Int_t TH1::GetBin(Int_t binx, Int_t, Int_t) const
4897{
4898 Int_t ofx = fXaxis.GetNbins() + 1; // overflow bin
4899 if (binx < 0) binx = 0;
4900 if (binx > ofx) binx = ofx;
4901
4902 return binx;
4903}
4904
4905////////////////////////////////////////////////////////////////////////////////
4906/// Return binx, biny, binz corresponding to the global bin number globalbin
4907/// see TH1::GetBin function above
4908
4909void TH1::GetBinXYZ(Int_t binglobal, Int_t &binx, Int_t &biny, Int_t &binz) const
4910{
4911 Int_t nx = fXaxis.GetNbins()+2;
4912 Int_t ny = fYaxis.GetNbins()+2;
4913
4914 if (GetDimension() == 1) {
4915 binx = binglobal%nx;
4916 biny = 0;
4917 binz = 0;
4918 return;
4919 }
4920 if (GetDimension() == 2) {
4921 binx = binglobal%nx;
4922 biny = ((binglobal-binx)/nx)%ny;
4923 binz = 0;
4924 return;
4925 }
4926 if (GetDimension() == 3) {
4927 binx = binglobal%nx;
4928 biny = ((binglobal-binx)/nx)%ny;
4929 binz = ((binglobal-binx)/nx -biny)/ny;
4930 }
4931}
4932
4933////////////////////////////////////////////////////////////////////////////////
4934/// Return a random number distributed according the histogram bin contents.
4935/// This function checks if the bins integral exists. If not, the integral
4936/// is evaluated, normalized to one.
4937///
4938/// @param rng (optional) Random number generator pointer used (default is gRandom)
4939///
4940/// The integral is automatically recomputed if the number of entries
4941/// is not the same then when the integral was computed.
4942/// NB Only valid for 1-d histograms. Use GetRandom2 or 3 otherwise.
4943/// If the histogram has a bin with negative content a NaN is returned
4944
4945Double_t TH1::GetRandom(TRandom * rng) const
4946{
4947 if (fDimension > 1) {
4948 Error("GetRandom","Function only valid for 1-d histograms");
4949 return 0;
4950 }
4951 Int_t nbinsx = GetNbinsX();
4952 Double_t integral = 0;
4953 // compute integral checking that all bins have positive content (see ROOT-5894)
4954 if (fIntegral) {
4955 if (fIntegral[nbinsx+1] != fEntries) integral = ((TH1*)this)->ComputeIntegral(true);
4956 else integral = fIntegral[nbinsx];
4957 } else {
4958 integral = ((TH1*)this)->ComputeIntegral(true);
4959 }
4960 if (integral == 0) return 0;
4961 // return a NaN in case some bins have negative content
4962 if (integral == TMath::QuietNaN() ) return TMath::QuietNaN();
4963
4964 Double_t r1 = (rng) ? rng->Rndm() : gRandom->Rndm();
4965 Int_t ibin = TMath::BinarySearch(nbinsx,fIntegral,r1);
4966 Double_t x = GetBinLowEdge(ibin+1);
4967 if (r1 > fIntegral[ibin]) x +=
4968 GetBinWidth(ibin+1)*(r1-fIntegral[ibin])/(fIntegral[ibin+1] - fIntegral[ibin]);
4969 return x;
4970}
4971
4972////////////////////////////////////////////////////////////////////////////////
4973/// Return content of bin number bin.
4974///
4975/// Implemented in TH1C,S,F,D
4976///
4977/// Convention for numbering bins
4978///
4979/// For all histogram types: nbins, xlow, xup
4980///
4981/// - bin = 0; underflow bin
4982/// - bin = 1; first bin with low-edge xlow INCLUDED
4983/// - bin = nbins; last bin with upper-edge xup EXCLUDED
4984/// - bin = nbins+1; overflow bin
4985///
4986/// In case of 2-D or 3-D histograms, a "global bin" number is defined.
4987/// For example, assuming a 3-D histogram with binx,biny,binz, the function
4988///
4989/// ~~~ {.cpp}
4990/// Int_t bin = h->GetBin(binx,biny,binz);
4991/// ~~~
4992///
4993/// returns a global/linearized bin number. This global bin is useful
4994/// to access the bin information independently of the dimension.
4995
4997{
4998 if (fBuffer) const_cast<TH1*>(this)->BufferEmpty();
4999 if (bin < 0) bin = 0;
5000 if (bin >= fNcells) bin = fNcells-1;
5001
5002 return RetrieveBinContent(bin);
5003}
5004
5005////////////////////////////////////////////////////////////////////////////////
5006/// Compute first binx in the range [firstx,lastx] for which
5007/// diff = abs(bin_content-c) <= maxdiff
5008///
5009/// In case several bins in the specified range with diff=0 are found
5010/// the first bin found is returned in binx.
5011/// In case several bins in the specified range satisfy diff <=maxdiff
5012/// the bin with the smallest difference is returned in binx.
5013/// In all cases the function returns the smallest difference.
5014///
5015/// NOTE1: if firstx <= 0, firstx is set to bin 1
5016/// if (lastx < firstx then firstx is set to the number of bins
5017/// ie if firstx=0 and lastx=0 (default) the search is on all bins.
5018///
5019/// NOTE2: if maxdiff=0 (default), the first bin with content=c is returned.
5020
5021Double_t TH1::GetBinWithContent(Double_t c, Int_t &binx, Int_t firstx, Int_t lastx,Double_t maxdiff) const
5022{
5023 if (fDimension > 1) {
5024 binx = 0;
5025 Error("GetBinWithContent","function is only valid for 1-D histograms");
5026 return 0;
5027 }
5028
5029 if (fBuffer) ((TH1*)this)->BufferEmpty();
5030
5031 if (firstx <= 0) firstx = 1;
5032 if (lastx < firstx) lastx = fXaxis.GetNbins();
5033 Int_t binminx = 0;
5034 Double_t diff, curmax = 1.e240;
5035 for (Int_t i=firstx;i<=lastx;i++) {
5036 diff = TMath::Abs(RetrieveBinContent(i)-c);
5037 if (diff <= 0) {binx = i; return diff;}
5038 if (diff < curmax && diff <= maxdiff) {curmax = diff, binminx=i;}
5039 }
5040 binx = binminx;
5041 return curmax;
5042}
5043
5044////////////////////////////////////////////////////////////////////////////////
5045/// Given a point x, approximates the value via linear interpolation
5046/// based on the two nearest bin centers
5047///
5048/// Andy Mastbaum 10/21/08
5049
5051{
5052 if (fBuffer) ((TH1*)this)->BufferEmpty();
5053
5054 Int_t xbin = fXaxis.FindFixBin(x);
5055 Double_t x0,x1,y0,y1;
5056
5057 if(x<=GetBinCenter(1)) {
5058 return RetrieveBinContent(1);
5059 } else if(x>=GetBinCenter(GetNbinsX())) {
5060 return RetrieveBinContent(GetNbinsX());
5061 } else {
5062 if(x<=GetBinCenter(xbin)) {
5063 y0 = RetrieveBinContent(xbin-1);
5064 x0 = GetBinCenter(xbin-1);
5065 y1 = RetrieveBinContent(xbin);
5066 x1 = GetBinCenter(xbin);
5067 } else {
5068 y0 = RetrieveBinContent(xbin);
5069 x0 = GetBinCenter(xbin);
5070 y1 = RetrieveBinContent(xbin+1);
5071 x1 = GetBinCenter(xbin+1);
5072 }
5073 return y0 + (x-x0)*((y1-y0)/(x1-x0));
5074 }
5075}
5076
5077////////////////////////////////////////////////////////////////////////////////
5078/// 2d Interpolation. Not yet implemented.
5079
5081{
5082 Error("Interpolate","This function must be called with 1 argument for a TH1");
5083 return 0;
5084}
5085
5086////////////////////////////////////////////////////////////////////////////////
5087/// 3d Interpolation. Not yet implemented.
5088
5090{
5091 Error("Interpolate","This function must be called with 1 argument for a TH1");
5092 return 0;
5093}
5094
5095///////////////////////////////////////////////////////////////////////////////
5096/// Check if a histogram is empty
5097/// (this is a protected method used mainly by TH1Merger )
5098
5099Bool_t TH1::IsEmpty() const
5100{
5101 // if fTsumw or fentries are not zero histogram is not empty
5102 // need to use GetEntries() instead of fEntries in case of bugger histograms
5103 // so we will flash the buffer
5104 if (fTsumw != 0) return kFALSE;
5105 if (GetEntries() != 0) return kFALSE;
5106 // case fTSumw == 0 amd entries are also zero
5107 // this should not really happening, but if one sets content by hand
5108 // it can happen. a call to ResetStats() should be done in such cases
5109 double sumw = 0;
5110 for (int i = 0; i< GetNcells(); ++i) sumw += RetrieveBinContent(i);
5111 return (sumw != 0) ? kFALSE : kTRUE;
5112}
5113
5114////////////////////////////////////////////////////////////////////////////////
5115/// Return true if the bin is overflow.
5116
5117Bool_t TH1::IsBinOverflow(Int_t bin, Int_t iaxis) const
5118{
5119 Int_t binx, biny, binz;
5120 GetBinXYZ(bin, binx, biny, binz);
5121
5122 if (iaxis == 0) {
5123 if ( fDimension == 1 )
5124 return binx >= GetNbinsX() + 1;
5125 if ( fDimension == 2 )
5126 return (binx >= GetNbinsX() + 1) ||
5127 (biny >= GetNbinsY() + 1);
5128 if ( fDimension == 3 )
5129 return (binx >= GetNbinsX() + 1) ||
5130 (biny >= GetNbinsY() + 1) ||
5131 (binz >= GetNbinsZ() + 1);
5132 return kFALSE;
5133 }
5134 if (iaxis == 1)
5135 return binx >= GetNbinsX() + 1;
5136 if (iaxis == 2)
5137 return biny >= GetNbinsY() + 1;
5138 if (iaxis == 3)
5139 return binz >= GetNbinsZ() + 1;
5140
5141 Error("IsBinOverflow","Invalid axis value");
5142 return kFALSE;
5143}
5144
5145////////////////////////////////////////////////////////////////////////////////
5146/// Return true if the bin is underflow.
5147/// If iaxis = 0 make OR with all axes otherwise check only for the given axis
5148
5149Bool_t TH1::IsBinUnderflow(Int_t bin, Int_t iaxis) const
5150{
5151 Int_t binx, biny, binz;
5152 GetBinXYZ(bin, binx, biny, binz);
5153
5154 if (iaxis == 0) {
5155 if ( fDimension == 1 )
5156 return (binx <= 0);
5157 else if ( fDimension == 2 )
5158 return (binx <= 0 || biny <= 0);
5159 else if ( fDimension == 3 )
5160 return (binx <= 0 || biny <= 0 || binz <= 0);
5161 else
5162 return kFALSE;
5163 }
5164 if (iaxis == 1)
5165 return (binx <= 0);
5166 if (iaxis == 2)
5167 return (biny <= 0);
5168 if (iaxis == 3)
5169 return (binz <= 0);
5170
5171 Error("IsBinUnderflow","Invalid axis value");
5172 return kFALSE;
5173}
5174
5175////////////////////////////////////////////////////////////////////////////////
5176/// Reduce the number of bins for the axis passed in the option to the number of bins having a label.
5177/// The method will remove only the extra bins existing after the last "labeled" bin.
5178/// Note that if there are "un-labeled" bins present between "labeled" bins they will not be removed
5179
5181{
5182 Int_t iaxis = AxisChoice(ax);
5183 TAxis *axis = 0;
5184 if (iaxis == 1) axis = GetXaxis();
5185 if (iaxis == 2) axis = GetYaxis();
5186 if (iaxis == 3) axis = GetZaxis();
5187 if (!axis) {
5188 Error("LabelsDeflate","Invalid axis option %s",ax);
5189 return;
5190 }
5191 if (!axis->GetLabels()) return;
5192
5193 // find bin with last labels
5194 // bin number is object ID in list of labels
5195 // therefore max bin number is number of bins of the deflated histograms
5196 TIter next(axis->GetLabels());
5197 TObject *obj;
5198 Int_t nbins = 0;
5199 while ((obj = next())) {
5200 Int_t ibin = obj->GetUniqueID();
5201 if (ibin > nbins) nbins = ibin;
5202 }
5203 if (nbins < 1) nbins = 1;
5204
5205 // Do nothing in case it was the last bin
5206 if (nbins==axis->GetNbins()) return;
5207
5208 TH1 *hold = (TH1*)IsA()->New();
5209 R__ASSERT(hold);
5210 hold->SetDirectory(0);
5211 Copy(*hold);
5212
5213 Bool_t timedisp = axis->GetTimeDisplay();
5214 Double_t xmin = axis->GetXmin();
5215 Double_t xmax = axis->GetBinUpEdge(nbins);
5216 if (xmax <= xmin) xmax = xmin +nbins;
5217 axis->SetRange(0,0);
5218 axis->Set(nbins,xmin,xmax);
5219 SetBinsLength(-1); // reset the number of cells
5220 Int_t errors = fSumw2.fN;
5221 if (errors) fSumw2.Set(fNcells);
5222 axis->SetTimeDisplay(timedisp);
5223 // reset histogram content
5224 Reset("ICE");
5225
5226 //now loop on all bins and refill
5227 // NOTE that if the bins without labels have content
5228 // it will be put in the underflow/overflow.
5229 // For this reason we use AddBinContent method
5230 Double_t oldEntries = fEntries;
5231 Int_t bin,binx,biny,binz;
5232 for (bin=0; bin < hold->fNcells; ++bin) {
5233 hold->GetBinXYZ(bin,binx,biny,binz);
5234 Int_t ibin = GetBin(binx,biny,binz);
5235 Double_t cu = hold->RetrieveBinContent(bin);
5236 AddBinContent(ibin,cu);
5237 if (errors) {
5238 fSumw2.fArray[ibin] += hold->fSumw2.fArray[bin];
5239 }
5240 }
5241 fEntries = oldEntries;
5242 delete hold;
5243}
5244
5245////////////////////////////////////////////////////////////////////////////////
5246/// Double the number of bins for axis.
5247/// Refill histogram.
5248/// This function is called by TAxis::FindBin(const char *label)
5249
5251{
5252 Int_t iaxis = AxisChoice(ax);
5253 TAxis *axis = 0;
5254 if (iaxis == 1) axis = GetXaxis();
5255 if (iaxis == 2) axis = GetYaxis();
5256 if (iaxis == 3) axis = GetZaxis();
5257 if (!axis) return;
5258
5259 TH1 *hold = (TH1*)IsA()->New();
5260 hold->SetDirectory(0);
5261 Copy(*hold);
5262 hold->ResetBit(kMustCleanup);
5263
5264 Bool_t timedisp = axis->GetTimeDisplay();
5265 Int_t nbins = axis->GetNbins();
5266 Double_t xmin = axis->GetXmin();
5267 Double_t xmax = axis->GetXmax();
5268 xmax = xmin + 2*(xmax-xmin);
5269 axis->SetRange(0,0);
5270 // double the bins and recompute ncells
5271 axis->Set(2*nbins,xmin,xmax);
5272 SetBinsLength(-1);
5273 Int_t errors = fSumw2.fN;
5274 if (errors) fSumw2.Set(fNcells);
5275 axis->SetTimeDisplay(timedisp);
5276
5277 Reset("ICE"); // reset content and error
5278
5279 //now loop on all bins and refill
5280 Double_t oldEntries = fEntries;
5281 Int_t bin,ibin,binx,biny,binz;
5282 for (ibin =0; ibin < hold->fNcells; ibin++) {
5283 // get the binx,y,z values . The x-y-z (axis) bin values will stay the same between new-old after the expanding
5284 hold->GetBinXYZ(ibin,binx,biny,binz);
5285 bin = GetBin(binx,biny,binz);
5286
5287 // underflow and overflow will be cleaned up because their meaning has been altered
5288 if (hold->IsBinUnderflow(ibin,iaxis) || hold->IsBinOverflow(ibin,iaxis)) {
5289 continue;
5290 }
5291 else {
5292 AddBinContent(bin, hold->RetrieveBinContent(ibin));
5293 if (errors) fSumw2.fArray[bin] += hold->fSumw2.fArray[ibin];
5294 }
5295 }
5296 fEntries = oldEntries;
5297 delete hold;
5298}
5299
5300////////////////////////////////////////////////////////////////////////////////
5301/// Sort bins with labels or set option(s) to draw axis with labels
5302/// \param[in] option
5303/// - "a" sort by alphabetic order
5304/// - ">" sort by decreasing values
5305/// - "<" sort by increasing values
5306/// - "h" draw labels horizontal
5307/// - "v" draw labels vertical
5308/// - "u" draw labels up (end of label right adjusted)
5309/// - "d" draw labels down (start of label left adjusted)
5310///
5311/// In case not all bins have labels sorting will work only in the case
5312/// the first `n` consecutive bins have all labels and sorting will be performed on
5313/// those label bins.
5314///
5315/// \param[in] ax axis
5316
5317void TH1::LabelsOption(Option_t *option, Option_t *ax)
5318{
5319 Int_t iaxis = AxisChoice(ax);
5320 TAxis *axis = 0;
5321 if (iaxis == 1)
5322 axis = GetXaxis();
5323 if (iaxis == 2)
5324 axis = GetYaxis();
5325 if (iaxis == 3)
5326 axis = GetZaxis();
5327 if (!axis)
5328 return;
5329 THashList *labels = axis->GetLabels();
5330 if (!labels) {
5331 Warning("LabelsOption", "Axis %s has no labels!",axis->GetName());
5332 return;
5333 }
5334 TString opt = option;
5335 opt.ToLower();
5336 Int_t iopt = -1;
5337 if (opt.Contains("h")) {
5342 iopt = 0;
5343 }
5344 if (opt.Contains("v")) {
5349 iopt = 1;
5350 }
5351 if (opt.Contains("u")) {
5352 axis->SetBit(TAxis::kLabelsUp);
5356 iopt = 2;
5357 }
5358 if (opt.Contains("d")) {
5363 iopt = 3;
5364 }
5365 Int_t sort = -1;
5366 if (opt.Contains("a"))
5367 sort = 0;
5368 if (opt.Contains(">"))
5369 sort = 1;
5370 if (opt.Contains("<"))
5371 sort = 2;
5372 if (sort < 0) {
5373 if (iopt < 0)
5374 Error("LabelsOption", "%s is an invalid label placement option!",opt.Data());
5375 return;
5376 }
5377
5378 // Code works only if first n bins have labels if we uncomment following line
5379 // but we don't want to support this special case
5380 // Int_t n = TMath::Min(axis->GetNbins(), labels->GetSize());
5381
5382 // support only cases where each bin has a labels (should be when axis is alphanumeric)
5383 Int_t n = labels->GetSize();
5384 if (n != axis->GetNbins()) {
5385 // check if labels are all consecutive and starts from the first bin
5386 // in that case the current code will work fine
5387 Int_t firstLabelBin = axis->GetNbins()+1;
5388 Int_t lastLabelBin = -1;
5389 for (Int_t i = 0; i < n; ++i) {
5390 Int_t bin = labels->At(i)->GetUniqueID();
5391 if (bin < firstLabelBin) firstLabelBin = bin;
5392 if (bin > lastLabelBin) lastLabelBin = bin;
5393 }
5394 if (firstLabelBin != 1 || lastLabelBin-firstLabelBin +1 != n) {
5395 Error("LabelsOption", "%s of Histogram %s contains bins without labels. Sorting will not work correctly - return",
5396 axis->GetName(), GetName());
5397 return;
5398 }
5399 // case where label bins are consecutive starting from first bin will work
5400 // calling before a TH1::LabelsDeflate() will avoid this error message
5401 Warning("LabelsOption", "axis %s of Histogram %s has extra following bins without labels. Sorting will work only for first label bins",
5402 axis->GetName(), GetName());
5403 }
5404 std::vector<Int_t> a(n);
5405 std::vector<Int_t> b(n);
5406
5407
5408 Int_t i, j, k;
5409 std::vector<Double_t> cont;
5410 std::vector<Double_t> errors2;
5411 THashList *labold = new THashList(labels->GetSize(), 1);
5412 TIter nextold(labels);
5413 TObject *obj = nullptr;
5414 labold->AddAll(labels);
5415 labels->Clear();
5416
5417 // delete buffer if it is there since bins will be reordered.
5418 if (fBuffer)
5419 BufferEmpty(1);
5420
5421 if (sort > 0) {
5422 //---sort by values of bins
5423 if (GetDimension() == 1) {
5424 cont.resize(n);
5425 if (fSumw2.fN)
5426 errors2.resize(n);
5427 for (i = 0; i < n; i++) {
5428 cont[i] = RetrieveBinContent(i + 1);
5429 if (!errors2.empty())
5430 errors2[i] = GetBinErrorSqUnchecked(i + 1);
5431 b[i] = labold->At(i)->GetUniqueID(); // this is the bin corresponding to the label
5432 a[i] = i;
5433 }
5434 if (sort == 1)
5435 TMath::Sort(n, cont.data(), a.data(), kTRUE); // sort by decreasing values
5436 else
5437 TMath::Sort(n, cont.data(), a.data(), kFALSE); // sort by increasing values
5438 for (i = 0; i < n; i++) {
5439 // use UpdateBinCOntent to not screw up histogram entries
5440 UpdateBinContent(i + 1, cont[b[a[i]] - 1]); // b[a[i]] returns bin number. .we need to subtract 1
5441 if (gDebug)
5442 Info("LabelsOption","setting bin %d value %f from bin %d label %s at pos %d ",
5443 i+1,cont[b[a[i]] - 1],b[a[i]],labold->At(a[i])->GetName(),a[i]);
5444 if (!errors2.empty())
5445 fSumw2.fArray[i + 1] = errors2[b[a[i]] - 1];
5446 }
5447 for (i = 0; i < n; i++) {
5448 obj = labold->At(a[i]);
5449 labels->Add(obj);
5450 obj->SetUniqueID(i + 1);
5451 }
5452 } else if (GetDimension() == 2) {
5453 std::vector<Double_t> pcont(n + 2);
5454 Int_t nx = fXaxis.GetNbins() + 2;
5455 Int_t ny = fYaxis.GetNbins() + 2;
5456 cont.resize((nx + 2) * (ny + 2));
5457 if (fSumw2.fN)
5458 errors2.resize((nx + 2) * (ny + 2));
5459 for (i = 0; i < nx; i++) {
5460 for (j = 0; j < ny; j++) {
5461 Int_t bin = GetBin(i,j);
5462 cont[i + nx * j] = RetrieveBinContent(bin);
5463 if (!errors2.empty())
5464 errors2[i + nx * j] = GetBinErrorSqUnchecked(bin);
5465 if (axis == GetXaxis())
5466 k = i - 1;
5467 else
5468 k = j - 1;
5469 if (k >= 0 && k < n) { // we consider underflow/overflows in y for ordering the bins
5470 pcont[k] += cont[i + nx * j];
5471 a[k] = k;
5472 }
5473 }
5474 }
5475 if (sort == 1)
5476 TMath::Sort(n, pcont.data(), a.data(), kTRUE); // sort by decreasing values
5477 else
5478 TMath::Sort(n, pcont.data(), a.data(), kFALSE); // sort by increasing values
5479 for (i = 0; i < n; i++) {
5480 // iterate on old label list to find corresponding bin match
5481 TIter next(labold);
5482 UInt_t bin = a[i] + 1;
5483 while ((obj = next())) {
5484 if (obj->GetUniqueID() == (UInt_t)bin)
5485 break;
5486 else
5487 obj = nullptr;
5488 }
5489 if (!obj) {
5490 // this should not really happen
5491 R__ASSERT("LabelsOption - No corresponding bin found when ordering labels");
5492 return;
5493 }
5494
5495 labels->Add(obj);
5496 if (gDebug)
5497 std::cout << " set label " << obj->GetName() << " to bin " << i + 1 << " from order " << a[i] << " bin "
5498 << b[a[i]] << "content " << pcont[a[i]] << std::endl;
5499 }
5500 // need to set here new ordered labels - otherwise loop before does not work since labold and labels list
5501 // contain same objects
5502 for (i = 0; i < n; i++) {
5503 labels->At(i)->SetUniqueID(i + 1);
5504 }
5505 // set now the bin contents
5506 if (axis == GetXaxis()) {
5507 for (i = 0; i < n; i++) {
5508 Int_t ix = a[i] + 1;
5509 for (j = 0; j < ny; j++) {
5510 Int_t bin = GetBin(i + 1, j);
5511 UpdateBinContent(bin, cont[ix + nx * j]);
5512 if (!errors2.empty())
5513 fSumw2.fArray[bin] = errors2[ix + nx * j];
5514 }
5515 }
5516 } else {
5517 // using y axis
5518 for (i = 0; i < nx; i++) {
5519 for (j = 0; j < n; j++) {
5520 Int_t iy = a[j] + 1;
5521 Int_t bin = GetBin(i, j + 1);
5522 UpdateBinContent(bin, cont[i + nx * iy]);
5523 if (!errors2.empty())
5524 fSumw2.fArray[bin] = errors2[i + nx * iy];
5525 }
5526 }
5527 }
5528 } else {
5529 // sorting histograms: 3D case
5530 std::vector<Double_t> pcont(n + 2);
5531 Int_t nx = fXaxis.GetNbins() + 2;
5532 Int_t ny = fYaxis.GetNbins() + 2;
5533 Int_t nz = fZaxis.GetNbins() + 2;
5534 Int_t l = 0;
5535 cont.resize((nx + 2) * (ny + 2) * (nz + 2));
5536 if (fSumw2.fN)
5537 errors2.resize((nx + 2) * (ny + 2) * (nz + 2));
5538 for (i = 0; i < nx; i++) {
5539 for (j = 0; j < ny; j++) {
5540 for (k = 0; k < nz; k++) {
5541 Int_t bin = GetBin(i,j,k);
5543 if (axis == GetXaxis())
5544 l = i - 1;
5545 else if (axis == GetYaxis())
5546 l = j - 1;
5547 else
5548 l = k - 1;
5549 if (l >= 0 && l < n) { // we consider underflow/overflows in y for ordering the bins
5550 pcont[l] += c;
5551 a[l] = l;
5552 }
5553 cont[i + nx * (j + ny * k)] = c;
5554 if (!errors2.empty())
5555 errors2[i + nx * (j + ny * k)] = GetBinErrorSqUnchecked(bin);
5556 }
5557 }
5558 }
5559 if (sort == 1)
5560 TMath::Sort(n, pcont.data(), a.data(), kTRUE); // sort by decreasing values
5561 else
5562 TMath::Sort(n, pcont.data(), a.data(), kFALSE); // sort by increasing values
5563 for (i = 0; i < n; i++) {
5564 // iterate on the old label list to find corresponding bin match
5565 TIter next(labold);
5566 UInt_t bin = a[i] + 1;
5567 obj = nullptr;
5568 while ((obj = next())) {
5569 if (obj->GetUniqueID() == (UInt_t)bin) {
5570 break;
5571 }
5572 else
5573 obj = nullptr;
5574 }
5575 if (!obj) {
5576 R__ASSERT("LabelsOption - No corresponding bin found when ordering labels");
5577 return;
5578 }
5579 labels->Add(obj);
5580 if (gDebug)
5581 std::cout << " set label " << obj->GetName() << " to bin " << i + 1 << " from bin " << a[i] << "content "
5582 << pcont[a[i]] << std::endl;
5583 }
5584
5585 // need to set here new ordered labels - otherwise loop before does not work since labold and llabels list
5586 // contain same objects
5587 for (i = 0; i < n; i++) {
5588 labels->At(i)->SetUniqueID(i + 1);
5589 }
5590 // set now the bin contents
5591 if (axis == GetXaxis()) {
5592 for (i = 0; i < n; i++) {
5593 Int_t ix = a[i] + 1;
5594 for (j = 0; j < ny; j++) {
5595 for (k = 0; k < nz; k++) {
5596 Int_t bin = GetBin(i + 1, j, k);
5597 UpdateBinContent(bin, cont[ix + nx * (j + ny * k)]);
5598 if (!errors2.empty())
5599 fSumw2.fArray[bin] = errors2[ix + nx * (j + ny * k)];
5600 }
5601 }
5602 }
5603 } else if (axis == GetYaxis()) {
5604 // using y axis
5605 for (i = 0; i < nx; i++) {
5606 for (j = 0; j < n; j++) {
5607 Int_t iy = a[j] + 1;
5608 for (k = 0; k < nz; k++) {
5609 Int_t bin = GetBin(i, j + 1, k);
5610 UpdateBinContent(bin, cont[i + nx * (iy + ny * k)]);
5611 if (!errors2.empty())
5612 fSumw2.fArray[bin] = errors2[i + nx * (iy + ny * k)];
5613 }
5614 }
5615 }
5616 } else {
5617 // using z axis
5618 for (i = 0; i < nx; i++) {
5619 for (j = 0; j < ny; j++) {
5620 for (k = 0; k < n; k++) {
5621 Int_t iz = a[k] + 1;
5622 Int_t bin = GetBin(i, j , k +1);
5623 UpdateBinContent(bin, cont[i + nx * (j + ny * iz)]);
5624 if (!errors2.empty())
5625 fSumw2.fArray[bin] = errors2[i + nx * (j + ny * iz)];
5626 }
5627 }
5628 }
5629 }
5630 }
5631 } else {
5632 //---alphabetic sort
5633 // sort labels using vector of strings and TMath::Sort
5634 // I need to array because labels order in list is not necessary that of the bins
5635 std::vector<std::string> vecLabels(n);
5636 for (i = 0; i < n; i++) {
5637 vecLabels[i] = labold->At(i)->GetName();
5638 b[i] = labold->At(i)->GetUniqueID(); // this is the bin corresponding to the label
5639 a[i] = i;
5640 }
5641 // sort in ascending order for strings
5642 TMath::Sort(n, vecLabels.data(), a.data(), kFALSE);
5643 // set the new labels
5644 for (i = 0; i < n; i++) {
5645 TObject *labelObj = labold->At(a[i]);
5646 labels->Add(labold->At(a[i]));
5647 // set the corresponding bin. NB bin starts from 1
5648 labelObj->SetUniqueID(i + 1);
5649 if (gDebug)
5650 std::cout << "bin " << i + 1 << " setting new labels for axis " << labold->At(a[i])->GetName() << " from "
5651 << b[a[i]] << std::endl;
5652 }
5653
5654 if (GetDimension() == 1) {
5655 cont.resize(n + 2);
5656 if (fSumw2.fN)
5657 errors2.resize(n + 2);
5658 for (i = 0; i < n; i++) {
5659 cont[i] = RetrieveBinContent(b[a[i]]);
5660 if (!errors2.empty())
5661 errors2[i] = GetBinErrorSqUnchecked(b[a[i]]);
5662 }
5663 for (i = 0; i < n; i++) {
5664 UpdateBinContent(i + 1, cont[i]);
5665 if (!errors2.empty())
5666 fSumw2.fArray[i+1] = errors2[i];
5667 }
5668 } else if (GetDimension() == 2) {
5669 Int_t nx = fXaxis.GetNbins() + 2;
5670 Int_t ny = fYaxis.GetNbins() + 2;
5671 cont.resize(nx * ny);
5672 if (fSumw2.fN)
5673 errors2.resize(nx * ny);
5674 // copy old bin contents and then set to new ordered bins
5675 // N.B. bin in histograms starts from 1, but in y we consider under/overflows
5676 for (i = 0; i < nx; i++) {
5677 for (j = 0; j < ny; j++) { // ny is nbins+2
5678 Int_t bin = GetBin(i, j);
5679 cont[i + nx * j] = RetrieveBinContent(bin);
5680 if (!errors2.empty())
5681 errors2[i + nx * j] = GetBinErrorSqUnchecked(bin);
5682 }
5683 }
5684 if (axis == GetXaxis()) {
5685 for (i = 0; i < n; i++) {
5686 for (j = 0; j < ny; j++) {
5687 Int_t bin = GetBin(i + 1 , j);
5688 UpdateBinContent(bin, cont[b[a[i]] + nx * j]);
5689 if (!errors2.empty())
5690 fSumw2.fArray[bin] = errors2[b[a[i]] + nx * j];
5691 }
5692 }
5693 } else {
5694 for (i = 0; i < nx; i++) {
5695 for (j = 0; j < n; j++) {
5696 Int_t bin = GetBin(i, j + 1);
5697 UpdateBinContent(bin, cont[i + nx * b[a[j]]]);
5698 if (!errors2.empty())
5699 fSumw2.fArray[bin] = errors2[i + nx * b[a[j]]];
5700 }
5701 }
5702 }
5703 } else {
5704 // case of 3D (needs to be tested)
5705 Int_t nx = fXaxis.GetNbins() + 2;
5706 Int_t ny = fYaxis.GetNbins() + 2;
5707 Int_t nz = fZaxis.GetNbins() + 2;
5708 cont.resize(nx * ny * nz);
5709 if (fSumw2.fN)
5710 errors2.resize(nx * ny * nz);
5711 for (i = 0; i < nx; i++) {
5712 for (j = 0; j < ny; j++) {
5713 for (k = 0; k < nz; k++) {
5714 Int_t bin = GetBin(i, j, k);
5715 cont[i + nx * (j + ny * k)] = RetrieveBinContent(bin);
5716 if (!errors2.empty())
5717 errors2[i + nx * (j + ny * k)] = GetBinErrorSqUnchecked(bin);
5718 }
5719 }
5720 }
5721 if (axis == GetXaxis()) {
5722 // labels on x axis
5723 for (i = 0; i < n; i++) { // for x we loop only on bins with the labels
5724 for (j = 0; j < ny; j++) {
5725 for (k = 0; k < nz; k++) {
5726 Int_t bin = GetBin(i + 1, j, k);
5727 UpdateBinContent(bin, cont[b[a[i]] + nx * (j + ny * k)]);
5728 if (!errors2.empty())
5729 fSumw2.fArray[bin] = errors2[b[a[i]] + nx * (j + ny * k)];
5730 }
5731 }
5732 }
5733 } else if (axis == GetYaxis()) {
5734 // labels on y axis
5735 for (i = 0; i < nx; i++) {
5736 for (j = 0; j < n; j++) {
5737 for (k = 0; k < nz; k++) {
5738 Int_t bin = GetBin(i, j+1, k);
5739 UpdateBinContent(bin, cont[i + nx * (b[a[j]] + ny * k)]);
5740 if (!errors2.empty())
5741 fSumw2.fArray[bin] = errors2[i + nx * (b[a[j]] + ny * k)];
5742 }
5743 }
5744 }
5745 } else {
5746 // labels on z axis
5747 for (i = 0; i < nx; i++) {
5748 for (j = 0; j < ny; j++) {
5749 for (k = 0; k < n; k++) {
5750 Int_t bin = GetBin(i, j, k+1);
5751 UpdateBinContent(bin, cont[i + nx * (j + ny * b[a[k]])]);
5752 if (!errors2.empty())
5753 fSumw2.fArray[bin] = errors2[i + nx * (j + ny * b[a[k]])];
5754 }
5755 }
5756 }
5757 }
5758 }
5759 }
5760 // need to set to zero the statistics if axis has been sorted
5761 // see for example TH3::PutStats for definition of s vector
5762 bool labelsAreSorted = kFALSE;
5763 for (i = 0; i < n; ++i) {
5764 if (a[i] != i) {
5765 labelsAreSorted = kTRUE;
5766 break;
5767 }
5768 }
5769 if (labelsAreSorted) {
5770 double s[TH1::kNstat];
5771 GetStats(s);
5772 if (iaxis == 1) {
5773 s[2] = 0; // fTsumwx
5774 s[3] = 0; // fTsumwx2
5775 s[6] = 0; // fTsumwxy
5776 s[9] = 0; // fTsumwxz
5777 } else if (iaxis == 2) {
5778 s[4] = 0; // fTsumwy
5779 s[5] = 0; // fTsumwy2
5780 s[6] = 0; // fTsumwxy
5781 s[10] = 0; // fTsumwyz
5782 } else if (iaxis == 3) {
5783 s[7] = 0; // fTsumwz
5784 s[8] = 0; // fTsumwz2
5785 s[9] = 0; // fTsumwxz
5786 s[10] = 0; // fTsumwyz
5787 }
5788 PutStats(s);
5789 }
5790 delete labold;
5791}
5792
5793////////////////////////////////////////////////////////////////////////////////
5794/// Test if two double are almost equal.
5795
5796static inline Bool_t AlmostEqual(Double_t a, Double_t b, Double_t epsilon = 0.00000001)
5797{
5798 return TMath::Abs(a - b) < epsilon;
5799}
5800
5801////////////////////////////////////////////////////////////////////////////////
5802/// Test if a double is almost an integer.
5803
5804static inline Bool_t AlmostInteger(Double_t a, Double_t epsilon = 0.00000001)
5805{
5806 return AlmostEqual(a - TMath::Floor(a), 0, epsilon) ||
5808}
5809
5810////////////////////////////////////////////////////////////////////////////////
5811/// Test if the binning is equidistant.
5812
5813static inline bool IsEquidistantBinning(const TAxis& axis)
5814{
5815 // check if axis bin are equals
5816 if (!axis.GetXbins()->fN) return true; //
5817 // not able to check if there is only one axis entry
5818 bool isEquidistant = true;
5819 const Double_t firstBinWidth = axis.GetBinWidth(1);
5820 for (int i = 1; i < axis.GetNbins(); ++i) {
5821 const Double_t binWidth = axis.GetBinWidth(i);
5822 const bool match = TMath::AreEqualRel(firstBinWidth, binWidth, 1.E-10);
5823 isEquidistant &= match;
5824 if (!match)
5825 break;
5826 }
5827 return isEquidistant;
5828}
5829
5830////////////////////////////////////////////////////////////////////////////////
5831/// Same limits and bins.
5832
5833Bool_t TH1::SameLimitsAndNBins(const TAxis &axis1, const TAxis &axis2){
5834 return axis1.GetNbins() == axis2.GetNbins() &&
5835 TMath::AreEqualAbs(axis1.GetXmin(), axis2.GetXmin(), axis1.GetBinWidth(axis1.GetNbins()) * 1.E-10) &&
5836 TMath::AreEqualAbs(axis1.GetXmax(), axis2.GetXmax(), axis1.GetBinWidth(axis1.GetNbins()) * 1.E-10);
5837}
5838
5839////////////////////////////////////////////////////////////////////////////////
5840/// Finds new limits for the axis for the Merge function.
5841/// returns false if the limits are incompatible
5842
5843Bool_t TH1::RecomputeAxisLimits(TAxis &destAxis, const TAxis &anAxis)
5844{
5845 if (SameLimitsAndNBins(destAxis, anAxis))
5846 return kTRUE;
5847
5848 if (!IsEquidistantBinning(destAxis) || !IsEquidistantBinning(anAxis))
5849 return kFALSE; // not equidistant user binning not supported
5850
5851 Double_t width1 = destAxis.GetBinWidth(0);
5852 Double_t width2 = anAxis.GetBinWidth(0);
5853 if (width1 == 0 || width2 == 0)
5854 return kFALSE; // no binning not supported
5855
5856 Double_t xmin = TMath::Min(destAxis.GetXmin(), anAxis.GetXmin());
5857 Double_t xmax = TMath::Max(destAxis.GetXmax(), anAxis.GetXmax());
5858 Double_t width = TMath::Max(width1, width2);
5859
5860 // check the bin size
5861 if (!AlmostInteger(width/width1) || !AlmostInteger(width/width2))
5862 return kFALSE;
5863
5864 // std::cout << "Find new limit using given axis " << anAxis.GetXmin() << " , " << anAxis.GetXmax() << " bin width " << width2 << std::endl;
5865 // std::cout << " and destination axis " << destAxis.GetXmin() << " , " << destAxis.GetXmax() << " bin width " << width1 << std::endl;
5866
5867
5868 // check the limits
5869 Double_t delta;
5870 delta = (destAxis.GetXmin() - xmin)/width1;
5871 if (!AlmostInteger(delta))
5872 xmin -= (TMath::Ceil(delta) - delta)*width1;
5873
5874 delta = (anAxis.GetXmin() - xmin)/width2;
5875 if (!AlmostInteger(delta))
5876 xmin -= (TMath::Ceil(delta) - delta)*width2;
5877
5878
5879 delta = (destAxis.GetXmin() - xmin)/width1;
5880 if (!AlmostInteger(delta))
5881 return kFALSE;
5882
5883
5884 delta = (xmax - destAxis.GetXmax())/width1;
5885 if (!AlmostInteger(delta))
5886 xmax += (TMath::Ceil(delta) - delta)*width1;
5887
5888
5889 delta = (xmax - anAxis.GetXmax())/width2;
5890 if (!AlmostInteger(delta))
5891 xmax += (TMath::Ceil(delta) - delta)*width2;
5892
5893
5894 delta = (xmax - destAxis.GetXmax())/width1;
5895 if (!AlmostInteger(delta))
5896 return kFALSE;
5897#ifdef DEBUG
5898 if (!AlmostInteger((xmax - xmin) / width)) { // unnecessary check
5899 printf("TH1::RecomputeAxisLimits - Impossible\n");
5900 return kFALSE;
5901 }
5902#endif
5903
5904
5905 destAxis.Set(TMath::Nint((xmax - xmin)/width), xmin, xmax);
5906
5907 //std::cout << "New re-computed axis : [ " << xmin << " , " << xmax << " ] width = " << width << " nbins " << destAxis.GetNbins() << std::endl;
5908
5909 return kTRUE;
5910}
5911
5912////////////////////////////////////////////////////////////////////////////////
5913/// Add all histograms in the collection to this histogram.
5914/// This function computes the min/max for the x axis,
5915/// compute a new number of bins, if necessary,
5916/// add bin contents, errors and statistics.
5917/// If all histograms have bin labels, bins with identical labels
5918/// will be merged, no matter what their order is.
5919/// If overflows are present and limits are different the function will fail.
5920/// The function returns the total number of entries in the result histogram
5921/// if the merge is successful, -1 otherwise.
5922///
5923/// Possible option:
5924/// -NOL : the merger will ignore the labels and merge the histograms bin by bin using bin center values to match bins
5925/// -NOCHECK: the histogram will not perform a check for duplicate labels in case of axes with labels. The check
5926/// (enabled by default) slows down the merging
5927///
5928/// IMPORTANT remark. The axis x may have different number
5929/// of bins and different limits, BUT the largest bin width must be
5930/// a multiple of the smallest bin width and the upper limit must also
5931/// be a multiple of the bin width.
5932/// Example:
5933///
5934/// ~~~ {.cpp}
5935/// void atest() {
5936/// TH1F *h1 = new TH1F("h1","h1",110,-110,0);
5937/// TH1F *h2 = new TH1F("h2","h2",220,0,110);
5938/// TH1F *h3 = new TH1F("h3","h3",330,-55,55);
5939/// TRandom r;
5940/// for (Int_t i=0;i<10000;i++) {
5941/// h1->Fill(r.Gaus(-55,10));
5942/// h2->Fill(r.Gaus(55,10));
5943/// h3->Fill(r.Gaus(0,10));
5944/// }
5945///
5946/// TList *list = new TList;
5947/// list->Add(h1);
5948/// list->Add(h2);
5949/// list->Add(h3);
5950/// TH1F *h = (TH1F*)h1->Clone("h");
5951/// h->Reset();
5952/// h->Merge(list);
5953/// h->Draw();
5954/// }
5955/// ~~~
5956
5958{
5959 if (!li) return 0;
5960 if (li->IsEmpty()) return (Long64_t) GetEntries();
5961
5962 // use TH1Merger class
5963 TH1Merger merger(*this,*li,opt);
5964 Bool_t ret = merger();
5965
5966 return (ret) ? GetEntries() : -1;
5967}
5968
5969
5970////////////////////////////////////////////////////////////////////////////////
5971/// Performs the operation:
5972///
5973/// `this = this*c1*f1`
5974///
5975/// If errors are defined (see TH1::Sumw2), errors are also recalculated.
5976///
5977/// Only bins inside the function range are recomputed.
5978/// IMPORTANT NOTE: If you intend to use the errors of this histogram later
5979/// you should call Sumw2 before making this operation.
5980/// This is particularly important if you fit the histogram after TH1::Multiply
5981///
5982/// The function return kFALSE if the Multiply operation failed
5983
5985{
5986 if (!f1) {
5987 Error("Multiply","Attempt to multiply by a non-existing function");
5988 return kFALSE;
5989 }
5990
5991 // delete buffer if it is there since it will become invalid
5992 if (fBuffer) BufferEmpty(1);
5993
5994 Int_t nx = GetNbinsX() + 2; // normal bins + uf / of (cells)
5995 Int_t ny = GetNbinsY() + 2;
5996 Int_t nz = GetNbinsZ() + 2;
5997 if (fDimension < 2) ny = 1;
5998 if (fDimension < 3) nz = 1;
5999
6000 // reset min-maximum
6001 SetMinimum();
6002 SetMaximum();
6003
6004 // - Loop on bins (including underflows/overflows)
6005 Double_t xx[3];
6006 Double_t *params = 0;
6007 f1->InitArgs(xx,params);
6008
6009 for (Int_t binz = 0; binz < nz; ++binz) {
6010 xx[2] = fZaxis.GetBinCenter(binz);
6011 for (Int_t biny = 0; biny < ny; ++biny) {
6012 xx[1] = fYaxis.GetBinCenter(biny);
6013 for (Int_t binx = 0; binx < nx; ++binx) {
6014 xx[0] = fXaxis.GetBinCenter(binx);
6015 if (!f1->IsInside(xx)) continue;
6017 Int_t bin = binx + nx * (biny + ny *binz);
6018 Double_t cu = c1*f1->EvalPar(xx);
6019 if (TF1::RejectedPoint()) continue;
6020 UpdateBinContent(bin, RetrieveBinContent(bin) * cu);
6021 if (fSumw2.fN) {
6022 fSumw2.fArray[bin] = cu * cu * GetBinErrorSqUnchecked(bin);
6023 }
6024 }
6025 }
6026 }
6027 ResetStats();
6028 return kTRUE;
6029}
6030
6031////////////////////////////////////////////////////////////////////////////////
6032/// Multiply this histogram by h1.
6033///
6034/// `this = this*h1`
6035///
6036/// If errors of this are available (TH1::Sumw2), errors are recalculated.
6037/// Note that if h1 has Sumw2 set, Sumw2 is automatically called for this
6038/// if not already set.
6039///
6040/// IMPORTANT NOTE: If you intend to use the errors of this histogram later
6041/// you should call Sumw2 before making this operation.
6042/// This is particularly important if you fit the histogram after TH1::Multiply
6043///
6044/// The function return kFALSE if the Multiply operation failed
6045
6046Bool_t TH1::Multiply(const TH1 *h1)
6047{
6048 if (!h1) {
6049 Error("Multiply","Attempt to multiply by a non-existing histogram");
6050 return kFALSE;
6051 }
6052
6053 // delete buffer if it is there since it will become invalid
6054 if (fBuffer) BufferEmpty(1);
6055
6056 try {
6057 CheckConsistency(this,h1);
6058 } catch(DifferentNumberOfBins&) {
6059 Error("Multiply","Attempt to multiply histograms with different number of bins");
6060 return kFALSE;
6061 } catch(DifferentAxisLimits&) {
6062 Warning("Multiply","Attempt to multiply histograms with different axis limits");
6063 } catch(DifferentBinLimits&) {
6064 Warning("Multiply","Attempt to multiply histograms with different bin limits");
6065 } catch(DifferentLabels&) {
6066 Warning("Multiply","Attempt to multiply histograms with different labels");
6067 }
6068
6069 // Create Sumw2 if h1 has Sumw2 set
6070 if (fSumw2.fN == 0 && h1->GetSumw2N() != 0) Sumw2();
6071
6072 // - Reset min- maximum
6073 SetMinimum();
6074 SetMaximum();
6075
6076 // - Loop on bins (including underflows/overflows)
6077 for (Int_t i = 0; i < fNcells; ++i) {
6080 UpdateBinContent(i, c0 * c1);
6081 if (fSumw2.fN) {
6083 }
6084 }
6085 ResetStats();
6086 return kTRUE;
6087}
6088
6089////////////////////////////////////////////////////////////////////////////////
6090/// Replace contents of this histogram by multiplication of h1 by h2.
6091///
6092/// `this = (c1*h1)*(c2*h2)`
6093///
6094/// If errors of this are available (TH1::Sumw2), errors are recalculated.
6095/// Note that if h1 or h2 have Sumw2 set, Sumw2 is automatically called for this
6096/// if not already set.
6097///
6098/// IMPORTANT NOTE: If you intend to use the errors of this histogram later
6099/// you should call Sumw2 before making this operation.
6100/// This is particularly important if you fit the histogram after TH1::Multiply
6101///
6102/// The function return kFALSE if the Multiply operation failed
6103
6104Bool_t TH1::Multiply(const TH1 *h1, const TH1 *h2, Double_t c1, Double_t c2, Option_t *option)
6105{
6106 TString opt = option;
6107 opt.ToLower();
6108 // Bool_t binomial = kFALSE;
6109 // if (opt.Contains("b")) binomial = kTRUE;
6110 if (!h1 || !h2) {
6111 Error("Multiply","Attempt to multiply by a non-existing histogram");
6112 return kFALSE;
6113 }
6114
6115 // delete buffer if it is there since it will become invalid
6116 if (fBuffer) BufferEmpty(1);
6117
6118 try {
6119 CheckConsistency(h1,h2);
6120 CheckConsistency(this,h1);
6121 } catch(DifferentNumberOfBins&) {
6122 Error("Multiply","Attempt to multiply histograms with different number of bins");
6123 return kFALSE;
6124 } catch(DifferentAxisLimits&) {
6125 Warning("Multiply","Attempt to multiply histograms with different axis limits");
6126 } catch(DifferentBinLimits&) {
6127 Warning("Multiply","Attempt to multiply histograms with different bin limits");
6128 } catch(DifferentLabels&) {
6129 Warning("Multiply","Attempt to multiply histograms with different labels");
6130 }
6131
6132 // Create Sumw2 if h1 or h2 have Sumw2 set
6133 if (fSumw2.fN == 0 && (h1->GetSumw2N() != 0 || h2->GetSumw2N() != 0)) Sumw2();
6134
6135 // - Reset min - maximum
6136 SetMinimum();
6137 SetMaximum();
6138
6139 // - Loop on bins (including underflows/overflows)
6140 Double_t c1sq = c1 * c1; Double_t c2sq = c2 * c2;
6141 for (Int_t i = 0; i < fNcells; ++i) {
6143 Double_t b2 = h2->RetrieveBinContent(i);
6144 UpdateBinContent(i, c1 * b1 * c2 * b2);
6145 if (fSumw2.fN) {
6146 fSumw2.fArray[i] = c1sq * c2sq * (h1->GetBinErrorSqUnchecked(i) * b2 * b2 + h2->GetBinErrorSqUnchecked(i) * b1 * b1);
6147 }
6148 }
6149 ResetStats();
6150 return kTRUE;
6151}
6152
6153////////////////////////////////////////////////////////////////////////////////
6154/// Control routine to paint any kind of histograms.
6155///
6156/// This function is automatically called by TCanvas::Update.
6157/// (see TH1::Draw for the list of options)
6158
6159void TH1::Paint(Option_t *option)
6160{
6161 GetPainter(option);
6162
6163 if (fPainter) {
6164 if (strlen(option) > 0) fPainter->Paint(option);
6165 else fPainter->Paint(fOption.Data());
6166 }
6167}
6168
6169////////////////////////////////////////////////////////////////////////////////
6170/// Rebin this histogram
6171///
6172/// #### case 1 xbins=0
6173///
6174/// If newname is blank (default), the current histogram is modified and
6175/// a pointer to it is returned.
6176///
6177/// If newname is not blank, the current histogram is not modified, and a
6178/// new histogram is returned which is a Clone of the current histogram
6179/// with its name set to newname.
6180///
6181/// The parameter ngroup indicates how many bins of this have to be merged
6182/// into one bin of the result.
6183///
6184/// If the original histogram has errors stored (via Sumw2), the resulting
6185/// histograms has new errors correctly calculated.
6186///
6187/// examples: if h1 is an existing TH1F histogram with 100 bins
6188///
6189/// ~~~ {.cpp}
6190/// h1->Rebin(); //merges two bins in one in h1: previous contents of h1 are lost
6191/// h1->Rebin(5); //merges five bins in one in h1
6192/// TH1F *hnew = dynamic_cast<TH1F*>(h1->Rebin(5,"hnew")); // creates a new histogram hnew
6193/// // merging 5 bins of h1 in one bin
6194/// ~~~
6195///
6196/// NOTE: If ngroup is not an exact divider of the number of bins,
6197/// the top limit of the rebinned histogram is reduced
6198/// to the upper edge of the last bin that can make a complete
6199/// group. The remaining bins are added to the overflow bin.
6200/// Statistics will be recomputed from the new bin contents.
6201///
6202/// #### case 2 xbins!=0
6203///
6204/// A new histogram is created (you should specify newname).
6205/// The parameter ngroup is the number of variable size bins in the created histogram.
6206/// The array xbins must contain ngroup+1 elements that represent the low-edges
6207/// of the bins.
6208/// If the original histogram has errors stored (via Sumw2), the resulting
6209/// histograms has new errors correctly calculated.
6210///
6211/// NOTE: The bin edges specified in xbins should correspond to bin edges
6212/// in the original histogram. If a bin edge in the new histogram is
6213/// in the middle of a bin in the original histogram, all entries in
6214/// the split bin in the original histogram will be transfered to the
6215/// lower of the two possible bins in the new histogram. This is
6216/// probably not what you want. A warning message is emitted in this
6217/// case
6218///
6219/// examples: if h1 is an existing TH1F histogram with 100 bins
6220///
6221/// ~~~ {.cpp}
6222/// Double_t xbins[25] = {...} array of low-edges (xbins[25] is the upper edge of last bin
6223/// h1->Rebin(24,"hnew",xbins); //creates a new variable bin size histogram hnew
6224/// ~~~
6225
6226TH1 *TH1::Rebin(Int_t ngroup, const char*newname, const Double_t *xbins)
6227{
6228 Int_t nbins = fXaxis.GetNbins();
6231 if ((ngroup <= 0) || (ngroup > nbins)) {
6232 Error("Rebin", "Illegal value of ngroup=%d",ngroup);
6233 return 0;
6234 }
6235
6236 if (fDimension > 1 || InheritsFrom(TProfile::Class())) {
6237 Error("Rebin", "Operation valid on 1-D histograms only");
6238 return 0;
6239 }
6240 if (!newname && xbins) {
6241 Error("Rebin","if xbins is specified, newname must be given");
6242 return 0;
6243 }
6244
6245 Int_t newbins = nbins/ngroup;
6246 if (!xbins) {
6247 Int_t nbg = nbins/ngroup;
6248 if (nbg*ngroup != nbins) {
6249 Warning("Rebin", "ngroup=%d is not an exact divider of nbins=%d.",ngroup,nbins);
6250 }
6251 }
6252 else {
6253 // in the case that xbins is given (rebinning in variable bins), ngroup is
6254 // the new number of bins and number of grouped bins is not constant.
6255 // when looping for setting the contents for the new histogram we
6256 // need to loop on all bins of original histogram. Then set ngroup=nbins
6257 newbins = ngroup;
6258 ngroup = nbins;
6259 }
6260
6261 // Save old bin contents into a new array
6262 Double_t entries = fEntries;
6263 Double_t *oldBins = new Double_t[nbins+2];
6264 Int_t bin, i;
6265 for (bin=0;bin<nbins+2;bin++) oldBins[bin] = RetrieveBinContent(bin);
6266 Double_t *oldErrors = 0;
6267 if (fSumw2.fN != 0) {
6268 oldErrors = new Double_t[nbins+2];
6269 for (bin=0;bin<nbins+2;bin++) oldErrors[bin] = GetBinError(bin);
6270 }
6271 // rebin will not include underflow/overflow if new axis range is larger than old axis range
6272 if (xbins) {
6273 if (xbins[0] < fXaxis.GetXmin() && oldBins[0] != 0 )
6274 Warning("Rebin","underflow entries will not be used when rebinning");
6275 if (xbins[newbins] > fXaxis.GetXmax() && oldBins[nbins+1] != 0 )
6276 Warning("Rebin","overflow entries will not be used when rebinning");
6277 }
6278
6279
6280 // create a clone of the old histogram if newname is specified
6281 TH1 *hnew = this;
6282 if ((newname && strlen(newname) > 0) || xbins) {
6283 hnew = (TH1*)Clone(newname);
6284 }
6285
6286 //reset can extend bit to avoid an axis extension in SetBinContent
6287 UInt_t oldExtendBitMask = hnew->SetCanExtend(kNoAxis);
6288
6289 // save original statistics
6290 Double_t stat[kNstat];
6291 GetStats(stat);
6292 bool resetStat = false;
6293 // change axis specs and rebuild bin contents array::RebinAx
6294 if(!xbins && (newbins*ngroup != nbins)) {
6295 xmax = fXaxis.GetBinUpEdge(newbins*ngroup);
6296 resetStat = true; //stats must be reset because top bins will be moved to overflow bin
6297 }
6298 // save the TAttAxis members (reset by SetBins)
6299 Int_t nDivisions = fXaxis.GetNdivisions();
6300 Color_t axisColor = fXaxis.GetAxisColor();
6301 Color_t labelColor = fXaxis.GetLabelColor();
6302 Style_t labelFont = fXaxis.GetLabelFont();
6303 Float_t labelOffset = fXaxis.GetLabelOffset();
6304 Float_t labelSize = fXaxis.GetLabelSize();
6305 Float_t tickLength = fXaxis.GetTickLength();
6306 Float_t titleOffset = fXaxis.GetTitleOffset();
6307 Float_t titleSize = fXaxis.GetTitleSize();
6308 Color_t titleColor = fXaxis.GetTitleColor();
6309 Style_t titleFont = fXaxis.GetTitleFont();
6310
6311 if(!xbins && (fXaxis.GetXbins()->GetSize() > 0)){ // variable bin sizes
6312 Double_t *bins = new Double_t[newbins+1];
6313 for(i = 0; i <= newbins; ++i) bins[i] = fXaxis.GetBinLowEdge(1+i*ngroup);
6314 hnew->SetBins(newbins,bins); //this also changes errors array (if any)
6315 delete [] bins;
6316 } else if (xbins) {
6317 hnew->SetBins(newbins,xbins);
6318 } else {
6319 hnew->SetBins(newbins,xmin,xmax);
6320 }
6321
6322 // Restore axis attributes
6323 fXaxis.SetNdivisions(nDivisions);
6324 fXaxis.SetAxisColor(axisColor);
6325 fXaxis.SetLabelColor(labelColor);
6326 fXaxis.SetLabelFont(labelFont);
6327 fXaxis.SetLabelOffset(labelOffset);
6328 fXaxis.SetLabelSize(labelSize);
6329 fXaxis.SetTickLength(tickLength);
6330 fXaxis.SetTitleOffset(titleOffset);
6331 fXaxis.SetTitleSize(titleSize);
6332 fXaxis.SetTitleColor(titleColor);
6333 fXaxis.SetTitleFont(titleFont);
6334
6335 // copy merged bin contents (ignore under/overflows)
6336 // Start merging only once the new lowest edge is reached
6337 Int_t startbin = 1;
6338 const Double_t newxmin = hnew->GetXaxis()->GetBinLowEdge(1);
6339 while( fXaxis.GetBinCenter(startbin) < newxmin && startbin <= nbins ) {
6340 startbin++;
6341 }
6342 Int_t oldbin = startbin;
6343 Double_t binContent, binError;
6344 for (bin = 1;bin<=newbins;bin++) {
6345 binContent = 0;
6346 binError = 0;
6347 Int_t imax = ngroup;
6348 Double_t xbinmax = hnew->GetXaxis()->GetBinUpEdge(bin);
6349 // check bin edges for the cases when we provide an array of bins
6350 // be careful in case bins can have zero width
6351 if (xbins && !TMath::AreEqualAbs(fXaxis.GetBinLowEdge(oldbin),
6352 hnew->GetXaxis()->GetBinLowEdge(bin),
6353 TMath::Max(1.E-8 * fXaxis.GetBinWidth(oldbin), 1.E-16 )) )
6354 {
6355 Warning("Rebin","Bin edge %d of rebinned histogram does not match any bin edges of the old histogram. Result can be inconsistent",bin);
6356 }
6357 for (i=0;i<ngroup;i++) {
6358 if( (oldbin+i > nbins) ||
6359 ( hnew != this && (fXaxis.GetBinCenter(oldbin+i) > xbinmax)) ) {
6360 imax = i;
6361 break;
6362 }
6363 binContent += oldBins[oldbin+i];
6364 if (oldErrors) binError += oldErrors[oldbin+i]*oldErrors[oldbin+i];
6365 }
6366 hnew->SetBinContent(bin,binContent);
6367 if (oldErrors) hnew->SetBinError(bin,TMath::Sqrt(binError));
6368 oldbin += imax;
6369 }
6370
6371 // sum underflow and overflow contents until startbin
6372 binContent = 0;
6373 binError = 0;
6374 for (i = 0; i < startbin; ++i) {
6375 binContent += oldBins[i];
6376 if (oldErrors) binError += oldErrors[i]*oldErrors[i];
6377 }
6378 hnew->SetBinContent(0,binContent);
6379 if (oldErrors) hnew->SetBinError(0,TMath::Sqrt(binError));
6380 // sum overflow
6381 binContent = 0;
6382 binError = 0;
6383 for (i = oldbin; i <= nbins+1; ++i) {
6384 binContent += oldBins[i];
6385 if (oldErrors) binError += oldErrors[i]*oldErrors[i];
6386 }
6387 hnew->SetBinContent(newbins+1,binContent);
6388 if (oldErrors) hnew->SetBinError(newbins+1,TMath::Sqrt(binError));
6389
6390 hnew->SetCanExtend(oldExtendBitMask); // restore previous state
6391
6392 // restore statistics and entries modified by SetBinContent
6393 hnew->SetEntries(entries);
6394 if (!resetStat) hnew->PutStats(stat);
6395 delete [] oldBins;
6396 if (oldErrors) delete [] oldErrors;
6397 return hnew;
6398}
6399
6400////////////////////////////////////////////////////////////////////////////////
6401/// finds new limits for the axis so that *point* is within the range and
6402/// the limits are compatible with the previous ones (see TH1::Merge).
6403/// new limits are put into *newMin* and *newMax* variables.
6404/// axis - axis whose limits are to be recomputed
6405/// point - point that should fit within the new axis limits
6406/// newMin - new minimum will be stored here
6407/// newMax - new maximum will be stored here.
6408/// false if failed (e.g. if the initial axis limits are wrong
6409/// or the new range is more than \f$ 2^{64} \f$ times the old one).
6410
6411Bool_t TH1::FindNewAxisLimits(const TAxis* axis, const Double_t point, Double_t& newMin, Double_t &newMax)
6412{
6413 Double_t xmin = axis->GetXmin();
6414 Double_t xmax = axis->GetXmax();
6415 if (xmin >= xmax) return kFALSE;
6416 Double_t range = xmax-xmin;
6417
6418 //recompute new axis limits by doubling the current range
6419 Int_t ntimes = 0;
6420 while (point < xmin) {
6421 if (ntimes++ > 64)
6422 return kFALSE;
6423 xmin = xmin - range;
6424 range *= 2;
6425 }
6426 while (point >= xmax) {
6427 if (ntimes++ > 64)
6428 return kFALSE;
6429 xmax = xmax + range;
6430 range *= 2;
6431 }
6432 newMin = xmin;
6433 newMax = xmax;
6434 // Info("FindNewAxisLimits", "OldAxis: (%lf, %lf), new: (%lf, %lf), point: %lf",
6435 // axis->GetXmin(), axis->GetXmax(), xmin, xmax, point);
6436
6437 return kTRUE;
6438}
6439
6440////////////////////////////////////////////////////////////////////////////////
6441/// Histogram is resized along axis such that x is in the axis range.
6442/// The new axis limits are recomputed by doubling iteratively
6443/// the current axis range until the specified value x is within the limits.
6444/// The algorithm makes a copy of the histogram, then loops on all bins
6445/// of the old histogram to fill the extended histogram.
6446/// Takes into account errors (Sumw2) if any.
6447/// The algorithm works for 1-d, 2-D and 3-D histograms.
6448/// The axis must be extendable before invoking this function.
6449/// Ex:
6450///
6451/// ~~~ {.cpp}
6452/// h->GetXaxis()->SetCanExtend(kTRUE);
6453/// ~~~
6454
6455void TH1::ExtendAxis(Double_t x, TAxis *axis)
6456{
6457 if (!axis->CanExtend()) return;
6458 if (TMath::IsNaN(x)) { // x may be a NaN
6460 return;
6461 }
6462
6463 if (axis->GetXmin() >= axis->GetXmax()) return;
6464 if (axis->GetNbins() <= 0) return;
6465
6467 if (!FindNewAxisLimits(axis, x, xmin, xmax))
6468 return;
6469
6470 //save a copy of this histogram
6471 TH1 *hold = (TH1*)IsA()->New();
6472 hold->SetDirectory(0);
6473 Copy(*hold);
6474 //set new axis limits
6475 axis->SetLimits(xmin,xmax);
6476
6477
6478 //now loop on all bins and refill
6479 Int_t errors = GetSumw2N();
6480
6481 Reset("ICE"); //reset only Integral, contents and Errors
6482
6483 int iaxis = 0;
6484 if (axis == &fXaxis) iaxis = 1;
6485 if (axis == &fYaxis) iaxis = 2;
6486 if (axis == &fZaxis) iaxis = 3;
6487 bool firstw = kTRUE;
6488 Int_t binx,biny, binz = 0;
6489 Int_t ix = 0,iy = 0,iz = 0;
6490 Double_t bx,by,bz;
6491 Int_t ncells = hold->GetNcells();
6492 for (Int_t bin = 0; bin < ncells; ++bin) {
6493 hold->GetBinXYZ(bin,binx,biny,binz);
6494 bx = hold->GetXaxis()->GetBinCenter(binx);
6495 ix = fXaxis.FindFixBin(bx);
6496 if (fDimension > 1) {
6497 by = hold->GetYaxis()->GetBinCenter(biny);
6498 iy = fYaxis.FindFixBin(by);
6499 if (fDimension > 2) {
6500 bz = hold->GetZaxis()->GetBinCenter(binz);
6501 iz = fZaxis.FindFixBin(bz);
6502 }
6503 }
6504 // exclude underflow/overflow
6505 double content = hold->RetrieveBinContent(bin);
6506 if (content == 0) continue;
6507 if (IsBinUnderflow(bin,iaxis) || IsBinOverflow(bin,iaxis) ) {
6508 if (firstw) {
6509 Warning("ExtendAxis","Histogram %s has underflow or overflow in the axis that is extendable"
6510 " their content will be lost",GetName() );
6511 firstw= kFALSE;
6512 }
6513 continue;
6514 }
6515 Int_t ibin= GetBin(ix,iy,iz);
6516 AddBinContent(ibin, content);
6517 if (errors) {
6518 fSumw2.fArray[ibin] += hold->GetBinErrorSqUnchecked(bin);
6519 }
6520 }
6521 delete hold;
6522}
6523
6524////////////////////////////////////////////////////////////////////////////////
6525/// Recursively remove object from the list of functions
6526
6528{
6529 // Rely on TROOT::RecursiveRemove to take the readlock.
6530
6531 if (fFunctions) {
6533 }
6534}
6535
6536////////////////////////////////////////////////////////////////////////////////
6537/// Multiply this histogram by a constant c1.
6538///
6539/// `this = c1*this`
6540///
6541/// Note that both contents and errors (if any) are scaled.
6542/// This function uses the services of TH1::Add
6543///
6544/// IMPORTANT NOTE: Sumw2() is called automatically when scaling.
6545/// If you are not interested in the histogram statistics you can call
6546/// Sumw2(kFALSE) or use the option "nosw2"
6547///
6548/// One can scale a histogram such that the bins integral is equal to
6549/// the normalization parameter via TH1::Scale(Double_t norm), where norm
6550/// is the desired normalization divided by the integral of the histogram.
6551///
6552/// If option contains "width" the bin contents and errors are divided
6553/// by the bin width.
6554
6555void TH1::Scale(Double_t c1, Option_t *option)
6556{
6557
6558 TString opt = option; opt.ToLower();
6559 // store bin errors when scaling since cannot anymore be computed as sqrt(N)
6560 if (!opt.Contains("nosw2") && GetSumw2N() == 0) Sumw2();
6561 if (opt.Contains("width")) Add(this, this, c1, -1);
6562 else {
6563 if (fBuffer) BufferEmpty(1);
6564 for(Int_t i = 0; i < fNcells; ++i) UpdateBinContent(i, c1 * RetrieveBinContent(i));
6565 if (fSumw2.fN) for(Int_t i = 0; i < fNcells; ++i) fSumw2.fArray[i] *= (c1 * c1); // update errors
6566 // update global histograms statistics
6567 Double_t s[kNstat] = {0};
6568 GetStats(s);
6569 for (Int_t i=0 ; i < kNstat; i++) {
6570 if (i == 1) s[i] = c1*c1*s[i];
6571 else s[i] = c1*s[i];
6572 }
6573 PutStats(s);
6574 SetMinimum(); SetMaximum(); // minimum and maximum value will be recalculated the next time
6575 }
6576
6577 // if contours set, must also scale contours
6578 Int_t ncontours = GetContour();
6579 if (ncontours == 0) return;
6580 Double_t* levels = fContour.GetArray();
6581 for (Int_t i = 0; i < ncontours; ++i) levels[i] *= c1;
6582}
6583
6584////////////////////////////////////////////////////////////////////////////////
6585/// Returns true if all axes are extendable.
6586
6588{
6589 Bool_t canExtend = fXaxis.CanExtend();
6590 if (GetDimension() > 1) canExtend &= fYaxis.CanExtend();
6591 if (GetDimension() > 2) canExtend &= fZaxis.CanExtend();
6592
6593 return canExtend;
6594}
6595
6596////////////////////////////////////////////////////////////////////////////////
6597/// Make the histogram axes extendable / not extendable according to the bit mask
6598/// returns the previous bit mask specifying which axes are extendable
6599
6600UInt_t TH1::SetCanExtend(UInt_t extendBitMask)
6601{
6602 UInt_t oldExtendBitMask = kNoAxis;
6603
6604 if (fXaxis.CanExtend()) oldExtendBitMask |= kXaxis;
6605 if (extendBitMask & kXaxis) fXaxis.SetCanExtend(kTRUE);
6607
6608 if (GetDimension() > 1) {
6609 if (fYaxis.CanExtend()) oldExtendBitMask |= kYaxis;
6610 if (extendBitMask & kYaxis) fYaxis.SetCanExtend(kTRUE);
6612 }
6613
6614 if (GetDimension() > 2) {
6615 if (fZaxis.CanExtend()) oldExtendBitMask |= kZaxis;
6616 if (extendBitMask & kZaxis) fZaxis.SetCanExtend(kTRUE);
6618 }
6619
6620 return oldExtendBitMask;
6621}
6622
6623///////////////////////////////////////////////////////////////////////////////
6624/// Internal function used in TH1::Fill to see which axis is full alphanumeric
6625/// i.e. can be extended and is alphanumeric
6627{
6628 UInt_t bitMask = kNoAxis;
6629 if (fXaxis.CanExtend() && fXaxis.IsAlphanumeric() ) bitMask |= kXaxis;
6631 bitMask |= kYaxis;
6633 bitMask |= kZaxis;
6634
6635 return bitMask;
6636}
6637
6638////////////////////////////////////////////////////////////////////////////////
6639/// Static function to set the default buffer size for automatic histograms.
6640/// When a histogram is created with one of its axis lower limit greater
6641/// or equal to its upper limit, the function SetBuffer is automatically
6642/// called with the default buffer size.
6643
6644void TH1::SetDefaultBufferSize(Int_t buffersize)
6645{
6646 fgBufferSize = buffersize > 0 ? buffersize : 0;
6647}
6648
6649////////////////////////////////////////////////////////////////////////////////
6650/// When this static function is called with `sumw2=kTRUE`, all new
6651/// histograms will automatically activate the storage
6652/// of the sum of squares of errors, ie TH1::Sumw2 is automatically called.
6653
6654void TH1::SetDefaultSumw2(Bool_t sumw2)
6655{
6656 fgDefaultSumw2 = sumw2;
6657}
6658
6659////////////////////////////////////////////////////////////////////////////////
6660/// Change (i.e. set) the title
6661///
6662/// if title is in the form `stringt;stringx;stringy;stringz`
6663/// the histogram title is set to `stringt`, the x axis title to `stringx`,
6664/// the y axis title to `stringy`, and the z axis title to `stringz`.
6665///
6666/// To insert the character `;` in one of the titles, one should use `#;`
6667/// or `#semicolon`.
6668
6669void TH1::SetTitle(const char *title)
6670{
6671 fTitle = title;
6672 fTitle.ReplaceAll("#;",2,"#semicolon",10);
6673
6674 // Decode fTitle. It may contain X, Y and Z titles
6675 TString str1 = fTitle, str2;
6676 Int_t isc = str1.Index(";");
6677 Int_t lns = str1.Length();
6678
6679 if (isc >=0 ) {
6680 fTitle = str1(0,isc);
6681 str1 = str1(isc+1, lns);
6682 isc = str1.Index(";");
6683 if (isc >=0 ) {
6684 str2 = str1(0,isc);
6685 str2.ReplaceAll("#semicolon",10,";",1);
6686 fXaxis.SetTitle(str2.Data());
6687 lns = str1.Length();
6688 str1 = str1(isc+1, lns);
6689 isc = str1.Index(";");
6690 if (isc >=0 ) {
6691 str2 = str1(0,isc);
6692 str2.ReplaceAll("#semicolon",10,";",1);
6693 fYaxis.SetTitle(str2.Data());
6694 lns = str1.Length();
6695 str1 = str1(isc+1, lns);
6696 str1.ReplaceAll("#semicolon",10,";",1);
6697 fZaxis.SetTitle(str1.Data());
6698 } else {
6699 str1.ReplaceAll("#semicolon",10,";",1);
6700 fYaxis.SetTitle(str1.Data());
6701 }
6702 } else {
6703 str1.ReplaceAll("#semicolon",10,";",1);
6704 fXaxis.SetTitle(str1.Data());
6705 }
6706 }
6707
6708 fTitle.ReplaceAll("#semicolon",10,";",1);
6709
6710 if (gPad && TestBit(kMustCleanup)) gPad->Modified();
6711}
6712
6713////////////////////////////////////////////////////////////////////////////////
6714/// Smooth array xx, translation of Hbook routine hsmoof.F
6715/// based on algorithm 353QH twice presented by J. Friedman
6716/// in Proc.of the 1974 CERN School of Computing, Norway, 11-24 August, 1974.
6717
6718void TH1::SmoothArray(Int_t nn, Double_t *xx, Int_t ntimes)
6719{
6720 if (nn < 3 ) {
6721 ::Error("SmoothArray","Need at least 3 points for smoothing: n = %d",nn);
6722 return;
6723 }
6724
6725 Int_t ii;
6726 Double_t hh[6] = {0,0,0,0,0,0};
6727
6728 std::vector<double> yy(nn);
6729 std::vector<double> zz(nn);
6730 std::vector<double> rr(nn);
6731
6732 for (Int_t pass=0;pass<ntimes;pass++) {
6733 // first copy original data into temp array
6734 std::copy(xx, xx+nn, zz.begin() );
6735
6736 for (int noent = 0; noent < 2; ++noent) { // run algorithm two times
6737
6738 // do 353 i.e. running median 3, 5, and 3 in a single loop
6739 for (int kk = 0; kk < 3; kk++) {
6740 std::copy(zz.begin(), zz.end(), yy.begin());
6741 int medianType = (kk != 1) ? 3 : 5;
6742 int ifirst = (kk != 1 ) ? 1 : 2;
6743 int ilast = (kk != 1 ) ? nn-1 : nn -2;
6744 //nn2 = nn - ik - 1;
6745 // do all elements beside the first and last point for median 3
6746 // and first two and last 2 for median 5
6747 for ( ii = ifirst; ii < ilast; ii++) {
6748 assert(ii - ifirst >= 0);
6749 for (int jj = 0; jj < medianType; jj++) {
6750 hh[jj] = yy[ii - ifirst + jj ];
6751 }
6752 zz[ii] = TMath::Median(medianType, hh);
6753 }
6754
6755 if (kk == 0) { // first median 3
6756 // first point
6757 hh[0] = zz[1];
6758 hh[1] = zz[0];
6759 hh[2] = 3*zz[1] - 2*zz[2];
6760 zz[0] = TMath::Median(3, hh);
6761 // last point
6762 hh[0] = zz[nn - 2];
6763 hh[1] = zz[nn - 1];
6764 hh[2] = 3*zz[nn - 2] - 2*zz[nn - 3];
6765 zz[nn - 1] = TMath::Median(3, hh);
6766 }
6767
6768 if (kk == 1) { // median 5
6769 for (ii = 0; ii < 3; ii++) {
6770 hh[ii] = yy[ii];
6771 }
6772 zz[1] = TMath::Median(3, hh);
6773 // last two points
6774 for (ii = 0; ii < 3; ii++) {
6775 hh[ii] = yy[nn - 3 + ii];
6776 }
6777 zz[nn - 2] = TMath::Median(3, hh);
6778 }
6779
6780 }
6781
6782 std::copy ( zz.begin(), zz.end(), yy.begin() );
6783
6784 // quadratic interpolation for flat segments
6785 for (ii = 2; ii < (nn - 2); ii++) {
6786 if (zz[ii - 1] != zz[ii]) continue;
6787 if (zz[ii] != zz[ii + 1]) continue;
6788 hh[0] = zz[ii - 2] - zz[ii];
6789 hh[1] = zz[ii + 2] - zz[ii];
6790 if (hh[0] * hh[1] <= 0) continue;
6791 int jk = 1;
6792 if ( TMath::Abs(hh[1]) > TMath::Abs(hh[0]) ) jk = -1;
6793 yy[ii] = -0.5*zz[ii - 2*jk] + zz[ii]/0.75 + zz[ii + 2*jk] /6.;
6794 yy[ii + jk] = 0.5*(zz[ii + 2*jk] - zz[ii - 2*jk]) + zz[ii];
6795 }
6796
6797 // running means
6798 //std::copy(zz.begin(), zz.end(), yy.begin());
6799 for (ii = 1; ii < nn - 1; ii++) {
6800 zz[ii] = 0.25*yy[ii - 1] + 0.5*yy[ii] + 0.25*yy[ii + 1];
6801 }
6802 zz[0] = yy[0];
6803 zz[nn - 1] = yy[nn - 1];
6804
6805 if (noent == 0) {
6806
6807 // save computed values
6808 std::copy(zz.begin(), zz.end(), rr.begin());
6809
6810 // COMPUTE residuals
6811 for (ii = 0; ii < nn; ii++) {
6812 zz[ii] = xx[ii] - zz[ii];
6813 }
6814 }
6815
6816 } // end loop on noent
6817
6818
6819 double xmin = TMath::MinElement(nn,xx);
6820 for (ii = 0; ii < nn; ii++) {
6821 if (xmin < 0) xx[ii] = rr[ii] + zz[ii];
6822 // make smoothing defined positive - not better using 0 ?
6823 else xx[ii] = TMath::Max((rr[ii] + zz[ii]),0.0 );
6824 }
6825 }
6826}
6827
6828////////////////////////////////////////////////////////////////////////////////
6829/// Smooth bin contents of this histogram.
6830/// if option contains "R" smoothing is applied only to the bins
6831/// defined in the X axis range (default is to smooth all bins)
6832/// Bin contents are replaced by their smooth values.
6833/// Errors (if any) are not modified.
6834/// the smoothing procedure is repeated ntimes (default=1)
6835
6836void TH1::Smooth(Int_t ntimes, Option_t *option)
6837{
6838 if (fDimension != 1) {
6839 Error("Smooth","Smooth only supported for 1-d histograms");
6840 return;
6841 }
6842 Int_t nbins = fXaxis.GetNbins();
6843 if (nbins < 3) {
6844 Error("Smooth","Smooth only supported for histograms with >= 3 bins. Nbins = %d",nbins);
6845 return;
6846 }
6847
6848 // delete buffer if it is there since it will become invalid
6849 if (fBuffer) BufferEmpty(1);
6850
6851 Int_t firstbin = 1, lastbin = nbins;
6852 TString opt = option;
6853 opt.ToLower();
6854 if (opt.Contains("r")) {
6855 firstbin= fXaxis.GetFirst();
6856 lastbin = fXaxis.GetLast();
6857 }
6858 nbins = lastbin - firstbin + 1;
6859 Double_t *xx = new Double_t[nbins];
6860 Double_t nent = fEntries;
6861 Int_t i;
6862 for (i=0;i<nbins;i++) {
6863 xx[i] = RetrieveBinContent(i+firstbin);
6864 }
6865
6866 TH1::SmoothArray(nbins,xx,ntimes);
6867
6868 for (i=0;i<nbins;i++) {
6869 UpdateBinContent(i+firstbin,xx[i]);
6870 }
6871 fEntries = nent;
6872 delete [] xx;
6873
6874 if (gPad) gPad->Modified();
6875}
6876
6877////////////////////////////////////////////////////////////////////////////////
6878/// if flag=kTRUE, underflows and overflows are used by the Fill functions
6879/// in the computation of statistics (mean value, StdDev).
6880/// By default, underflows or overflows are not used.
6881
6882void TH1::StatOverflows(Bool_t flag)
6883{
6884 fgStatOverflows = flag;
6885}
6886
6887////////////////////////////////////////////////////////////////////////////////
6888/// Stream a class object.
6889
6890void TH1::Streamer(TBuffer &b)
6891{
6892 if (b.IsReading()) {
6893 UInt_t R__s, R__c;
6894 Version_t R__v = b.ReadVersion(&R__s, &R__c);
6895 if (fDirectory) fDirectory->Remove(this);
6896 fDirectory = 0;
6897 if (R__v > 2) {
6898 b.ReadClassBuffer(TH1::Class(), this, R__v, R__s, R__c);
6899
6901 fXaxis.SetParent(this);
6902 fYaxis.SetParent(this);
6903 fZaxis.SetParent(this);
6904 TIter next(fFunctions);
6905 TObject *obj;
6906 while ((obj=next())) {
6907 if (obj->InheritsFrom(TF1::Class())) ((TF1*)obj)->SetParent(this);
6908 }
6909 return;
6910 }
6911 //process old versions before automatic schema evolution
6912 TNamed::Streamer(b);
6913 TAttLine::Streamer(b);
6914 TAttFill::Streamer(b);
6915 TAttMarker::Streamer(b);
6916 b >> fNcells;
6917 fXaxis.Streamer(b);
6918 fYaxis.Streamer(b);
6919 fZaxis.Streamer(b);
6920 fXaxis.SetParent(this);
6921 fYaxis.SetParent(this);
6922 fZaxis.SetParent(this);
6923 b >> fBarOffset;
6924 b >> fBarWidth;
6925 b >> fEntries;
6926 b >> fTsumw;
6927 b >> fTsumw2;
6928 b >> fTsumwx;
6929 b >> fTsumwx2;
6930 if (R__v < 2) {
6931 Float_t maximum, minimum, norm;
6932 Float_t *contour=0;
6933 b >> maximum; fMaximum = maximum;
6934 b >> minimum; fMinimum = minimum;
6935 b >> norm; fNormFactor = norm;
6936 Int_t n = b.ReadArray(contour);
6937 fContour.Set(n);
6938 for (Int_t i=0;i<n;i++) fContour.fArray[i] = contour[i];
6939 delete [] contour;
6940 } else {
6941 b >> fMaximum;
6942 b >> fMinimum;
6943 b >> fNormFactor;
6944 fContour.Streamer(b);
6945 }
6946 fSumw2.Streamer(b);
6947 fOption.Streamer(b);
6948 fFunctions->Delete();
6949 fFunctions->Streamer(b);
6950 b.CheckByteCount(R__s, R__c, TH1::IsA());
6951
6952 } else {
6953 b.WriteClassBuffer(TH1::Class(),this);
6954 }
6955}
6956
6957////////////////////////////////////////////////////////////////////////////////
6958/// Print some global quantities for this histogram.
6959/// \param[in] option
6960/// - "base" is given, number of bins and ranges are also printed
6961/// - "range" is given, bin contents and errors are also printed
6962/// for all bins in the current range (default 1-->nbins)
6963/// - "all" is given, bin contents and errors are also printed
6964/// for all bins including under and overflows.
6965
6966void TH1::Print(Option_t *option) const
6967{
6968 if (fBuffer) const_cast<TH1*>(this)->BufferEmpty();
6969 printf( "TH1.Print Name = %s, Entries= %d, Total sum= %g\n",GetName(),Int_t(fEntries),GetSumOfWeights());
6970 TString opt = option;
6971 opt.ToLower();
6972 Int_t all;
6973 if (opt.Contains("all")) all = 0;
6974 else if (opt.Contains("range")) all = 1;
6975 else if (opt.Contains("base")) all = 2;
6976 else return;
6977
6978 Int_t bin, binx, biny, binz;
6979 Int_t firstx=0,lastx=0,firsty=0,lasty=0,firstz=0,lastz=0;
6980 if (all == 0) {
6981 lastx = fXaxis.GetNbins()+1;
6982 if (fDimension > 1) lasty = fYaxis.GetNbins()+1;
6983 if (fDimension > 2) lastz = fZaxis.GetNbins()+1;
6984 } else {
6985 firstx = fXaxis.GetFirst(); lastx = fXaxis.GetLast();
6986 if (fDimension > 1) {firsty = fYaxis.GetFirst(); lasty = fYaxis.GetLast();}
6987 if (fDimension > 2) {firstz = fZaxis.GetFirst(); lastz = fZaxis.GetLast();}
6988 }
6989
6990 if (all== 2) {
6991 printf(" Title = %s\n", GetTitle());
6992 printf(" NbinsX= %d, xmin= %g, xmax=%g", fXaxis.GetNbins(), fXaxis.GetXmin(), fXaxis.GetXmax());
6993 if( fDimension > 1) printf(", NbinsY= %d, ymin= %g, ymax=%g", fYaxis.GetNbins(), fYaxis.GetXmin(), fYaxis.GetXmax());
6994 if( fDimension > 2) printf(", NbinsZ= %d, zmin= %g, zmax=%g", fZaxis.GetNbins(), fZaxis.GetXmin(), fZaxis.GetXmax());
6995 printf("\n");
6996 return;
6997 }
6998
6999 Double_t w,e;
7000 Double_t x,y,z;
7001 if (fDimension == 1) {
7002 for (binx=firstx;binx<=lastx;binx++) {
7003 x = fXaxis.GetBinCenter(binx);
7004 w = RetrieveBinContent(binx);
7005 e = GetBinError(binx);
7006 if(fSumw2.fN) printf(" fSumw[%d]=%g, x=%g, error=%g\n",binx,w,x,e);
7007 else printf(" fSumw[%d]=%g, x=%g\n",binx,w,x);
7008 }
7009 }
7010 if (fDimension == 2) {
7011 for (biny=firsty;biny<=lasty;biny++) {
7012 y = fYaxis.GetBinCenter(biny);
7013 for (binx=firstx;binx<=lastx;binx++) {
7014 bin = GetBin(binx,biny);
7015 x = fXaxis.GetBinCenter(binx);
7016 w = RetrieveBinContent(bin);
7017 e = GetBinError(bin);
7018 if(fSumw2.fN) printf(" fSumw[%d][%d]=%g, x=%g, y=%g, error=%g\n",binx,biny,w,x,y,e);
7019 else printf(" fSumw[%d][%d]=%g, x=%g, y=%g\n",binx,biny,w,x,y);
7020 }
7021 }
7022 }
7023 if (fDimension == 3) {
7024 for (binz=firstz;binz<=lastz;binz++) {
7025 z = fZaxis.GetBinCenter(binz);
7026 for (biny=firsty;biny<=lasty;biny++) {
7027 y = fYaxis.GetBinCenter(biny);
7028 for (binx=firstx;binx<=lastx;binx++) {
7029 bin = GetBin(binx,biny,binz);
7030 x = fXaxis.GetBinCenter(binx);
7031 w = RetrieveBinContent(bin);
7032 e = GetBinError(bin);
7033 if(fSumw2.fN) printf(" fSumw[%d][%d][%d]=%g, x=%g, y=%g, z=%g, error=%g\n",binx,biny,binz,w,x,y,z,e);
7034 else printf(" fSumw[%d][%d][%d]=%g, x=%g, y=%g, z=%g\n",binx,biny,binz,w,x,y,z);
7035 }
7036 }
7037 }
7038 }
7039}
7040
7041////////////////////////////////////////////////////////////////////////////////
7042/// Using the current bin info, recompute the arrays for contents and errors
7043
7044void TH1::Rebuild(Option_t *)
7045{
7046 SetBinsLength();
7047 if (fSumw2.fN) {
7049 }
7050}
7051
7052////////////////////////////////////////////////////////////////////////////////
7053/// Reset this histogram: contents, errors, etc.
7054/// \param[in] option
7055/// - if "ICE" is specified, resets only Integral, Contents and Errors.
7056/// - if "ICES" is specified, resets only Integral, Contents, Errors and Statistics
7057/// This option is used
7058/// - if "M" is specified, resets also Minimum and Maximum
7059
7060void TH1::Reset(Option_t *option)
7061{
7062 // The option "ICE" is used when extending the histogram (in ExtendAxis, LabelInflate, etc..)
7063 // The option "ICES is used in combination with the buffer (see BufferEmpty and BufferFill)
7064
7065 TString opt = option;
7066 opt.ToUpper();
7067 fSumw2.Reset();
7068 if (fIntegral) {delete [] fIntegral; fIntegral = 0;}
7069
7070 if (opt.Contains("M")) {
7071 SetMinimum();
7072 SetMaximum();
7073 }
7074
7075 if (opt.Contains("ICE") && !opt.Contains("S")) return;
7076
7077 // Setting fBuffer[0] = 0 is like resetting the buffer but not deleting it
7078 // But what is the sense of calling BufferEmpty() ? For making the axes ?
7079 // BufferEmpty will update contents that later will be
7080 // reset in calling TH1D::Reset. For this we need to reset the stats afterwards
7081 // It may be needed for computing the axis limits....
7082 if (fBuffer) {BufferEmpty(); fBuffer[0] = 0;}
7083
7084 // need to reset also the statistics
7085 // (needs to be done after calling BufferEmpty() )
7086 fTsumw = 0;
7087 fTsumw2 = 0;
7088 fTsumwx = 0;
7089 fTsumwx2 = 0;
7090 fEntries = 0;
7091
7092 if (opt == "ICES") return;
7093
7094
7095 TObject *stats = fFunctions->FindObject("stats");
7096 fFunctions->Remove(stats);
7097 //special logic to support the case where the same object is
7098 //added multiple times in fFunctions.
7099 //This case happens when the same object is added with different
7100 //drawing modes
7101 TObject *obj;
7102 while ((obj = fFunctions->First())) {
7103 while(fFunctions->Remove(obj)) { }
7104 delete obj;
7105 }
7106 if(stats) fFunctions->Add(stats);
7107 fContour.Set(0);
7108}
7109
7110////////////////////////////////////////////////////////////////////////////////
7111/// Save primitive as a C++ statement(s) on output stream out
7112
7113void TH1::SavePrimitive(std::ostream &out, Option_t *option /*= ""*/)
7114{
7115 // empty the buffer before if it exists
7116 if (fBuffer) BufferEmpty();
7117
7118 Bool_t nonEqiX = kFALSE;
7119 Bool_t nonEqiY = kFALSE;
7120 Bool_t nonEqiZ = kFALSE;
7121 Int_t i;
7122 static Int_t nxaxis = 0;
7123 static Int_t nyaxis = 0;
7124 static Int_t nzaxis = 0;
7125 TString sxaxis="xAxis",syaxis="yAxis",szaxis="zAxis";
7126
7127 // Check if the histogram has equidistant X bins or not. If not, we
7128 // create an array holding the bins.
7129 if (GetXaxis()->GetXbins()->fN && GetXaxis()->GetXbins()->fArray) {
7130 nonEqiX = kTRUE;
7131 nxaxis++;
7132 sxaxis += nxaxis;
7133 out << " Double_t "<<sxaxis<<"[" << GetXaxis()->GetXbins()->fN
7134 << "] = {";
7135 for (i = 0; i < GetXaxis()->GetXbins()->fN; i++) {
7136 if (i != 0) out << ", ";
7137 out << GetXaxis()->GetXbins()->fArray[i];
7138 }
7139 out << "}; " << std::endl;
7140 }
7141 // If the histogram is 2 or 3 dimensional, check if the histogram
7142 // has equidistant Y bins or not. If not, we create an array
7143 // holding the bins.
7144 if (fDimension > 1 && GetYaxis()->GetXbins()->fN &&
7145 GetYaxis()->GetXbins()->fArray) {
7146 nonEqiY = kTRUE;
7147 nyaxis++;
7148 syaxis += nyaxis;
7149 out << " Double_t "<<syaxis<<"[" << GetYaxis()->GetXbins()->fN
7150 << "] = {";
7151 for (i = 0; i < GetYaxis()->GetXbins()->fN; i++) {
7152 if (i != 0) out << ", ";
7153 out << GetYaxis()->GetXbins()->fArray[i];
7154 }
7155 out << "}; " << std::endl;
7156 }
7157 // IF the histogram is 3 dimensional, check if the histogram
7158 // has equidistant Z bins or not. If not, we create an array
7159 // holding the bins.
7160 if (fDimension > 2 && GetZaxis()->GetXbins()->fN &&
7161 GetZaxis()->GetXbins()->fArray) {
7162 nonEqiZ = kTRUE;
7163 nzaxis++;
7164 szaxis += nzaxis;
7165 out << " Double_t "<<szaxis<<"[" << GetZaxis()->GetXbins()->fN
7166 << "] = {";
7167 for (i = 0; i < GetZaxis()->GetXbins()->fN; i++) {
7168 if (i != 0) out << ", ";
7169 out << GetZaxis()->GetXbins()->fArray[i];
7170 }
7171 out << "}; " << std::endl;
7172 }
7173
7174 char quote = '"';
7175 out <<" "<<std::endl;
7176 out <<" "<< ClassName() <<" *";
7177
7178 // Histogram pointer has by default the histogram name with an incremental suffix.
7179 // If the histogram belongs to a graph or a stack the suffix is not added because
7180 // the graph and stack objects are not aware of this new name. Same thing if
7181 // the histogram is drawn with the option COLZ because the TPaletteAxis drawn
7182 // when this option is selected, does not know this new name either.
7183 TString opt = option;
7184 opt.ToLower();
7185 static Int_t hcounter = 0;
7186 TString histName = GetName();
7187 if ( !histName.Contains("Graph")
7188 && !histName.Contains("_stack_")
7189 && !opt.Contains("colz")) {
7190 hcounter++;
7191 histName += "__";
7192 histName += hcounter;
7193 }
7194 histName = gInterpreter-> MapCppName(histName);
7195 const char *hname = histName.Data();
7196 if (!strlen(hname)) hname = "unnamed";
7197 TString savedName = GetName();
7198 this->SetName(hname);
7199 TString t(GetTitle());
7200 t.ReplaceAll("\\","\\\\");
7201 t.ReplaceAll("\"","\\\"");
7202 out << hname << " = new " << ClassName() << "(" << quote
7203 << hname << quote << "," << quote<< t.Data() << quote
7204 << "," << GetXaxis()->GetNbins();
7205 if (nonEqiX)
7206 out << ", "<<sxaxis;
7207 else
7208 out << "," << GetXaxis()->GetXmin()
7209 << "," << GetXaxis()->GetXmax();
7210 if (fDimension > 1) {
7211 out << "," << GetYaxis()->GetNbins();
7212 if (nonEqiY)
7213 out << ", "<<syaxis;
7214 else
7215 out << "," << GetYaxis()->GetXmin()
7216 << "," << GetYaxis()->GetXmax();
7217 }
7218 if (fDimension > 2) {
7219 out << "," << GetZaxis()->GetNbins();
7220 if (nonEqiZ)
7221 out << ", "<<szaxis;
7222 else
7223 out << "," << GetZaxis()->GetXmin()
7224 << "," << GetZaxis()->GetXmax();
7225 }
7226 out << ");" << std::endl;
7227
7228 // save bin contents
7229 Int_t bin;
7230 for (bin=0;bin<fNcells;bin++) {
7231 Double_t bc = RetrieveBinContent(bin);
7232 if (bc) {
7233 out<<" "<<hname<<"->SetBinContent("<<bin<<","<<bc<<");"<<std::endl;
7234 }
7235 }
7236
7237 // save bin errors
7238 if (fSumw2.fN) {
7239 for (bin=0;bin<fNcells;bin++) {
7240 Double_t be = GetBinError(bin);
7241 if (be) {
7242 out<<" "<<hname<<"->SetBinError("<<bin<<","<<be<<");"<<std::endl;
7243 }
7244 }
7245 }
7246
7247 TH1::SavePrimitiveHelp(out, hname, option);
7248 this->SetName(savedName.Data());
7249}
7250
7251////////////////////////////////////////////////////////////////////////////////
7252/// Helper function for the SavePrimitive functions from TH1
7253/// or classes derived from TH1, eg TProfile, TProfile2D.
7254
7255void TH1::SavePrimitiveHelp(std::ostream &out, const char *hname, Option_t *option /*= ""*/)
7256{
7257 char quote = '"';
7258 if (TMath::Abs(GetBarOffset()) > 1e-5) {
7259 out<<" "<<hname<<"->SetBarOffset("<<GetBarOffset()<<");"<<std::endl;
7260 }
7261 if (TMath::Abs(GetBarWidth()-1) > 1e-5) {
7262 out<<" "<<hname<<"->SetBarWidth("<<GetBarWidth()<<");"<<std::endl;
7263 }
7264 if (fMinimum != -1111) {
7265 out<<" "<<hname<<"->SetMinimum("<<fMinimum<<");"<<std::endl;
7266 }
7267 if (fMaximum != -1111) {
7268 out<<" "<<hname<<"->SetMaximum("<<fMaximum<<");"<<std::endl;
7269 }
7270 if (fNormFactor != 0) {
7271 out<<" "<<hname<<"->SetNormFactor("<<fNormFactor<<");"<<std::endl;
7272 }
7273 if (fEntries != 0) {
7274 out<<" "<<hname<<"->SetEntries("<<fEntries<<");"<<std::endl;
7275 }
7276 if (fDirectory == 0) {
7277 out<<" "<<hname<<"->SetDirectory(0);"<<std::endl;
7278 }
7279 if (TestBit(kNoStats)) {
7280 out<<" "<<hname<<"->SetStats(0);"<<std::endl;
7281 }
7282 if (fOption.Length() != 0) {
7283 out<<" "<<hname<<"->SetOption("<<quote<<fOption.Data()<<quote<<");"<<std::endl;
7284 }
7285
7286 // save contour levels
7287 Int_t ncontours = GetContour();
7288 if (ncontours > 0) {
7289 out<<" "<<hname<<"->SetContour("<<ncontours<<");"<<std::endl;
7290 Double_t zlevel;
7291 for (Int_t bin=0;bin<ncontours;bin++) {
7292 if (gPad->GetLogz()) {
7293 zlevel = TMath::Power(10,GetContourLevel(bin));
7294 } else {
7295 zlevel = GetContourLevel(bin);
7296 }
7297 out<<" "<<hname<<"->SetContourLevel("<<bin<<","<<zlevel<<");"<<std::endl;
7298 }
7299 }
7300
7301 // save list of functions
7303 TObject *obj;
7304 static Int_t funcNumber = 0;
7305 while (lnk) {
7306 obj = lnk->GetObject();
7307 obj->SavePrimitive(out,Form("nodraw #%d\n",++funcNumber));
7308 if (obj->InheritsFrom(TF1::Class())) {
7309 TString fname;
7310 fname.Form("%s%d",obj->GetName(),funcNumber);
7311 out << " " << fname << "->SetParent(" << hname << ");\n";
7312 out<<" "<<hname<<"->GetListOfFunctions()->Add("
7313 << fname <<");"<<std::endl;
7314 } else if (obj->InheritsFrom("TPaveStats")) {
7315 out<<" "<<hname<<"->GetListOfFunctions()->Add(ptstats);"<<std::endl;
7316 out<<" ptstats->SetParent("<<hname<<");"<<std::endl;
7317 } else if (obj->InheritsFrom("TPolyMarker")) {
7318 out<<" "<<hname<<"->GetListOfFunctions()->Add("
7319 <<"pmarker ,"<<quote<<lnk->GetOption()<<quote<<");"<<std::endl;
7320 } else {
7321 out<<" "<<hname<<"->GetListOfFunctions()->Add("
7322 <<obj->GetName()
7323 <<","<<quote<<lnk->GetOption()<<quote<<");"<<std::endl;
7324 }
7325 lnk = (TObjOptLink*)lnk->Next();
7326 }
7327
7328 // save attributes
7329 SaveFillAttributes(out,hname,0,1001);
7330 SaveLineAttributes(out,hname,1,1,1);
7331 SaveMarkerAttributes(out,hname,1,1,1);
7332 fXaxis.SaveAttributes(out,hname,"->GetXaxis()");
7333 fYaxis.SaveAttributes(out,hname,"->GetYaxis()");
7334 fZaxis.SaveAttributes(out,hname,"->GetZaxis()");
7335 TString opt = option;
7336 opt.ToLower();
7337 if (!opt.Contains("nodraw")) {
7338 out<<" "<<hname<<"->Draw("
7339 <<quote<<option<<quote<<");"<<std::endl;
7340 }
7341}
7342
7343////////////////////////////////////////////////////////////////////////////////
7344/// Copy current attributes from/to current style
7345
7347{
7348 if (!gStyle) return;
7349 if (gStyle->IsReading()) {
7350 fXaxis.ResetAttAxis("X");
7351 fYaxis.ResetAttAxis("Y");
7352 fZaxis.ResetAttAxis("Z");
7363 Int_t dostat = gStyle->GetOptStat();
7364 if (gStyle->GetOptFit() && !dostat) dostat = 1000000001;
7365 SetStats(dostat);
7366 } else {
7378 }
7379 TIter next(GetListOfFunctions());
7380 TObject *obj;
7381
7382 while ((obj = next())) {
7383 obj->UseCurrentStyle();
7384 }
7385}
7386
7387////////////////////////////////////////////////////////////////////////////////
7388/// For axis = 1,2 or 3 returns the mean value of the histogram along
7389/// X,Y or Z axis.
7390///
7391/// For axis = 11, 12, 13 returns the standard error of the mean value
7392/// of the histogram along X, Y or Z axis
7393///
7394/// Note that the mean value/StdDev is computed using the bins in the currently
7395/// defined range (see TAxis::SetRange). By default the range includes
7396/// all bins from 1 to nbins included, excluding underflows and overflows.
7397/// To force the underflows and overflows in the computation, one must
7398/// call the static function TH1::StatOverflows(kTRUE) before filling
7399/// the histogram.
7400///
7401/// IMPORTANT NOTE: The returned value depends on how the histogram statistics
7402/// are calculated. By default, if no range has been set, the returned mean is
7403/// the (unbinned) one calculated at fill time. If a range has been set, however,
7404/// the mean is calculated using the bins in range, as described above; THIS
7405/// IS TRUE EVEN IF THE RANGE INCLUDES ALL BINS--use TAxis::SetRange(0, 0) to unset
7406/// the range. To ensure that the returned mean (and all other statistics) is
7407/// always that of the binned data stored in the histogram, call TH1::ResetStats.
7408/// See TH1::GetStats.
7409///
7410/// Return mean value of this histogram along the X axis.
7411
7412Double_t TH1::GetMean(Int_t axis) const
7413{
7414 if (axis<1 || (axis>3 && axis<11) || axis>13) return 0;
7415 Double_t stats[kNstat];
7416 for (Int_t i=4;i<kNstat;i++) stats[i] = 0;
7417 GetStats(stats);
7418 if (stats[0] == 0) return 0;
7419 if (axis<4){
7420 Int_t ax[3] = {2,4,7};
7421 return stats[ax[axis-1]]/stats[0];
7422 } else {
7423 // mean error = StdDev / sqrt( Neff )
7424 Double_t stddev = GetStdDev(axis-10);
7426 return ( neff > 0 ? stddev/TMath::Sqrt(neff) : 0. );
7427 }
7428}
7429
7430////////////////////////////////////////////////////////////////////////////////
7431/// Return standard error of mean of this histogram along the X axis.
7432///
7433/// Note that the mean value/StdDev is computed using the bins in the currently
7434/// defined range (see TAxis::SetRange). By default the range includes
7435/// all bins from 1 to nbins included, excluding underflows and overflows.
7436/// To force the underflows and overflows in the computation, one must
7437/// call the static function TH1::StatOverflows(kTRUE) before filling
7438/// the histogram.
7439///
7440/// Also note, that although the definition of standard error doesn't include the
7441/// assumption of normality, many uses of this feature implicitly assume it.
7442///
7443/// IMPORTANT NOTE: The returned value depends on how the histogram statistics
7444/// are calculated. By default, if no range has been set, the returned value is
7445/// the (unbinned) one calculated at fill time. If a range has been set, however,
7446/// the value is calculated using the bins in range, as described above; THIS
7447/// IS TRUE EVEN IF THE RANGE INCLUDES ALL BINS--use TAxis::SetRange(0, 0) to unset
7448/// the range. To ensure that the returned value (and all other statistics) is
7449/// always that of the binned data stored in the histogram, call TH1::ResetStats.
7450/// See TH1::GetStats.
7451
7453{
7454 return GetMean(axis+10);
7455}
7456
7457////////////////////////////////////////////////////////////////////////////////
7458/// Returns the Standard Deviation (Sigma).
7459/// The Sigma estimate is computed as
7460/// \f[
7461/// \sqrt{\frac{1}{N}(\sum(x_i-x_{mean})^2)}
7462/// \f]
7463/// For axis = 1,2 or 3 returns the Sigma value of the histogram along
7464/// X, Y or Z axis
7465/// For axis = 11, 12 or 13 returns the error of StdDev estimation along
7466/// X, Y or Z axis for Normal distribution
7467///
7468/// Note that the mean value/sigma is computed using the bins in the currently
7469/// defined range (see TAxis::SetRange). By default the range includes
7470/// all bins from 1 to nbins included, excluding underflows and overflows.
7471/// To force the underflows and overflows in the computation, one must
7472/// call the static function TH1::StatOverflows(kTRUE) before filling
7473/// the histogram.
7474///
7475/// IMPORTANT NOTE: The returned value depends on how the histogram statistics
7476/// are calculated. By default, if no range has been set, the returned standard
7477/// deviation is the (unbinned) one calculated at fill time. If a range has been
7478/// set, however, the standard deviation is calculated using the bins in range,
7479/// as described above; THIS IS TRUE EVEN IF THE RANGE INCLUDES ALL BINS--use
7480/// TAxis::SetRange(0, 0) to unset the range. To ensure that the returned standard
7481/// deviation (and all other statistics) is always that of the binned data stored
7482/// in the histogram, call TH1::ResetStats. See TH1::GetStats.
7483
7484Double_t TH1::GetStdDev(Int_t axis) const
7485{
7486 if (axis<1 || (axis>3 && axis<11) || axis>13) return 0;
7487
7488 Double_t x, stddev2, stats[kNstat];
7489 for (Int_t i=4;i<kNstat;i++) stats[i] = 0;
7490 GetStats(stats);
7491 if (stats[0] == 0) return 0;
7492 Int_t ax[3] = {2,4,7};
7493 Int_t axm = ax[axis%10 - 1];
7494 x = stats[axm]/stats[0];
7495 // for negative stddev (e.g. when having negative weights) - return stdev=0
7496 stddev2 = TMath::Max( stats[axm+1]/stats[0] -x*x, 0.0 );
7497 if (axis<10)
7498 return TMath::Sqrt(stddev2);
7499 else {
7500 // The right formula for StdDev error depends on 4th momentum (see Kendall-Stuart Vol 1 pag 243)
7501 // formula valid for only gaussian distribution ( 4-th momentum = 3 * sigma^4 )
7503 return ( neff > 0 ? TMath::Sqrt(stddev2/(2*neff) ) : 0. );
7504 }
7505}
7506
7507////////////////////////////////////////////////////////////////////////////////
7508/// Return error of standard deviation estimation for Normal distribution
7509///
7510/// Note that the mean value/StdDev is computed using the bins in the currently
7511/// defined range (see TAxis::SetRange). By default the range includes
7512/// all bins from 1 to nbins included, excluding underflows and overflows.
7513/// To force the underflows and overflows in the computation, one must
7514/// call the static function TH1::StatOverflows(kTRUE) before filling
7515/// the histogram.
7516///
7517/// Value returned is standard deviation of sample standard deviation.
7518/// Note that it is an approximated value which is valid only in the case that the
7519/// original data distribution is Normal. The correct one would require
7520/// the 4-th momentum value, which cannot be accurately estimated from a histogram since
7521/// the x-information for all entries is not kept.
7522///
7523/// IMPORTANT NOTE: The returned value depends on how the histogram statistics
7524/// are calculated. By default, if no range has been set, the returned value is
7525/// the (unbinned) one calculated at fill time. If a range has been set, however,
7526/// the value is calculated using the bins in range, as described above; THIS
7527/// IS TRUE EVEN IF THE RANGE INCLUDES ALL BINS--use TAxis::SetRange(0, 0) to unset
7528/// the range. To ensure that the returned value (and all other statistics) is
7529/// always that of the binned data stored in the histogram, call TH1::ResetStats.
7530/// See TH1::GetStats.
7531
7533{
7534 return GetStdDev(axis+10);
7535}
7536
7537////////////////////////////////////////////////////////////////////////////////
7538/// - For axis = 1, 2 or 3 returns skewness of the histogram along x, y or z axis.
7539/// - For axis = 11, 12 or 13 returns the approximate standard error of skewness
7540/// of the histogram along x, y or z axis
7541///
7542///Note, that since third and fourth moment are not calculated
7543///at the fill time, skewness and its standard error are computed bin by bin
7544///
7545/// IMPORTANT NOTE: The returned value depends on how the histogram statistics
7546/// are calculated. See TH1::GetMean and TH1::GetStdDev.
7547
7549{
7550
7551 if (axis > 0 && axis <= 3){
7552
7553 Double_t mean = GetMean(axis);
7554 Double_t stddev = GetStdDev(axis);
7555 Double_t stddev3 = stddev*stddev*stddev;
7556
7557 Int_t firstBinX = fXaxis.GetFirst();
7558 Int_t lastBinX = fXaxis.GetLast();
7559 Int_t firstBinY = fYaxis.GetFirst();
7560 Int_t lastBinY = fYaxis.GetLast();
7561 Int_t firstBinZ = fZaxis.GetFirst();
7562 Int_t lastBinZ = fZaxis.GetLast();
7563 // include underflow/overflow if TH1::StatOverflows(kTRUE) in case no range is set on the axis
7566 if (firstBinX == 1) firstBinX = 0;
7567 if (lastBinX == fXaxis.GetNbins() ) lastBinX += 1;
7568 }
7570 if (firstBinY == 1) firstBinY = 0;
7571 if (lastBinY == fYaxis.GetNbins() ) lastBinY += 1;
7572 }
7574 if (firstBinZ == 1) firstBinZ = 0;
7575 if (lastBinZ == fZaxis.GetNbins() ) lastBinZ += 1;
7576 }
7577 }
7578
7579 Double_t x = 0;
7580 Double_t sum=0;
7581 Double_t np=0;
7582 for (Int_t binx = firstBinX; binx <= lastBinX; binx++) {
7583 for (Int_t biny = firstBinY; biny <= lastBinY; biny++) {
7584 for (Int_t binz = firstBinZ; binz <= lastBinZ; binz++) {
7585 if (axis==1 ) x = fXaxis.GetBinCenter(binx);
7586 else if (axis==2 ) x = fYaxis.GetBinCenter(biny);
7587 else if (axis==3 ) x = fZaxis.GetBinCenter(binz);
7588 Double_t w = GetBinContent(binx,biny,binz);
7589 np+=w;
7590 sum+=w*(x-mean)*(x-mean)*(x-mean);
7591 }
7592 }
7593 }
7594 sum/=np*stddev3;
7595 return sum;
7596 }
7597 else if (axis > 10 && axis <= 13) {
7598 //compute standard error of skewness
7599 // assume parent normal distribution use formula from Kendall-Stuart, Vol 1 pag 243, second edition
7601 return ( neff > 0 ? TMath::Sqrt(6./neff ) : 0. );
7602 }
7603 else {
7604 Error("GetSkewness", "illegal value of parameter");
7605 return 0;
7606 }
7607}
7608
7609////////////////////////////////////////////////////////////////////////////////
7610/// - For axis =1, 2 or 3 returns kurtosis of the histogram along x, y or z axis.
7611/// Kurtosis(gaussian(0, 1)) = 0.
7612/// - For axis =11, 12 or 13 returns the approximate standard error of kurtosis
7613/// of the histogram along x, y or z axis
7614////
7615/// Note, that since third and fourth moment are not calculated
7616/// at the fill time, kurtosis and its standard error are computed bin by bin
7617///
7618/// IMPORTANT NOTE: The returned value depends on how the histogram statistics
7619/// are calculated. See TH1::GetMean and TH1::GetStdDev.
7620
7622{
7623 if (axis > 0 && axis <= 3){
7624
7625 Double_t mean = GetMean(axis);
7626 Double_t stddev = GetStdDev(axis);
7627 Double_t stddev4 = stddev*stddev*stddev*stddev;
7628
7629 Int_t firstBinX = fXaxis.GetFirst();
7630 Int_t lastBinX = fXaxis.GetLast();
7631 Int_t firstBinY = fYaxis.GetFirst();
7632 Int_t lastBinY = fYaxis.GetLast();
7633 Int_t firstBinZ = fZaxis.GetFirst();
7634 Int_t lastBinZ = fZaxis.GetLast();
7635 // include underflow/overflow if TH1::StatOverflows(kTRUE) in case no range is set on the axis
7638 if (firstBinX == 1) firstBinX = 0;
7639 if (lastBinX == fXaxis.GetNbins() ) lastBinX += 1;
7640 }
7642 if (firstBinY == 1) firstBinY = 0;
7643 if (lastBinY == fYaxis.GetNbins() ) lastBinY += 1;
7644 }
7646 if (firstBinZ == 1) firstBinZ = 0;
7647 if (lastBinZ == fZaxis.GetNbins() ) lastBinZ += 1;
7648 }
7649 }
7650
7651 Double_t x = 0;
7652 Double_t sum=0;
7653 Double_t np=0;
7654 for (Int_t binx = firstBinX; binx <= lastBinX; binx++) {
7655 for (Int_t biny = firstBinY; biny <= lastBinY; biny++) {
7656 for (Int_t binz = firstBinZ; binz <= lastBinZ; binz++) {
7657 if (axis==1 ) x = fXaxis.GetBinCenter(binx);
7658 else if (axis==2 ) x = fYaxis.GetBinCenter(biny);
7659 else if (axis==3 ) x = fZaxis.GetBinCenter(binz);
7660 Double_t w = GetBinContent(binx,biny,binz);
7661 np+=w;
7662 sum+=w*(x-mean)*(x-mean)*(x-mean)*(x-mean);
7663 }
7664 }
7665 }
7666 sum/=(np*stddev4);
7667 return sum-3;
7668
7669 } else if (axis > 10 && axis <= 13) {
7670 //compute standard error of skewness
7671 // assume parent normal distribution use formula from Kendall-Stuart, Vol 1 pag 243, second edition
7673 return ( neff > 0 ? TMath::Sqrt(24./neff ) : 0. );
7674 }
7675 else {
7676 Error("GetKurtosis", "illegal value of parameter");
7677 return 0;
7678 }
7679}
7680
7681////////////////////////////////////////////////////////////////////////////////
7682/// fill the array stats from the contents of this histogram
7683/// The array stats must be correctly dimensioned in the calling program.
7684///
7685/// ~~~ {.cpp}
7686/// stats[0] = sumw
7687/// stats[1] = sumw2
7688/// stats[2] = sumwx
7689/// stats[3] = sumwx2
7690/// ~~~
7691///
7692/// If no axis-subrange is specified (via TAxis::SetRange), the array stats
7693/// is simply a copy of the statistics quantities computed at filling time.
7694/// If a sub-range is specified, the function recomputes these quantities
7695/// from the bin contents in the current axis range.
7696///
7697/// IMPORTANT NOTE: This means that the returned statistics are context-dependent.
7698/// If TAxis::kAxisRange, the returned statistics are dependent on the binning;
7699/// otherwise, they are a copy of the histogram statistics computed at fill time,
7700/// which are unbinned by default (calling TH1::ResetStats forces them to use
7701/// binned statistics). You can reset TAxis::kAxisRange using TAxis::SetRange(0, 0).
7702///
7703/// Note that the mean value/StdDev is computed using the bins in the currently
7704/// defined range (see TAxis::SetRange). By default the range includes
7705/// all bins from 1 to nbins included, excluding underflows and overflows.
7706/// To force the underflows and overflows in the computation, one must
7707/// call the static function TH1::StatOverflows(kTRUE) before filling
7708/// the histogram.
7709
7710void TH1::GetStats(Double_t *stats) const
7711{
7712 if (fBuffer) ((TH1*)this)->BufferEmpty();
7713
7714 // Loop on bins (possibly including underflows/overflows)
7715 Int_t bin, binx;
7716 Double_t w,err;
7717 Double_t x;
7718 // identify the case of labels with extension of axis range
7719 // in this case the statistics in x does not make any sense
7720 Bool_t labelHist = ((const_cast<TAxis&>(fXaxis)).GetLabels() && fXaxis.CanExtend() );
7721 // fTsumw == 0 && fEntries > 0 is a special case when uses SetBinContent or calls ResetStats before
7722 if ( (fTsumw == 0 && fEntries > 0) || fXaxis.TestBit(TAxis::kAxisRange) ) {
7723 for (bin=0;bin<4;bin++) stats[bin] = 0;
7724
7725 Int_t firstBinX = fXaxis.GetFirst();
7726 Int_t lastBinX = fXaxis.GetLast();
7727 // include underflow/overflow if TH1::StatOverflows(kTRUE) in case no range is set on the axis
7729 if (firstBinX == 1) firstBinX = 0;
7730 if (lastBinX == fXaxis.GetNbins() ) lastBinX += 1;
7731 }
7732 for (binx = firstBinX; binx <= lastBinX; binx++) {
7733 x = fXaxis.GetBinCenter(binx);
7734 //w = TMath::Abs(RetrieveBinContent(binx));
7735 // not sure what to do here if w < 0
7736 w = RetrieveBinContent(binx);
7737 err = TMath::Abs(GetBinError(binx));
7738 stats[0] += w;
7739 stats[1] += err*err;
7740 // statistics in x makes sense only for not labels histograms
7741 if (!labelHist) {
7742 stats[2] += w*x;
7743 stats[3] += w*x*x;
7744 }
7745 }
7746 // if (stats[0] < 0) {
7747 // // in case total is negative do something ??
7748 // stats[0] = 0;
7749 // }
7750 } else {
7751 stats[0] = fTsumw;
7752 stats[1] = fTsumw2;
7753 stats[2] = fTsumwx;
7754 stats[3] = fTsumwx2;
7755 }
7756}
7757
7758////////////////////////////////////////////////////////////////////////////////
7759/// Replace current statistics with the values in array stats
7760
7761void TH1::PutStats(Double_t *stats)
7762{
7763 fTsumw = stats[0];
7764 fTsumw2 = stats[1];
7765 fTsumwx = stats[2];
7766 fTsumwx2 = stats[3];
7767}
7768
7769////////////////////////////////////////////////////////////////////////////////
7770/// Reset the statistics including the number of entries
7771/// and replace with values calculated from bin content
7772///
7773/// The number of entries is set to the total bin content or (in case of weighted histogram)
7774/// to number of effective entries
7775///
7776/// Note that, by default, before calling this function, statistics are those
7777/// computed at fill time, which are unbinned. See TH1::GetStats.
7778
7779void TH1::ResetStats()
7780{
7781 Double_t stats[kNstat] = {0};
7782 fTsumw = 0;
7783 fEntries = 1; // to force re-calculation of the statistics in TH1::GetStats
7784 GetStats(stats);
7785 PutStats(stats);
7787 // use effective entries for weighted histograms: (sum_w) ^2 / sum_w2
7788 if (fSumw2.fN > 0 && fTsumw > 0 && stats[1] > 0 ) fEntries = stats[0]*stats[0]/ stats[1];
7789}
7790
7791////////////////////////////////////////////////////////////////////////////////
7792/// Return the sum of weights excluding under/overflows.
7793
7795{
7796 if (fBuffer) const_cast<TH1*>(this)->BufferEmpty();
7797
7798 Int_t bin,binx,biny,binz;
7799 Double_t sum =0;
7800 for(binz=1; binz<=fZaxis.GetNbins(); binz++) {
7801 for(biny=1; biny<=fYaxis.GetNbins(); biny++) {
7802 for(binx=1; binx<=fXaxis.GetNbins(); binx++) {
7803 bin = GetBin(binx,biny,binz);
7804 sum += RetrieveBinContent(bin);
7805 }
7806 }
7807 }
7808 return sum;
7809}
7810
7811////////////////////////////////////////////////////////////////////////////////
7812///Return integral of bin contents. Only bins in the bins range are considered.
7813///
7814/// By default the integral is computed as the sum of bin contents in the range.
7815/// if option "width" is specified, the integral is the sum of
7816/// the bin contents multiplied by the bin width in x.
7817
7818Double_t TH1::Integral(Option_t *option) const
7819{
7820 return Integral(fXaxis.GetFirst(),fXaxis.GetLast(),option);
7821}
7822
7823////////////////////////////////////////////////////////////////////////////////
7824/// Return integral of bin contents in range [binx1,binx2].
7825///
7826/// By default the integral is computed as the sum of bin contents in the range.
7827/// if option "width" is specified, the integral is the sum of
7828/// the bin contents multiplied by the bin width in x.
7829
7830Double_t TH1::Integral(Int_t binx1, Int_t binx2, Option_t *option) const
7831{
7832 double err = 0;
7833 return DoIntegral(binx1,binx2,0,-1,0,-1,err,option);
7834}
7835
7836////////////////////////////////////////////////////////////////////////////////
7837/// Return integral of bin contents in range [binx1,binx2] and its error.
7838///
7839/// By default the integral is computed as the sum of bin contents in the range.
7840/// if option "width" is specified, the integral is the sum of
7841/// the bin contents multiplied by the bin width in x.
7842/// the error is computed using error propagation from the bin errors assuming that
7843/// all the bins are uncorrelated
7844
7845Double_t TH1::IntegralAndError(Int_t binx1, Int_t binx2, Double_t & error, Option_t *option) const
7846{
7847 return DoIntegral(binx1,binx2,0,-1,0,-1,error,option,kTRUE);
7848}
7849
7850////////////////////////////////////////////////////////////////////////////////
7851/// Internal function compute integral and optionally the error between the limits
7852/// specified by the bin number values working for all histograms (1D, 2D and 3D)
7853
7854Double_t TH1::DoIntegral(Int_t binx1, Int_t binx2, Int_t biny1, Int_t biny2, Int_t binz1, Int_t binz2, Double_t & error ,
7855 Option_t *option, Bool_t doError) const
7856{
7857 if (fBuffer) ((TH1*)this)->BufferEmpty();
7858
7859 Int_t nx = GetNbinsX() + 2;
7860 if (binx1 < 0) binx1 = 0;
7861 if (binx2 >= nx || binx2 < binx1) binx2 = nx - 1;
7862
7863 if (GetDimension() > 1) {
7864 Int_t ny = GetNbinsY() + 2;
7865 if (biny1 < 0) biny1 = 0;
7866 if (biny2 >= ny || biny2 < biny1) biny2 = ny - 1;
7867 } else {
7868 biny1 = 0; biny2 = 0;
7869 }
7870
7871 if (GetDimension() > 2) {
7872 Int_t nz = GetNbinsZ() + 2;
7873 if (binz1 < 0) binz1 = 0;
7874 if (binz2 >= nz || binz2 < binz1) binz2 = nz - 1;
7875 } else {
7876 binz1 = 0; binz2 = 0;
7877 }
7878
7879 // - Loop on bins in specified range
7880 TString opt = option;
7881 opt.ToLower();
7883 if (opt.Contains("width")) width = kTRUE;
7884
7885
7886 Double_t dx = 1., dy = .1, dz =.1;
7887 Double_t integral = 0;
7888 Double_t igerr2 = 0;
7889 for (Int_t binx = binx1; binx <= binx2; ++binx) {
7890 if (width) dx = fXaxis.GetBinWidth(binx);
7891 for (Int_t biny = biny1; biny <= biny2; ++biny) {
7892 if (width) dy = fYaxis.GetBinWidth(biny);
7893 for (Int_t binz = binz1; binz <= binz2; ++binz) {
7894 Int_t bin = GetBin(binx, biny, binz);
7895 Double_t dv = 0.0;
7896 if (width) {
7897 dz = fZaxis.GetBinWidth(binz);
7898 dv = dx * dy * dz;
7899 integral += RetrieveBinContent(bin) * dv;
7900 } else {
7901 integral += RetrieveBinContent(bin);
7902 }
7903 if (doError) {
7904 if (width) igerr2 += GetBinErrorSqUnchecked(bin) * dv * dv;
7905 else igerr2 += GetBinErrorSqUnchecked(bin);
7906 }
7907 }
7908 }
7909 }
7910
7911 if (doError) error = TMath::Sqrt(igerr2);
7912 return integral;
7913}
7914
7915////////////////////////////////////////////////////////////////////////////////
7916/// Statistical test of compatibility in shape between
7917/// this histogram and h2, using the Anderson-Darling 2 sample test.
7918///
7919/// The AD 2 sample test formula are derived from the paper
7920/// F.W Scholz, M.A. Stephens "k-Sample Anderson-Darling Test".
7921///
7922/// The test is implemented in root in the ROOT::Math::GoFTest class
7923/// It is the same formula ( (6) in the paper), and also shown in
7924/// [this preprint](http://arxiv.org/pdf/0804.0380v1.pdf)
7925///
7926/// Binned data are considered as un-binned data
7927/// with identical observation happening in the bin center.
7928///
7929/// \param[in] option is a character string to specify options
7930/// - "D" Put out a line of "Debug" printout
7931/// - "T" Return the normalized A-D test statistic
7932///
7933/// - Note1: Underflow and overflow are not considered in the test
7934/// - Note2: The test works only for un-weighted histogram (i.e. representing counts)
7935/// - Note3: The histograms are not required to have the same X axis
7936/// - Note4: The test works only for 1-dimensional histograms
7937
7938Double_t TH1::AndersonDarlingTest(const TH1 *h2, Option_t *option) const
7939{
7940 Double_t advalue = 0;
7941 Double_t pvalue = AndersonDarlingTest(h2, advalue);
7942
7943 TString opt = option;
7944 opt.ToUpper();
7945 if (opt.Contains("D") ) {
7946 printf(" AndersonDarlingTest Prob = %g, AD TestStatistic = %g\n",pvalue,advalue);
7947 }
7948 if (opt.Contains("T") ) return advalue;
7949
7950 return pvalue;
7951}
7952
7953////////////////////////////////////////////////////////////////////////////////
7954/// Same function as above but returning also the test statistic value
7955
7956Double_t TH1::AndersonDarlingTest(const TH1 *h2, Double_t & advalue) const
7957{
7958 if (GetDimension() != 1 || h2->GetDimension() != 1) {
7959 Error("AndersonDarlingTest","Histograms must be 1-D");
7960 return -1;
7961 }
7962
7963 // empty the buffer. Probably we could add as an unbinned test
7964 if (fBuffer) ((TH1*)this)->BufferEmpty();
7965
7966 // use the BinData class
7967 ROOT::Fit::BinData data1;
7968 ROOT::Fit::BinData data2;
7969
7970 ROOT::Fit::FillData(data1, this, 0);
7971 ROOT::Fit::FillData(data2, h2, 0);
7972
7973 double pvalue;
7974 ROOT::Math::GoFTest::AndersonDarling2SamplesTest(data1,data2, pvalue,advalue);
7975
7976 return pvalue;
7977}
7978
7979////////////////////////////////////////////////////////////////////////////////
7980/// Statistical test of compatibility in shape between
7981/// this histogram and h2, using Kolmogorov test.
7982/// Note that the KolmogorovTest (KS) test should in theory be used only for unbinned data
7983/// and not for binned data as in the case of the histogram (see NOTE 3 below).
7984/// So, before using this method blindly, read the NOTE 3.
7985///
7986/// Default: Ignore under- and overflow bins in comparison
7987///
7988/// \param[in] h2 histogram
7989/// \param[in] option is a character string to specify options
7990/// - "U" include Underflows in test (also for 2-dim)
7991/// - "O" include Overflows (also valid for 2-dim)
7992/// - "N" include comparison of normalizations
7993/// - "D" Put out a line of "Debug" printout
7994/// - "M" Return the Maximum Kolmogorov distance instead of prob
7995/// - "X" Run the pseudo experiments post-processor with the following procedure:
7996/// make pseudoexperiments based on random values from the parent distribution,
7997/// compare the KS distance of the pseudoexperiment to the parent
7998/// distribution, and count all the KS values above the value
7999/// obtained from the original data to Monte Carlo distribution.
8000/// The number of pseudo-experiments nEXPT is currently fixed at 1000.
8001/// The function returns the probability.
8002/// (thanks to Ben Kilminster to submit this procedure). Note that
8003/// this option "X" is much slower.
8004///
8005/// The returned function value is the probability of test
8006/// (much less than one means NOT compatible)
8007///
8008/// Code adapted by Rene Brun from original HBOOK routine HDIFF
8009///
8010/// NOTE1
8011/// A good description of the Kolmogorov test can be seen at:
8012/// http://www.itl.nist.gov/div898/handbook/eda/section3/eda35g.htm
8013///
8014/// NOTE2
8015/// see also alternative function TH1::Chi2Test
8016/// The Kolmogorov test is assumed to give better results than Chi2Test
8017/// in case of histograms with low statistics.
8018///
8019/// NOTE3 (Jan Conrad, Fred James)
8020/// "The returned value PROB is calculated such that it will be
8021/// uniformly distributed between zero and one for compatible histograms,
8022/// provided the data are not binned (or the number of bins is very large
8023/// compared with the number of events). Users who have access to unbinned
8024/// data and wish exact confidence levels should therefore not put their data
8025/// into histograms, but should call directly TMath::KolmogorovTest. On
8026/// the other hand, since TH1 is a convenient way of collecting data and
8027/// saving space, this function has been provided. However, the values of
8028/// PROB for binned data will be shifted slightly higher than expected,
8029/// depending on the effects of the binning. For example, when comparing two
8030/// uniform distributions of 500 events in 100 bins, the values of PROB,
8031/// instead of being exactly uniformly distributed between zero and one, have
8032/// a mean value of about 0.56. We can apply a useful
8033/// rule: As long as the bin width is small compared with any significant
8034/// physical effect (for example the experimental resolution) then the binning
8035/// cannot have an important effect. Therefore, we believe that for all
8036/// practical purposes, the probability value PROB is calculated correctly
8037/// provided the user is aware that:
8038///
8039/// 1. The value of PROB should not be expected to have exactly the correct
8040/// distribution for binned data.
8041/// 2. The user is responsible for seeing to it that the bin widths are
8042/// small compared with any physical phenomena of interest.
8043/// 3. The effect of binning (if any) is always to make the value of PROB
8044/// slightly too big. That is, setting an acceptance criterion of (PROB>0.05
8045/// will assure that at most 5% of truly compatible histograms are rejected,
8046/// and usually somewhat less."
8047///
8048/// Note also that for GoF test of unbinned data ROOT provides also the class
8049/// ROOT::Math::GoFTest. The class has also method for doing one sample tests
8050/// (i.e. comparing the data with a given distribution).
8051
8052Double_t TH1::KolmogorovTest(const TH1 *h2, Option_t *option) const
8053{
8054 TString opt = option;
8055 opt.ToUpper();
8056
8057 Double_t prob = 0;
8058 TH1 *h1 = (TH1*)this;
8059 if (h2 == 0) return 0;
8060 const TAxis *axis1 = h1->GetXaxis();
8061 const TAxis *axis2 = h2->GetXaxis();
8062 Int_t ncx1 = axis1->GetNbins();
8063 Int_t ncx2 = axis2->GetNbins();
8064
8065 // Check consistency of dimensions
8066 if (h1->GetDimension() != 1 || h2->GetDimension() != 1) {
8067 Error("KolmogorovTest","Histograms must be 1-D\n");
8068 return 0;
8069 }
8070
8071 // Check consistency in number of channels
8072 if (ncx1 != ncx2) {
8073 Error("KolmogorovTest","Histograms have different number of bins, %d and %d\n",ncx1,ncx2);
8074 return 0;
8075 }
8076
8077 // empty the buffer. Probably we could add as an unbinned test
8078 if (fBuffer) ((TH1*)this)->BufferEmpty();
8079
8080 // Check consistency in bin edges
8081 for(Int_t i = 1; i <= axis1->GetNbins() + 1; ++i) {
8082 if(!TMath::AreEqualRel(axis1->GetBinLowEdge(i), axis2->GetBinLowEdge(i), 1.E-15)) {
8083 Error("KolmogorovTest","Histograms are not consistent: they have different bin edges");
8084 return 0;
8085 }
8086 }
8087
8088 Bool_t afunc1 = kFALSE;
8089 Bool_t afunc2 = kFALSE;
8090 Double_t sum1 = 0, sum2 = 0;
8091 Double_t ew1, ew2, w1 = 0, w2 = 0;
8092 Int_t bin;
8093 Int_t ifirst = 1;
8094 Int_t ilast = ncx1;
8095 // integral of all bins (use underflow/overflow if option)
8096 if (opt.Contains("U")) ifirst = 0;
8097 if (opt.Contains("O")) ilast = ncx1 +1;
8098 for (bin = ifirst; bin <= ilast; bin++) {
8099 sum1 += h1->RetrieveBinContent(bin);
8100 sum2 += h2->RetrieveBinContent(bin);
8101 ew1 = h1->GetBinError(bin);
8102 ew2 = h2->GetBinError(bin);
8103 w1 += ew1*ew1;
8104 w2 += ew2*ew2;
8105 }
8106 if (sum1 == 0) {
8107 Error("KolmogorovTest","Histogram1 %s integral is zero\n",h1->GetName());
8108 return 0;
8109 }
8110 if (sum2 == 0) {
8111 Error("KolmogorovTest","Histogram2 %s integral is zero\n",h2->GetName());
8112 return 0;
8113 }
8114
8115 // calculate the effective entries.
8116 // the case when errors are zero (w1 == 0 or w2 ==0) are equivalent to
8117 // compare to a function. In that case the rescaling is done only on sqrt(esum2) or sqrt(esum1)
8118 Double_t esum1 = 0, esum2 = 0;
8119 if (w1 > 0)
8120 esum1 = sum1 * sum1 / w1;
8121 else
8122 afunc1 = kTRUE; // use later for calculating z
8123
8124 if (w2 > 0)
8125 esum2 = sum2 * sum2 / w2;
8126 else
8127 afunc2 = kTRUE; // use later for calculating z
8128
8129 if (afunc2 && afunc1) {
8130 Error("KolmogorovTest","Errors are zero for both histograms\n");
8131 return 0;
8132 }
8133
8134
8135 Double_t s1 = 1/sum1;
8136 Double_t s2 = 1/sum2;
8137
8138 // Find largest difference for Kolmogorov Test
8139 Double_t dfmax =0, rsum1 = 0, rsum2 = 0;
8140
8141 for (bin=ifirst;bin<=ilast;bin++) {
8142 rsum1 += s1*h1->RetrieveBinContent(bin);
8143 rsum2 += s2*h2->RetrieveBinContent(bin);
8144 dfmax = TMath::Max(dfmax,TMath::Abs(rsum1-rsum2));
8145 }
8146
8147 // Get Kolmogorov probability
8148 Double_t z, prb1=0, prb2=0, prb3=0;
8149
8150 // case h1 is exact (has zero errors)
8151 if (afunc1)
8152 z = dfmax*TMath::Sqrt(esum2);
8153 // case h2 has zero errors
8154 else if (afunc2)
8155 z = dfmax*TMath::Sqrt(esum1);
8156 else
8157 // for comparison between two data sets
8158 z = dfmax*TMath::Sqrt(esum1*esum2/(esum1+esum2));
8159
8160 prob = TMath::KolmogorovProb(z);
8161
8162 // option N to combine normalization makes sense if both afunc1 and afunc2 are false
8163 if (opt.Contains("N") && !(afunc1 || afunc2 ) ) {
8164 // Combine probabilities for shape and normalization,
8165 prb1 = prob;
8166 Double_t d12 = esum1-esum2;
8167 Double_t chi2 = d12*d12/(esum1+esum2);
8168 prb2 = TMath::Prob(chi2,1);
8169 // see Eadie et al., section 11.6.2
8170 if (prob > 0 && prb2 > 0) prob *= prb2*(1-TMath::Log(prob*prb2));
8171 else prob = 0;
8172 }
8173 // X option. Pseudo-experiments post-processor to determine KS probability
8174 const Int_t nEXPT = 1000;
8175 if (opt.Contains("X") && !(afunc1 || afunc2 ) ) {
8176 Double_t dSEXPT;
8177 TH1 *h1_cpy = (TH1 *)(gDirectory ? gDirectory->CloneObject(this, kFALSE) : gROOT->CloneObject(this, kFALSE));
8178 TH1 *h1Expt = (TH1*)(gDirectory ? gDirectory->CloneObject(this,kFALSE) : gROOT->CloneObject(this,kFALSE));
8179 TH1 *h2Expt = (TH1*)(gDirectory ? gDirectory->CloneObject(this,kFALSE) : gROOT->CloneObject(this,kFALSE));
8180
8181 if (GetMinimum() < 0.0) {
8182 // we need to create a new histogram
8183 // With negative bins we can't draw random samples in a meaningful way.
8184 Warning("KolmogorovTest", "Detected bins with negative weights, these have been ignored and output might be "
8185 "skewed. Reduce number of bins for histogram?");
8186 while (h1_cpy->GetMinimum() < 0.0) {
8187 Int_t idx = h1_cpy->GetMinimumBin();
8188 h1_cpy->SetBinContent(idx, 0.0);
8189 }
8190 }
8191
8192 // make nEXPT experiments (this should be a parameter)
8193 prb3 = 0;
8194 for (Int_t i=0; i < nEXPT; i++) {
8195 h1Expt->Reset();
8196 h2Expt->Reset();
8197 h1Expt->FillRandom(h1_cpy, (Int_t)esum1);
8198 h2Expt->FillRandom(h1_cpy, (Int_t)esum2);
8199 dSEXPT = h1Expt->KolmogorovTest(h2Expt,"M");
8200 if (dSEXPT>dfmax) prb3 += 1.0;
8201 }
8202 prb3 /= (Double_t)nEXPT;
8203 delete h1_cpy;
8204 delete h1Expt;
8205 delete h2Expt;
8206 }
8207
8208 // debug printout
8209 if (opt.Contains("D")) {
8210 printf(" Kolmo Prob h1 = %s, sum bin content =%g effective entries =%g\n",h1->GetName(),sum1,esum1);
8211 printf(" Kolmo Prob h2 = %s, sum bin content =%g effective entries =%g\n",h2->GetName(),sum2,esum2);
8212 printf(" Kolmo Prob = %g, Max Dist = %g\n",prob,dfmax);
8213 if (opt.Contains("N"))
8214 printf(" Kolmo Prob = %f for shape alone, =%f for normalisation alone\n",prb1,prb2);
8215 if (opt.Contains("X"))
8216 printf(" Kolmo Prob = %f with %d pseudo-experiments\n",prb3,nEXPT);
8217 }
8218 // This numerical error condition should never occur:
8219 if (TMath::Abs(rsum1-1) > 0.002) Warning("KolmogorovTest","Numerical problems with h1=%s\n",h1->GetName());
8220 if (TMath::Abs(rsum2-1) > 0.002) Warning("KolmogorovTest","Numerical problems with h2=%s\n",h2->GetName());
8221
8222 if(opt.Contains("M")) return dfmax;
8223 else if(opt.Contains("X")) return prb3;
8224 else return prob;
8225}
8226
8227////////////////////////////////////////////////////////////////////////////////
8228/// Replace bin contents by the contents of array content
8229
8230void TH1::SetContent(const Double_t *content)
8231{
8232 fEntries = fNcells;
8233 fTsumw = 0;
8234 for (Int_t i = 0; i < fNcells; ++i) UpdateBinContent(i, content[i]);
8235}
8236
8237////////////////////////////////////////////////////////////////////////////////
8238/// Return contour values into array levels if pointer levels is non zero.
8239///
8240/// The function returns the number of contour levels.
8241/// see GetContourLevel to return one contour only
8242
8244{
8245 Int_t nlevels = fContour.fN;
8246 if (levels) {
8247 if (nlevels == 0) {
8248 nlevels = 20;
8249 SetContour(nlevels);
8250 } else {
8251 if (TestBit(kUserContour) == 0) SetContour(nlevels);
8252 }
8253 for (Int_t level=0; level<nlevels; level++) levels[level] = fContour.fArray[level];
8254 }
8255 return nlevels;
8256}
8257
8258////////////////////////////////////////////////////////////////////////////////
8259/// Return value of contour number level.
8260/// Use GetContour to return the array of all contour levels
8261
8263{
8264 return (level >= 0 && level < fContour.fN) ? fContour.fArray[level] : 0.0;
8265}
8266
8267////////////////////////////////////////////////////////////////////////////////
8268/// Return the value of contour number "level" in Pad coordinates.
8269/// ie: if the Pad is in log scale along Z it returns le log of the contour level
8270/// value. See GetContour to return the array of all contour levels
8271
8273{
8274 if (level <0 || level >= fContour.fN) return 0;
8275 Double_t zlevel = fContour.fArray[level];
8276
8277 // In case of user defined contours and Pad in log scale along Z,
8278 // fContour.fArray doesn't contain the log of the contour whereas it does
8279 // in case of equidistant contours.
8280 if (gPad && gPad->GetLogz() && TestBit(kUserContour)) {
8281 if (zlevel <= 0) return 0;
8282 zlevel = TMath::Log10(zlevel);
8283 }
8284 return zlevel;
8285}
8286
8287////////////////////////////////////////////////////////////////////////////////
8288/// Set the maximum number of entries to be kept in the buffer.
8289
8290void TH1::SetBuffer(Int_t buffersize, Option_t * /*option*/)
8291{
8292 if (fBuffer) {
8293 BufferEmpty();
8294 delete [] fBuffer;
8295 fBuffer = 0;
8296 }
8297 if (buffersize <= 0) {
8298 fBufferSize = 0;
8299 return;
8300 }
8301 if (buffersize < 100) buffersize = 100;
8302 fBufferSize = 1 + buffersize*(fDimension+1);
8304 memset(fBuffer,0,sizeof(Double_t)*fBufferSize);
8305}
8306
8307////////////////////////////////////////////////////////////////////////////////
8308/// Set the number and values of contour levels.
8309///
8310/// By default the number of contour levels is set to 20. The contours values
8311/// in the array "levels" should be specified in increasing order.
8312///
8313/// if argument levels = 0 or missing, equidistant contours are computed
8314
8315void TH1::SetContour(Int_t nlevels, const Double_t *levels)
8316{
8317 Int_t level;
8319 if (nlevels <=0 ) {
8320 fContour.Set(0);
8321 return;
8322 }
8323 fContour.Set(nlevels);
8324
8325 // - Contour levels are specified
8326 if (levels) {
8328 for (level=0; level<nlevels; level++) fContour.fArray[level] = levels[level];
8329 } else {
8330 // - contour levels are computed automatically as equidistant contours
8331 Double_t zmin = GetMinimum();
8332 Double_t zmax = GetMaximum();
8333 if ((zmin == zmax) && (zmin != 0)) {
8334 zmax += 0.01*TMath::Abs(zmax);
8335 zmin -= 0.01*TMath::Abs(zmin);
8336 }
8337 Double_t dz = (zmax-zmin)/Double_t(nlevels);
8338 if (gPad && gPad->GetLogz()) {
8339 if (zmax <= 0) return;
8340 if (zmin <= 0) zmin = 0.001*zmax;
8341 zmin = TMath::Log10(zmin);
8342 zmax = TMath::Log10(zmax);
8343 dz = (zmax-zmin)/Double_t(nlevels);
8344 }
8345 for (level=0; level<nlevels; level++) {
8346 fContour.fArray[level] = zmin + dz*Double_t(level);
8347 }
8348 }
8349}
8350
8351////////////////////////////////////////////////////////////////////////////////
8352/// Set value for one contour level.
8353
8354void TH1::SetContourLevel(Int_t level, Double_t value)
8355{
8356 if (level < 0 || level >= fContour.fN) return;
8358 fContour.fArray[level] = value;
8359}
8360
8361////////////////////////////////////////////////////////////////////////////////
8362/// Return maximum value smaller than maxval of bins in the range,
8363/// unless the value has been overridden by TH1::SetMaximum,
8364/// in which case it returns that value. This happens, for example,
8365/// when the histogram is drawn and the y or z axis limits are changed
8366///
8367/// To get the maximum value of bins in the histogram regardless of
8368/// whether the value has been overridden (using TH1::SetMaximum), use
8369///
8370/// ~~~ {.cpp}
8371/// h->GetBinContent(h->GetMaximumBin())
8372/// ~~~
8373///
8374/// TH1::GetMaximumBin can be used to get the location of the maximum
8375/// value.
8376
8377Double_t TH1::GetMaximum(Double_t maxval) const
8378{
8379 if (fMaximum != -1111) return fMaximum;
8380
8381 // empty the buffer
8382 if (fBuffer) ((TH1*)this)->BufferEmpty();
8383
8384 Int_t bin, binx, biny, binz;
8385 Int_t xfirst = fXaxis.GetFirst();
8386 Int_t xlast = fXaxis.GetLast();
8387 Int_t yfirst = fYaxis.GetFirst();
8388 Int_t ylast = fYaxis.GetLast();
8389 Int_t zfirst = fZaxis.GetFirst();
8390 Int_t zlast = fZaxis.GetLast();
8391 Double_t maximum = -FLT_MAX, value;
8392 for (binz=zfirst;binz<=zlast;binz++) {
8393 for (biny=yfirst;biny<=ylast;biny++) {
8394 for (binx=xfirst;binx<=xlast;binx++) {
8395 bin = GetBin(binx,biny,binz);
8396 value = RetrieveBinContent(bin);
8397 if (value > maximum && value < maxval) maximum = value;
8398 }
8399 }
8400 }
8401 return maximum;
8402}
8403
8404////////////////////////////////////////////////////////////////////////////////
8405/// Return location of bin with maximum value in the range.
8406///
8407/// TH1::GetMaximum can be used to get the maximum value.
8408
8410{
8411 Int_t locmax, locmay, locmaz;
8412 return GetMaximumBin(locmax, locmay, locmaz);
8413}
8414
8415////////////////////////////////////////////////////////////////////////////////
8416/// Return location of bin with maximum value in the range.
8417
8418Int_t TH1::GetMaximumBin(Int_t &locmax, Int_t &locmay, Int_t &locmaz) const
8419{
8420 // empty the buffer
8421 if (fBuffer) ((TH1*)this)->BufferEmpty();
8422
8423 Int_t bin, binx, biny, binz;
8424 Int_t locm;
8425 Int_t xfirst = fXaxis.GetFirst();
8426 Int_t xlast = fXaxis.GetLast();
8427 Int_t yfirst = fYaxis.GetFirst();
8428 Int_t ylast = fYaxis.GetLast();
8429 Int_t zfirst = fZaxis.GetFirst();
8430 Int_t zlast = fZaxis.GetLast();
8431 Double_t maximum = -FLT_MAX, value;
8432 locm = locmax = locmay = locmaz = 0;
8433 for (binz=zfirst;binz<=zlast;binz++) {
8434 for (biny=yfirst;biny<=ylast;biny++) {
8435 for (binx=xfirst;binx<=xlast;binx++) {
8436 bin = GetBin(binx,biny,binz);
8437 value = RetrieveBinContent(bin);
8438 if (value > maximum) {
8439 maximum = value;
8440 locm = bin;
8441 locmax = binx;
8442 locmay = biny;
8443 locmaz = binz;
8444 }
8445 }
8446 }
8447 }
8448 return locm;
8449}
8450
8451////////////////////////////////////////////////////////////////////////////////
8452/// Return minimum value larger than minval of bins in the range,
8453/// unless the value has been overridden by TH1::SetMinimum,
8454/// in which case it returns that value. This happens, for example,
8455/// when the histogram is drawn and the y or z axis limits are changed
8456///
8457/// To get the minimum value of bins in the histogram regardless of
8458/// whether the value has been overridden (using TH1::SetMinimum), use
8459///
8460/// ~~~ {.cpp}
8461/// h->GetBinContent(h->GetMinimumBin())
8462/// ~~~
8463///
8464/// TH1::GetMinimumBin can be used to get the location of the
8465/// minimum value.
8466
8467Double_t TH1::GetMinimum(Double_t minval) const
8468{
8469 if (fMinimum != -1111) return fMinimum;
8470
8471 // empty the buffer
8472 if (fBuffer) ((TH1*)this)->BufferEmpty();
8473
8474 Int_t bin, binx, biny, binz;
8475 Int_t xfirst = fXaxis.GetFirst();
8476 Int_t xlast = fXaxis.GetLast();
8477 Int_t yfirst = fYaxis.GetFirst();
8478 Int_t ylast = fYaxis.GetLast();
8479 Int_t zfirst = fZaxis.GetFirst();
8480 Int_t zlast = fZaxis.GetLast();
8481 Double_t minimum=FLT_MAX, value;
8482 for (binz=zfirst;binz<=zlast;binz++) {
8483 for (biny=yfirst;biny<=ylast;biny++) {
8484 for (binx=xfirst;binx<=xlast;binx++) {
8485 bin = GetBin(binx,biny,binz);
8486 value = RetrieveBinContent(bin);
8487 if (value < minimum && value > minval) minimum = value;
8488 }
8489 }
8490 }
8491 return minimum;
8492}
8493
8494////////////////////////////////////////////////////////////////////////////////
8495/// Return location of bin with minimum value in the range.
8496
8498{
8499 Int_t locmix, locmiy, locmiz;
8500 return GetMinimumBin(locmix, locmiy, locmiz);
8501}
8502
8503////////////////////////////////////////////////////////////////////////////////
8504/// Return location of bin with minimum value in the range.
8505
8506Int_t TH1::GetMinimumBin(Int_t &locmix, Int_t &locmiy, Int_t &locmiz) const
8507{
8508 // empty the buffer
8509 if (fBuffer) ((TH1*)this)->BufferEmpty();
8510
8511 Int_t bin, binx, biny, binz;
8512 Int_t locm;
8513 Int_t xfirst = fXaxis.GetFirst();
8514 Int_t xlast = fXaxis.GetLast();
8515 Int_t yfirst = fYaxis.GetFirst();
8516 Int_t ylast = fYaxis.GetLast();
8517 Int_t zfirst = fZaxis.GetFirst();
8518 Int_t zlast = fZaxis.GetLast();
8519 Double_t minimum = FLT_MAX, value;
8520 locm = locmix = locmiy = locmiz = 0;
8521 for (binz=zfirst;binz<=zlast;binz++) {
8522 for (biny=yfirst;biny<=ylast;biny++) {
8523 for (binx=xfirst;binx<=xlast;binx++) {
8524 bin = GetBin(binx,biny,binz);
8525 value = RetrieveBinContent(bin);
8526 if (value < minimum) {
8527 minimum = value;
8528 locm = bin;
8529 locmix = binx;
8530 locmiy = biny;
8531 locmiz = binz;
8532 }
8533 }
8534 }
8535 }
8536 return locm;
8537}
8538
8539///////////////////////////////////////////////////////////////////////////////
8540/// Retrieve the minimum and maximum values in the histogram
8541///
8542/// This will not return a cached value and will always search the
8543/// histogram for the min and max values. The user can condition whether
8544/// or not to call this with the GetMinimumStored() and GetMaximumStored()
8545/// methods. If the cache is empty, then the value will be -1111. Users
8546/// can then use the SetMinimum() or SetMaximum() methods to cache the results.
8547/// For example, the following recipe will make efficient use of this method
8548/// and the cached minimum and maximum values.
8549//
8550/// \code{.cpp}
8551/// Double_t currentMin = pHist->GetMinimumStored();
8552/// Double_t currentMax = pHist->GetMaximumStored();
8553/// if ((currentMin == -1111) || (currentMax == -1111)) {
8554/// pHist->GetMinimumAndMaximum(currentMin, currentMax);
8555/// pHist->SetMinimum(currentMin);
8556/// pHist->SetMaximum(currentMax);
8557/// }
8558/// \endcode
8559///
8560/// \param min reference to variable that will hold found minimum value
8561/// \param max reference to variable that will hold found maximum value
8562
8563void TH1::GetMinimumAndMaximum(Double_t& min, Double_t& max) const
8564{
8565 // empty the buffer
8566 if (fBuffer) ((TH1*)this)->BufferEmpty();
8567
8568 Int_t bin, binx, biny, binz;
8569 Int_t xfirst = fXaxis.GetFirst();
8570 Int_t xlast = fXaxis.GetLast();
8571 Int_t yfirst = fYaxis.GetFirst();
8572 Int_t ylast = fYaxis.GetLast();
8573 Int_t zfirst = fZaxis.GetFirst();
8574 Int_t zlast = fZaxis.GetLast();
8575 min=TMath::Infinity();
8576 max=-TMath::Infinity();
8577 Double_t value;
8578 for (binz=zfirst;binz<=zlast;binz++) {
8579 for (biny=yfirst;biny<=ylast;biny++) {
8580 for (binx=xfirst;binx<=xlast;binx++) {
8581 bin = GetBin(binx,biny,binz);
8582 value = RetrieveBinContent(bin);
8583 if (value < min) min = value;
8584 if (value > max) max = value;
8585 }
8586 }
8587 }
8588}
8589
8590////////////////////////////////////////////////////////////////////////////////
8591/// Redefine x axis parameters.
8592///
8593/// The X axis parameters are modified.
8594/// The bins content array is resized
8595/// if errors (Sumw2) the errors array is resized
8596/// The previous bin contents are lost
8597/// To change only the axis limits, see TAxis::SetRange
8598
8600{
8601 if (GetDimension() != 1) {
8602 Error("SetBins","Operation only valid for 1-d histograms");
8603 return;
8604 }
8605 fXaxis.SetRange(0,0);
8606 fXaxis.Set(nx,xmin,xmax);
8607 fYaxis.Set(1,0,1);
8608 fZaxis.Set(1,0,1);
8609 fNcells = nx+2;
8611 if (fSumw2.fN) {
8613 }
8614}
8615
8616////////////////////////////////////////////////////////////////////////////////
8617/// Redefine x axis parameters with variable bin sizes.
8618///
8619/// The X axis parameters are modified.
8620/// The bins content array is resized
8621/// if errors (Sumw2) the errors array is resized
8622/// The previous bin contents are lost
8623/// To change only the axis limits, see TAxis::SetRange
8624/// xBins is supposed to be of length nx+1
8625
8626void TH1::SetBins(Int_t nx, const Double_t *xBins)
8627{
8628 if (GetDimension() != 1) {
8629 Error("SetBins","Operation only valid for 1-d histograms");
8630 return;
8631 }
8632 fXaxis.SetRange(0,0);
8633 fXaxis.Set(nx,xBins);
8634 fYaxis.Set(1,0,1);
8635 fZaxis.Set(1,0,1);
8636 fNcells = nx+2;
8638 if (fSumw2.fN) {
8640 }
8641}
8642
8643////////////////////////////////////////////////////////////////////////////////
8644/// Redefine x and y axis parameters.
8645///
8646/// The X and Y axis parameters are modified.
8647/// The bins content array is resized
8648/// if errors (Sumw2) the errors array is resized
8649/// The previous bin contents are lost
8650/// To change only the axis limits, see TAxis::SetRange
8651
8653{
8654 if (GetDimension() != 2) {
8655 Error("SetBins","Operation only valid for 2-D histograms");
8656 return;
8657 }
8658 fXaxis.SetRange(0,0);
8659 fYaxis.SetRange(0,0);
8660 fXaxis.Set(nx,xmin,xmax);
8661 fYaxis.Set(ny,ymin,ymax);
8662 fZaxis.Set(1,0,1);
8663 fNcells = (nx+2)*(ny+2);
8665 if (fSumw2.fN) {
8667 }
8668}
8669
8670////////////////////////////////////////////////////////////////////////////////
8671/// Redefine x and y axis parameters with variable bin sizes.
8672///
8673/// The X and Y axis parameters are modified.
8674/// The bins content array is resized
8675/// if errors (Sumw2) the errors array is resized
8676/// The previous bin contents are lost
8677/// To change only the axis limits, see TAxis::SetRange
8678/// xBins is supposed to be of length nx+1, yBins is supposed to be of length ny+1
8679
8680void TH1::SetBins(Int_t nx, const Double_t *xBins, Int_t ny, const Double_t *yBins)
8681{
8682 if (GetDimension() != 2) {
8683 Error("SetBins","Operation only valid for 2-D histograms");
8684 return;
8685 }
8686 fXaxis.SetRange(0,0);
8687 fYaxis.SetRange(0,0);
8688 fXaxis.Set(nx,xBins);
8689 fYaxis.Set(ny,yBins);
8690 fZaxis.Set(1,0,1);
8691 fNcells = (nx+2)*(ny+2);
8693 if (fSumw2.fN) {
8695 }
8696}
8697
8698////////////////////////////////////////////////////////////////////////////////
8699/// Redefine x, y and z axis parameters.
8700///
8701/// The X, Y and Z axis parameters are modified.
8702/// The bins content array is resized
8703/// if errors (Sumw2) the errors array is resized
8704/// The previous bin contents are lost
8705/// To change only the axis limits, see TAxis::SetRange
8706
8708{
8709 if (GetDimension() != 3) {
8710 Error("SetBins","Operation only valid for 3-D histograms");
8711 return;
8712 }
8713 fXaxis.SetRange(0,0);
8714 fYaxis.SetRange(0,0);
8715 fZaxis.SetRange(0,0);
8716 fXaxis.Set(nx,xmin,xmax);
8717 fYaxis.Set(ny,ymin,ymax);
8718 fZaxis.Set(nz,zmin,zmax);
8719 fNcells = (nx+2)*(ny+2)*(nz+2);
8721 if (fSumw2.fN) {
8723 }
8724}
8725
8726////////////////////////////////////////////////////////////////////////////////
8727/// Redefine x, y and z axis parameters with variable bin sizes.
8728///
8729/// The X, Y and Z axis parameters are modified.
8730/// The bins content array is resized
8731/// if errors (Sumw2) the errors array is resized
8732/// The previous bin contents are lost
8733/// To change only the axis limits, see TAxis::SetRange
8734/// xBins is supposed to be of length nx+1, yBins is supposed to be of length ny+1,
8735/// zBins is supposed to be of length nz+1
8736
8737void TH1::SetBins(Int_t nx, const Double_t *xBins, Int_t ny, const Double_t *yBins, Int_t nz, const Double_t *zBins)
8738{
8739 if (GetDimension() != 3) {
8740 Error("SetBins","Operation only valid for 3-D histograms");
8741 return;
8742 }
8743 fXaxis.SetRange(0,0);
8744 fYaxis.SetRange(0,0);
8745 fZaxis.SetRange(0,0);
8746 fXaxis.Set(nx,xBins);
8747 fYaxis.Set(ny,yBins);
8748 fZaxis.Set(nz,zBins);
8749 fNcells = (nx+2)*(ny+2)*(nz+2);
8751 if (fSumw2.fN) {
8753 }
8754}
8755
8756////////////////////////////////////////////////////////////////////////////////
8757/// By default, when a histogram is created, it is added to the list
8758/// of histogram objects in the current directory in memory.
8759/// Remove reference to this histogram from current directory and add
8760/// reference to new directory dir. dir can be 0 in which case the
8761/// histogram does not belong to any directory.
8762///
8763/// Note that the directory is not a real property of the histogram and
8764/// it will not be copied when the histogram is copied or cloned.
8765/// If the user wants to have the copied (cloned) histogram in the same
8766/// directory, he needs to set again the directory using SetDirectory to the
8767/// copied histograms
8768
8770{
8771 if (fDirectory == dir) return;
8772 if (fDirectory) fDirectory->Remove(this);
8773 fDirectory = dir;
8774 if (fDirectory) {
8776 fDirectory->Append(this);
8777 }
8778}
8779
8780////////////////////////////////////////////////////////////////////////////////
8781/// Replace bin errors by values in array error.
8782
8783void TH1::SetError(const Double_t *error)
8784{
8785 for (Int_t i = 0; i < fNcells; ++i) SetBinError(i, error[i]);
8786}
8787
8788////////////////////////////////////////////////////////////////////////////////
8789/// Change the name of this histogram
8791
8792void TH1::SetName(const char *name)
8793{
8794 // Histograms are named objects in a THashList.
8795 // We must update the hashlist if we change the name
8796 // We protect this operation
8798 if (fDirectory) fDirectory->Remove(this);
8799 fName = name;
8800 if (fDirectory) fDirectory->Append(this);
8801}
8802
8803////////////////////////////////////////////////////////////////////////////////
8804/// Change the name and title of this histogram
8805
8806void TH1::SetNameTitle(const char *name, const char *title)
8807{
8808 // Histograms are named objects in a THashList.
8809 // We must update the hashlist if we change the name
8810 SetName(name);
8811 SetTitle(title);
8812}
8813
8814////////////////////////////////////////////////////////////////////////////////
8815/// Set statistics option on/off.
8816///
8817/// By default, the statistics box is drawn.
8818/// The paint options can be selected via gStyle->SetOptStats.
8819/// This function sets/resets the kNoStats bit in the histogram object.
8820/// It has priority over the Style option.
8821
8822void TH1::SetStats(Bool_t stats)
8823{
8825 if (!stats) {
8827 //remove the "stats" object from the list of functions
8828 if (fFunctions) {
8829 TObject *obj = fFunctions->FindObject("stats");
8830 if (obj) {
8831 fFunctions->Remove(obj);
8832 delete obj;
8833 }
8834 }
8835 }
8836}
8837
8838////////////////////////////////////////////////////////////////////////////////
8839/// Create structure to store sum of squares of weights.
8840///
8841/// if histogram is already filled, the sum of squares of weights
8842/// is filled with the existing bin contents
8843///
8844/// The error per bin will be computed as sqrt(sum of squares of weight)
8845/// for each bin.
8846///
8847/// This function is automatically called when the histogram is created
8848/// if the static function TH1::SetDefaultSumw2 has been called before.
8849/// If flag = false the structure containing the sum of the square of weights
8850/// is rest and it will be empty, but it is not deleted (i.e. GetSumw2()->fN = 0)
8851
8852void TH1::Sumw2(Bool_t flag)
8853{
8854 if (!flag) {
8855 // clear the array if existing - do nothing otherwise
8856 if (fSumw2.fN > 0 ) fSumw2.Set(0);
8857 return;
8858 }
8859
8860 if (fSumw2.fN == fNcells) {
8861 if (!fgDefaultSumw2 )
8862 Warning("Sumw2","Sum of squares of weights structure already created");
8863 return;
8864 }
8865
8867
8868 // empty the buffer
8869 if (fBuffer) BufferEmpty();
8870
8871 if (fEntries > 0)
8872 for (Int_t i = 0; i < fNcells; ++i)
8874}
8875
8876////////////////////////////////////////////////////////////////////////////////
8877/// Return pointer to function with name.
8878///
8879///
8880/// Functions such as TH1::Fit store the fitted function in the list of
8881/// functions of this histogram.
8882
8883TF1 *TH1::GetFunction(const char *name) const
8884{
8885 return (TF1*)fFunctions->FindObject(name);
8886}
8887
8888////////////////////////////////////////////////////////////////////////////////
8889/// Return value of error associated to bin number bin.
8890///
8891/// if the sum of squares of weights has been defined (via Sumw2),
8892/// this function returns the sqrt(sum of w2).
8893/// otherwise it returns the sqrt(contents) for this bin.
8894
8896{
8897 if (bin < 0) bin = 0;
8898 if (bin >= fNcells) bin = fNcells-1;
8899 if (fBuffer) ((TH1*)this)->BufferEmpty();
8900 if (fSumw2.fN) return TMath::Sqrt(fSumw2.fArray[bin]);
8901
8903}
8904
8905////////////////////////////////////////////////////////////////////////////////
8906/// Return lower error associated to bin number bin.
8907///
8908/// The error will depend on the statistic option used will return
8909/// the binContent - lower interval value
8910
8912{
8913 if (fBinStatErrOpt == kNormal) return GetBinError(bin);
8914 // in case of weighted histogram check if it is really weighted
8915 if (fSumw2.fN && fTsumw != fTsumw2) return GetBinError(bin);
8916
8917 if (bin < 0) bin = 0;
8918 if (bin >= fNcells) bin = fNcells-1;
8919 if (fBuffer) ((TH1*)this)->BufferEmpty();
8920
8921 Double_t alpha = 1.- 0.682689492;
8922 if (fBinStatErrOpt == kPoisson2) alpha = 0.05;
8923
8925 Int_t n = int(c);
8926 if (n < 0) {
8927 Warning("GetBinErrorLow","Histogram has negative bin content-force usage to normal errors");
8928 ((TH1*)this)->fBinStatErrOpt = kNormal;
8929 return GetBinError(bin);
8930 }
8931
8932 if (n == 0) return 0;
8933 return c - ROOT::Math::gamma_quantile( alpha/2, n, 1.);
8934}
8935
8936////////////////////////////////////////////////////////////////////////////////
8937/// Return upper error associated to bin number bin.
8938///
8939/// The error will depend on the statistic option used will return
8940/// the binContent - upper interval value
8941
8943{
8944 if (fBinStatErrOpt == kNormal) return GetBinError(bin);
8945 // in case of weighted histogram check if it is really weighted
8946 if (fSumw2.fN && fTsumw != fTsumw2) return GetBinError(bin);
8947 if (bin < 0) bin = 0;
8948 if (bin >= fNcells) bin = fNcells-1;
8949 if (fBuffer) ((TH1*)this)->BufferEmpty();
8950
8951 Double_t alpha = 1.- 0.682689492;
8952 if (fBinStatErrOpt == kPoisson2) alpha = 0.05;
8953
8955 Int_t n = int(c);
8956 if (n < 0) {
8957 Warning("GetBinErrorUp","Histogram has negative bin content-force usage to normal errors");
8958 ((TH1*)this)->fBinStatErrOpt = kNormal;
8959 return GetBinError(bin);
8960 }
8961
8962 // for N==0 return an upper limit at 0.68 or (1-alpha)/2 ?
8963 // decide to return always (1-alpha)/2 upper interval
8964 //if (n == 0) return ROOT::Math::gamma_quantile_c(alpha,n+1,1);
8965 return ROOT::Math::gamma_quantile_c( alpha/2, n+1, 1) - c;
8966}
8967
8968//L.M. These following getters are useless and should be probably deprecated
8969////////////////////////////////////////////////////////////////////////////////
8970/// Return bin center for 1D histogram.
8971/// Better to use h1.GetXaxis()->GetBinCenter(bin)
8972
8974{
8975 if (fDimension == 1) return fXaxis.GetBinCenter(bin);
8976 Error("GetBinCenter","Invalid method for a %d-d histogram - return a NaN",fDimension);
8977 return TMath::QuietNaN();
8978}
8979
8980////////////////////////////////////////////////////////////////////////////////
8981/// Return bin lower edge for 1D histogram.
8982/// Better to use h1.GetXaxis()->GetBinLowEdge(bin)
8983
8985{
8986 if (fDimension == 1) return fXaxis.GetBinLowEdge(bin);
8987 Error("GetBinLowEdge","Invalid method for a %d-d histogram - return a NaN",fDimension);
8988 return TMath::QuietNaN();
8989}
8990
8991////////////////////////////////////////////////////////////////////////////////
8992/// Return bin width for 1D histogram.
8993/// Better to use h1.GetXaxis()->GetBinWidth(bin)
8994
8996{
8997 if (fDimension == 1) return fXaxis.GetBinWidth(bin);
8998 Error("GetBinWidth","Invalid method for a %d-d histogram - return a NaN",fDimension);
8999 return TMath::QuietNaN();
9000}
9001
9002////////////////////////////////////////////////////////////////////////////////
9003/// Fill array with center of bins for 1D histogram
9004/// Better to use h1.GetXaxis()->GetCenter(center)
9005
9006void TH1::GetCenter(Double_t *center) const
9007{
9008 if (fDimension == 1) {
9009 fXaxis.GetCenter(center);
9010 return;
9011 }
9012 Error("GetCenter","Invalid method for a %d-d histogram ",fDimension);
9013}
9014
9015////////////////////////////////////////////////////////////////////////////////
9016/// Fill array with low edge of bins for 1D histogram
9017/// Better to use h1.GetXaxis()->GetLowEdge(edge)
9018
9019void TH1::GetLowEdge(Double_t *edge) const
9020{
9021 if (fDimension == 1) {
9022 fXaxis.GetLowEdge(edge);
9023 return;
9024 }
9025 Error("GetLowEdge","Invalid method for a %d-d histogram ",fDimension);
9026}
9027
9028////////////////////////////////////////////////////////////////////////////////
9029/// Set the bin Error
9030/// Note that this resets the bin eror option to be of Normal Type and for the
9031/// non-empty bin the bin error is set by default to the square root of their content.
9032/// Note that in case the user sets after calling SetBinError explicitly a new bin content (e.g. using SetBinContent)
9033/// he needs then to provide also the corresponding bin error (using SetBinError) since the bin error
9034/// will not be recalculated after setting the content and a default error = 0 will be used for those bins.
9035///
9036/// See convention for numbering bins in TH1::GetBin
9037
9038void TH1::SetBinError(Int_t bin, Double_t error)
9039{
9040 if (bin < 0 || bin>= fNcells) return;
9041 if (!fSumw2.fN) Sumw2();
9042 fSumw2.fArray[bin] = error * error;
9043 // reset the bin error option
9045}
9046
9047////////////////////////////////////////////////////////////////////////////////
9048/// Set bin content
9049/// see convention for numbering bins in TH1::GetBin
9050/// In case the bin number is greater than the number of bins and
9051/// the timedisplay option is set or CanExtendAllAxes(),
9052/// the number of bins is automatically doubled to accommodate the new bin
9053
9054void TH1::SetBinContent(Int_t bin, Double_t content)
9055{
9056 fEntries++;
9057 fTsumw = 0;
9058 if (bin < 0) return;
9059 if (bin >= fNcells-1) {
9061 while (bin >= fNcells-1) LabelsInflate();
9062 } else {
9063 if (bin == fNcells-1) UpdateBinContent(bin, content);
9064 return;
9065 }
9066 }
9067 UpdateBinContent(bin, content);
9068}
9069
9070////////////////////////////////////////////////////////////////////////////////
9071/// See convention for numbering bins in TH1::GetBin
9072
9073void TH1::SetBinError(Int_t binx, Int_t biny, Double_t error)
9074{
9075 if (binx < 0 || binx > fXaxis.GetNbins() + 1) return;
9076 if (biny < 0 || biny > fYaxis.GetNbins() + 1) return;
9077 SetBinError(GetBin(binx, biny), error);
9078}
9079
9080////////////////////////////////////////////////////////////////////////////////
9081/// See convention for numbering bins in TH1::GetBin
9082
9083void TH1::SetBinError(Int_t binx, Int_t biny, Int_t binz, Double_t error)
9084{
9085 if (binx < 0 || binx > fXaxis.GetNbins() + 1) return;
9086 if (biny < 0 || biny > fYaxis.GetNbins() + 1) return;
9087 if (binz < 0 || binz > fZaxis.GetNbins() + 1) return;
9088 SetBinError(GetBin(binx, biny, binz), error);
9089}
9090
9091////////////////////////////////////////////////////////////////////////////////
9092/// This function calculates the background spectrum in this histogram.
9093/// The background is returned as a histogram.
9094///
9095/// \param[in] niter number of iterations (default value = 2)
9096/// Increasing niter make the result smoother and lower.
9097/// \param[in] option may contain one of the following options
9098/// - to set the direction parameter
9099/// "BackDecreasingWindow". By default the direction is BackIncreasingWindow
9100/// - filterOrder-order of clipping filter (default "BackOrder2")
9101/// possible values= "BackOrder4" "BackOrder6" "BackOrder8"
9102/// - "nosmoothing" - if selected, the background is not smoothed
9103/// By default the background is smoothed.
9104/// - smoothWindow - width of smoothing window, (default is "BackSmoothing3")
9105/// possible values= "BackSmoothing5" "BackSmoothing7" "BackSmoothing9"
9106/// "BackSmoothing11" "BackSmoothing13" "BackSmoothing15"
9107/// - "nocompton" - if selected the estimation of Compton edge
9108/// will be not be included (by default the compton estimation is set)
9109/// - "same" if this option is specified, the resulting background
9110/// histogram is superimposed on the picture in the current pad.
9111/// This option is given by default.
9112///
9113/// NOTE that the background is only evaluated in the current range of this histogram.
9114/// i.e., if this has a bin range (set via h->GetXaxis()->SetRange(binmin, binmax),
9115/// the returned histogram will be created with the same number of bins
9116/// as this input histogram, but only bins from binmin to binmax will be filled
9117/// with the estimated background.
9118
9119TH1 *TH1::ShowBackground(Int_t niter, Option_t *option)
9120{
9121
9122 return (TH1*)gROOT->ProcessLineFast(Form("TSpectrum::StaticBackground((TH1*)0x%zx,%d,\"%s\")",
9123 (size_t)this, niter, option));
9124}
9125
9126////////////////////////////////////////////////////////////////////////////////
9127/// Interface to TSpectrum::Search.
9128/// The function finds peaks in this histogram where the width is > sigma
9129/// and the peak maximum greater than threshold*maximum bin content of this.
9130/// For more details see TSpectrum::Search.
9131/// Note the difference in the default value for option compared to TSpectrum::Search
9132/// option="" by default (instead of "goff").
9133
9135{
9136 return (Int_t)gROOT->ProcessLineFast(Form("TSpectrum::StaticSearch((TH1*)0x%zx,%g,\"%s\",%g)",
9137 (size_t)this, sigma, option, threshold));
9138}
9139
9140////////////////////////////////////////////////////////////////////////////////
9141/// For a given transform (first parameter), fills the histogram (second parameter)
9142/// with the transform output data, specified in the third parameter
9143/// If the 2nd parameter h_output is empty, a new histogram (TH1D or TH2D) is created
9144/// and the user is responsible for deleting it.
9145///
9146/// Available options:
9147/// - "RE" - real part of the output
9148/// - "IM" - imaginary part of the output
9149/// - "MAG" - magnitude of the output
9150/// - "PH" - phase of the output
9151
9152TH1* TH1::TransformHisto(TVirtualFFT *fft, TH1* h_output, Option_t *option)
9153{
9154 if (!fft || !fft->GetN() ) {
9155 ::Error("TransformHisto","Invalid FFT transform class");
9156 return 0;
9157 }
9158
9159 if (fft->GetNdim()>2){
9160 ::Error("TransformHisto","Only 1d and 2D transform are supported");
9161 return 0;
9162 }
9163 Int_t binx,biny;
9164 TString opt = option;
9165 opt.ToUpper();
9166 Int_t *n = fft->GetN();
9167 TH1 *hout=0;
9168 if (h_output) {
9169 hout = h_output;
9170 }
9171 else {
9172 TString name = TString::Format("out_%s", opt.Data());
9173 if (fft->GetNdim()==1)
9174 hout = new TH1D(name, name,n[0], 0, n[0]);
9175 else if (fft->GetNdim()==2)
9176 hout = new TH2D(name, name, n[0], 0, n[0], n[1], 0, n[1]);
9177 }
9178 R__ASSERT(hout != 0);
9179 TString type=fft->GetType();
9180 Int_t ind[2];
9181 if (opt.Contains("RE")){
9182 if (type.Contains("2C") || type.Contains("2HC")) {
9183 Double_t re, im;
9184 for (binx = 1; binx<=hout->GetNbinsX(); binx++) {
9185 for (biny=1; biny<=hout->GetNbinsY(); biny++) {
9186 ind[0] = binx-1; ind[1] = biny-1;
9187 fft->GetPointComplex(ind, re, im);
9188 hout->SetBinContent(binx, biny, re);
9189 }
9190 }
9191 } else {
9192 for (binx = 1; binx<=hout->GetNbinsX(); binx++) {
9193 for (biny=1; biny<=hout->GetNbinsY(); biny++) {
9194 ind[0] = binx-1; ind[1] = biny-1;
9195 hout->SetBinContent(binx, biny, fft->GetPointReal(ind));
9196 }
9197 }
9198 }
9199 }
9200 if (opt.Contains("IM")) {
9201 if (type.Contains("2C") || type.Contains("2HC")) {
9202 Double_t re, im;
9203 for (binx = 1; binx<=hout->GetNbinsX(); binx++) {
9204 for (biny=1; biny<=hout->GetNbinsY(); biny++) {
9205 ind[0] = binx-1; ind[1] = biny-1;
9206 fft->GetPointComplex(ind, re, im);
9207 hout->SetBinContent(binx, biny, im);
9208 }
9209 }
9210 } else {
9211 ::Error("TransformHisto","No complex numbers in the output");
9212 return 0;
9213 }
9214 }
9215 if (opt.Contains("MA")) {
9216 if (type.Contains("2C") || type.Contains("2HC")) {
9217 Double_t re, im;
9218 for (binx = 1; binx<=hout->GetNbinsX(); binx++) {
9219 for (biny=1; biny<=hout->GetNbinsY(); biny++) {
9220 ind[0] = binx-1; ind[1] = biny-1;
9221 fft->GetPointComplex(ind, re, im);
9222 hout->SetBinContent(binx, biny, TMath::Sqrt(re*re + im*im));
9223 }
9224 }
9225 } else {
9226 for (binx = 1; binx<=hout->GetNbinsX(); binx++) {
9227 for (biny=1; biny<=hout->GetNbinsY(); biny++) {
9228 ind[0] = binx-1; ind[1] = biny-1;
9229 hout->SetBinContent(binx, biny, TMath::Abs(fft->GetPointReal(ind)));
9230 }
9231 }
9232 }
9233 }
9234 if (opt.Contains("PH")) {
9235 if (type.Contains("2C") || type.Contains("2HC")){
9236 Double_t re, im, ph;
9237 for (binx = 1; binx<=hout->GetNbinsX(); binx++){
9238 for (biny=1; biny<=hout->GetNbinsY(); biny++){
9239 ind[0] = binx-1; ind[1] = biny-1;
9240 fft->GetPointComplex(ind, re, im);
9241 if (TMath::Abs(re) > 1e-13){
9242 ph = TMath::ATan(im/re);
9243 //find the correct quadrant
9244 if (re<0 && im<0)
9245 ph -= TMath::Pi();
9246 if (re<0 && im>=0)
9247 ph += TMath::Pi();
9248 } else {
9249 if (TMath::Abs(im) < 1e-13)
9250 ph = 0;
9251 else if (im>0)
9252 ph = TMath::Pi()*0.5;
9253 else
9254 ph = -TMath::Pi()*0.5;
9255 }
9256 hout->SetBinContent(binx, biny, ph);
9257 }
9258 }
9259 } else {
9260 printf("Pure real output, no phase");
9261 return 0;
9262 }
9263 }
9264
9265 return hout;
9266}
9267
9268////////////////////////////////////////////////////////////////////////////////
9269/// Raw retrieval of bin content on internal data structure
9270/// see convention for numbering bins in TH1::GetBin
9271
9273{
9274 AbstractMethod("RetrieveBinContent");
9275 return 0;
9276}
9277
9278////////////////////////////////////////////////////////////////////////////////
9279/// Raw update of bin content on internal data structure
9280/// see convention for numbering bins in TH1::GetBin
9281
9283{
9284 AbstractMethod("UpdateBinContent");
9285}
9286
9287////////////////////////////////////////////////////////////////////////////////
9288/// Print value overload
9289
9290std::string cling::printValue(TH1 *val) {
9291 std::ostringstream strm;
9292 strm << cling::printValue((TObject*)val) << " NbinsX: " << val->GetNbinsX();
9293 return strm.str();
9294}
9295
9296//______________________________________________________________________________
9297// TH1C methods
9298// TH1C : histograms with one byte per channel. Maximum bin content = 127
9299//______________________________________________________________________________
9300
9301ClassImp(TH1C);
9302
9303////////////////////////////////////////////////////////////////////////////////
9304/// Constructor.
9305
9306TH1C::TH1C(): TH1(), TArrayC()
9307{
9308 fDimension = 1;
9309 SetBinsLength(3);
9310 if (fgDefaultSumw2) Sumw2();
9311}
9312
9313////////////////////////////////////////////////////////////////////////////////
9314/// Create a 1-Dim histogram with fix bins of type char (one byte per channel)
9315/// (see TH1::TH1 for explanation of parameters)
9316
9317TH1C::TH1C(const char *name,const char *title,Int_t nbins,Double_t xlow,Double_t xup)
9318: TH1(name,title,nbins,xlow,xup)
9319{
9320 fDimension = 1;
9322
9323 if (xlow >= xup) SetBuffer(fgBufferSize);
9324 if (fgDefaultSumw2) Sumw2();
9325}
9326
9327////////////////////////////////////////////////////////////////////////////////
9328/// Create a 1-Dim histogram with variable bins of type char (one byte per channel)
9329/// (see TH1::TH1 for explanation of parameters)
9330
9331TH1C::TH1C(const char *name,const char *title,Int_t nbins,const Float_t *xbins)
9332: TH1(name,title,nbins,xbins)
9333{
9334 fDimension = 1;
9336 if (fgDefaultSumw2) Sumw2();
9337}
9338
9339////////////////////////////////////////////////////////////////////////////////
9340/// Create a 1-Dim histogram with variable bins of type char (one byte per channel)
9341/// (see TH1::TH1 for explanation of parameters)
9342
9343TH1C::TH1C(const char *name,const char *title,Int_t nbins,const Double_t *xbins)
9344: TH1(name,title,nbins,xbins)
9345{
9346 fDimension = 1;
9348 if (fgDefaultSumw2) Sumw2();
9349}
9350
9351////////////////////////////////////////////////////////////////////////////////
9352/// Destructor.
9353
9355{
9356}
9357
9358////////////////////////////////////////////////////////////////////////////////
9359/// Copy constructor.
9360/// The list of functions is not copied. (Use Clone() if needed)
9361
9362TH1C::TH1C(const TH1C &h1c) : TH1(), TArrayC()
9363{
9364 ((TH1C&)h1c).Copy(*this);
9365}
9366
9367////////////////////////////////////////////////////////////////////////////////
9368/// Increment bin content by 1.
9369
9370void TH1C::AddBinContent(Int_t bin)
9371{
9372 if (fArray[bin] < 127) fArray[bin]++;
9373}
9374
9375////////////////////////////////////////////////////////////////////////////////
9376/// Increment bin content by w.
9377
9379{
9380 Int_t newval = fArray[bin] + Int_t(w);
9381 if (newval > -128 && newval < 128) {fArray[bin] = Char_t(newval); return;}
9382 if (newval < -127) fArray[bin] = -127;
9383 if (newval > 127) fArray[bin] = 127;
9384}
9385
9386////////////////////////////////////////////////////////////////////////////////
9387/// Copy this to newth1
9388
9389void TH1C::Copy(TObject &newth1) const
9390{
9391 TH1::Copy(newth1);
9392}
9393
9394////////////////////////////////////////////////////////////////////////////////
9395/// Reset.
9396
9397void TH1C::Reset(Option_t *option)
9398{
9399 TH1::Reset(option);
9401}
9402
9403////////////////////////////////////////////////////////////////////////////////
9404/// Set total number of bins including under/overflow
9405/// Reallocate bin contents array
9406
9408{
9409 if (n < 0) n = fXaxis.GetNbins() + 2;
9410 fNcells = n;
9411 TArrayC::Set(n);
9412}
9413
9414////////////////////////////////////////////////////////////////////////////////
9415/// Operator =
9416
9417TH1C& TH1C::operator=(const TH1C &h1)
9418{
9419 if (this != &h1) ((TH1C&)h1).Copy(*this);
9420 return *this;
9421}
9422
9423////////////////////////////////////////////////////////////////////////////////
9424/// Operator *
9425
9427{
9428 TH1C hnew = h1;
9429 hnew.Scale(c1);
9430 hnew.SetDirectory(0);
9431 return hnew;
9432}
9433
9434////////////////////////////////////////////////////////////////////////////////
9435/// Operator +
9436
9437TH1C operator+(const TH1C &h1, const TH1C &h2)
9438{
9439 TH1C hnew = h1;
9440 hnew.Add(&h2,1);
9441 hnew.SetDirectory(0);
9442 return hnew;
9443}
9444
9445////////////////////////////////////////////////////////////////////////////////
9446/// Operator -
9447
9448TH1C operator-(const TH1C &h1, const TH1C &h2)
9449{
9450 TH1C hnew = h1;
9451 hnew.Add(&h2,-1);
9452 hnew.SetDirectory(0);
9453 return hnew;
9454}
9455
9456////////////////////////////////////////////////////////////////////////////////
9457/// Operator *
9458
9459TH1C operator*(const TH1C &h1, const TH1C &h2)
9460{
9461 TH1C hnew = h1;
9462 hnew.Multiply(&h2);
9463 hnew.SetDirectory(0);
9464 return hnew;
9465}
9466
9467////////////////////////////////////////////////////////////////////////////////
9468/// Operator /
9469
9470TH1C operator/(const TH1C &h1, const TH1C &h2)
9471{
9472 TH1C hnew = h1;
9473 hnew.Divide(&h2);
9474 hnew.SetDirectory(0);
9475 return hnew;
9476}
9477
9478//______________________________________________________________________________
9479// TH1S methods
9480// TH1S : histograms with one short per channel. Maximum bin content = 32767
9481//______________________________________________________________________________
9482
9483ClassImp(TH1S);
9484
9485////////////////////////////////////////////////////////////////////////////////
9486/// Constructor.
9487
9488TH1S::TH1S(): TH1(), TArrayS()
9489{
9490 fDimension = 1;
9491 SetBinsLength(3);
9492 if (fgDefaultSumw2) Sumw2();
9493}
9494
9495////////////////////////////////////////////////////////////////////////////////
9496/// Create a 1-Dim histogram with fix bins of type short
9497/// (see TH1::TH1 for explanation of parameters)
9498
9499TH1S::TH1S(const char *name,const char *title,Int_t nbins,Double_t xlow,Double_t xup)
9500: TH1(name,title,nbins,xlow,xup)
9501{
9502 fDimension = 1;
9504
9505 if (xlow >= xup) SetBuffer(fgBufferSize);
9506 if (fgDefaultSumw2) Sumw2();
9507}
9508
9509////////////////////////////////////////////////////////////////////////////////
9510/// Create a 1-Dim histogram with variable bins of type short
9511/// (see TH1::TH1 for explanation of parameters)
9512
9513TH1S::TH1S(const char *name,const char *title,Int_t nbins,const Float_t *xbins)
9514: TH1(name,title,nbins,xbins)
9515{
9516 fDimension = 1;
9518 if (fgDefaultSumw2) Sumw2();
9519}
9520
9521////////////////////////////////////////////////////////////////////////////////
9522/// Create a 1-Dim histogram with variable bins of type short
9523/// (see TH1::TH1 for explanation of parameters)
9524
9525TH1S::TH1S(const char *name,const char *title,Int_t nbins,const Double_t *xbins)
9526: TH1(name,title,nbins,xbins)
9527{
9528 fDimension = 1;
9530 if (fgDefaultSumw2) Sumw2();
9531}
9532
9533////////////////////////////////////////////////////////////////////////////////
9534/// Destructor.
9535
9537{
9538}
9539
9540////////////////////////////////////////////////////////////////////////////////
9541/// Copy constructor.
9542/// The list of functions is not copied. (Use Clone() if needed)
9543
9544TH1S::TH1S(const TH1S &h1s) : TH1(), TArrayS()
9545{
9546 ((TH1S&)h1s).Copy(*this);
9547}
9548
9549////////////////////////////////////////////////////////////////////////////////
9550/// Increment bin content by 1.
9551
9552void TH1S::AddBinContent(Int_t bin)
9553{
9554 if (fArray[bin] < 32767) fArray[bin]++;
9555}
9556
9557////////////////////////////////////////////////////////////////////////////////
9558/// Increment bin content by w
9559
9561{
9562 Int_t newval = fArray[bin] + Int_t(w);
9563 if (newval > -32768 && newval < 32768) {fArray[bin] = Short_t(newval); return;}
9564 if (newval < -32767) fArray[bin] = -32767;
9565 if (newval > 32767) fArray[bin] = 32767;
9566}
9567
9568////////////////////////////////////////////////////////////////////////////////
9569/// Copy this to newth1
9570
9571void TH1S::Copy(TObject &newth1) const
9572{
9573 TH1::Copy(newth1);
9574}
9575
9576////////////////////////////////////////////////////////////////////////////////
9577/// Reset.
9578
9579void TH1S::Reset(Option_t *option)
9580{
9581 TH1::Reset(option);
9583}
9584
9585////////////////////////////////////////////////////////////////////////////////
9586/// Set total number of bins including under/overflow
9587/// Reallocate bin contents array
9588
9590{
9591 if (n < 0) n = fXaxis.GetNbins() + 2;
9592 fNcells = n;
9593 TArrayS::Set(n);
9594}
9595
9596////////////////////////////////////////////////////////////////////////////////
9597/// Operator =
9598
9599TH1S& TH1S::operator=(const TH1S &h1)
9600{
9601 if (this != &h1) ((TH1S&)h1).Copy(*this);
9602 return *this;
9603}
9604
9605////////////////////////////////////////////////////////////////////////////////
9606/// Operator *
9607
9609{
9610 TH1S hnew = h1;
9611 hnew.Scale(c1);
9612 hnew.SetDirectory(0);
9613 return hnew;
9614}
9615
9616////////////////////////////////////////////////////////////////////////////////
9617/// Operator +
9618
9619TH1S operator+(const TH1S &h1, const TH1S &h2)
9620{
9621 TH1S hnew = h1;
9622 hnew.Add(&h2,1);
9623 hnew.SetDirectory(0);
9624 return hnew;
9625}
9626
9627////////////////////////////////////////////////////////////////////////////////
9628/// Operator -
9629
9630TH1S operator-(const TH1S &h1, const TH1S &h2)
9631{
9632 TH1S hnew = h1;
9633 hnew.Add(&h2,-1);
9634 hnew.SetDirectory(0);
9635 return hnew;
9636}
9637
9638////////////////////////////////////////////////////////////////////////////////
9639/// Operator *
9640
9641TH1S operator*(const TH1S &h1, const TH1S &h2)
9642{
9643 TH1S hnew = h1;
9644 hnew.Multiply(&h2);
9645 hnew.SetDirectory(0);
9646 return hnew;
9647}
9648
9649////////////////////////////////////////////////////////////////////////////////
9650/// Operator /
9651
9652TH1S operator/(const TH1S &h1, const TH1S &h2)
9653{
9654 TH1S hnew = h1;
9655 hnew.Divide(&h2);
9656 hnew.SetDirectory(0);
9657 return hnew;
9658}
9659
9660//______________________________________________________________________________
9661// TH1I methods
9662// TH1I : histograms with one int per channel. Maximum bin content = 2147483647
9663// 2147483647 = INT_MAX
9664//______________________________________________________________________________
9665
9666ClassImp(TH1I);
9667
9668////////////////////////////////////////////////////////////////////////////////
9669/// Constructor.
9670
9671TH1I::TH1I(): TH1(), TArrayI()
9672{
9673 fDimension = 1;
9674 SetBinsLength(3);
9675 if (fgDefaultSumw2) Sumw2();
9676}
9677
9678////////////////////////////////////////////////////////////////////////////////
9679/// Create a 1-Dim histogram with fix bins of type integer
9680/// (see TH1::TH1 for explanation of parameters)
9681
9682TH1I::TH1I(const char *name,const char *title,Int_t nbins,Double_t xlow,Double_t xup)
9683: TH1(name,title,nbins,xlow,xup)
9684{
9685 fDimension = 1;
9687
9688 if (xlow >= xup) SetBuffer(fgBufferSize);
9689 if (fgDefaultSumw2) Sumw2();
9690}
9691
9692////////////////////////////////////////////////////////////////////////////////
9693/// Create a 1-Dim histogram with variable bins of type integer
9694/// (see TH1::TH1 for explanation of parameters)
9695
9696TH1I::TH1I(const char *name,const char *title,Int_t nbins,const Float_t *xbins)
9697: TH1(name,title,nbins,xbins)
9698{
9699 fDimension = 1;
9701 if (fgDefaultSumw2) Sumw2();
9702}
9703
9704////////////////////////////////////////////////////////////////////////////////
9705/// Create a 1-Dim histogram with variable bins of type integer
9706/// (see TH1::TH1 for explanation of parameters)
9707
9708TH1I::TH1I(const char *name,const char *title,Int_t nbins,const Double_t *xbins)
9709: TH1(name,title,nbins,xbins)
9710{
9711 fDimension = 1;
9713 if (fgDefaultSumw2) Sumw2();
9714}
9715
9716////////////////////////////////////////////////////////////////////////////////
9717/// Destructor.
9718
9720{
9721}
9722
9723////////////////////////////////////////////////////////////////////////////////
9724/// Copy constructor.
9725/// The list of functions is not copied. (Use Clone() if needed)
9726
9727TH1I::TH1I(const TH1I &h1i) : TH1(), TArrayI()
9728{
9729 ((TH1I&)h1i).Copy(*this);
9730}
9731
9732////////////////////////////////////////////////////////////////////////////////
9733/// Increment bin content by 1.
9734
9735void TH1I::AddBinContent(Int_t bin)
9736{
9737 if (fArray[bin] < INT_MAX) fArray[bin]++;
9738}
9739
9740////////////////////////////////////////////////////////////////////////////////
9741/// Increment bin content by w
9742
9744{
9745 Long64_t newval = fArray[bin] + Long64_t(w);
9746 if (newval > -INT_MAX && newval < INT_MAX) {fArray[bin] = Int_t(newval); return;}
9747 if (newval < -INT_MAX) fArray[bin] = -INT_MAX;
9748 if (newval > INT_MAX) fArray[bin] = INT_MAX;
9749}
9750
9751////////////////////////////////////////////////////////////////////////////////
9752/// Copy this to newth1
9753
9754void TH1I::Copy(TObject &newth1) const
9755{
9756 TH1::Copy(newth1);
9757}
9758
9759////////////////////////////////////////////////////////////////////////////////
9760/// Reset.
9761
9762void TH1I::Reset(Option_t *option)
9763{
9764 TH1::Reset(option);
9766}
9767
9768////////////////////////////////////////////////////////////////////////////////
9769/// Set total number of bins including under/overflow
9770/// Reallocate bin contents array
9771
9773{
9774 if (n < 0) n = fXaxis.GetNbins() + 2;
9775 fNcells = n;
9776 TArrayI::Set(n);
9777}
9778
9779////////////////////////////////////////////////////////////////////////////////
9780/// Operator =
9781
9782TH1I& TH1I::operator=(const TH1I &h1)
9783{
9784 if (this != &h1) ((TH1I&)h1).Copy(*this);
9785 return *this;
9786}
9787
9788
9789////////////////////////////////////////////////////////////////////////////////
9790/// Operator *
9791
9793{
9794 TH1I hnew = h1;
9795 hnew.Scale(c1);
9796 hnew.SetDirectory(0);
9797 return hnew;
9798}
9799
9800////////////////////////////////////////////////////////////////////////////////
9801/// Operator +
9802
9803TH1I operator+(const TH1I &h1, const TH1I &h2)
9804{
9805 TH1I hnew = h1;
9806 hnew.Add(&h2,1);
9807 hnew.SetDirectory(0);
9808 return hnew;
9809}
9810
9811////////////////////////////////////////////////////////////////////////////////
9812/// Operator -
9813
9814TH1I operator-(const TH1I &h1, const TH1I &h2)
9815{
9816 TH1I hnew = h1;
9817 hnew.Add(&h2,-1);
9818 hnew.SetDirectory(0);
9819 return hnew;
9820}
9821
9822////////////////////////////////////////////////////////////////////////////////
9823/// Operator *
9824
9825TH1I operator*(const TH1I &h1, const TH1I &h2)
9826{
9827 TH1I hnew = h1;
9828 hnew.Multiply(&h2);
9829 hnew.SetDirectory(0);
9830 return hnew;
9831}
9832
9833////////////////////////////////////////////////////////////////////////////////
9834/// Operator /
9835
9836TH1I operator/(const TH1I &h1, const TH1I &h2)
9837{
9838 TH1I hnew = h1;
9839 hnew.Divide(&h2);
9840 hnew.SetDirectory(0);
9841 return hnew;
9842}
9843
9844//______________________________________________________________________________
9845// TH1F methods
9846// TH1F : histograms with one float per channel. Maximum precision 7 digits
9847//______________________________________________________________________________
9848
9849ClassImp(TH1F);
9850
9851////////////////////////////////////////////////////////////////////////////////
9852/// Constructor.
9853
9854TH1F::TH1F(): TH1(), TArrayF()
9855{
9856 fDimension = 1;
9857 SetBinsLength(3);
9858 if (fgDefaultSumw2) Sumw2();
9859}
9860
9861////////////////////////////////////////////////////////////////////////////////
9862/// Create a 1-Dim histogram with fix bins of type float
9863/// (see TH1::TH1 for explanation of parameters)
9864
9865TH1F::TH1F(const char *name,const char *title,Int_t nbins,Double_t xlow,Double_t xup)
9866: TH1(name,title,nbins,xlow,xup)
9867{
9868 fDimension = 1;
9870
9871 if (xlow >= xup) SetBuffer(fgBufferSize);
9872 if (fgDefaultSumw2) Sumw2();
9873}
9874
9875////////////////////////////////////////////////////////////////////////////////
9876/// Create a 1-Dim histogram with variable bins of type float
9877/// (see TH1::TH1 for explanation of parameters)
9878
9879TH1F::TH1F(const char *name,const char *title,Int_t nbins,const Float_t *xbins)
9880: TH1(name,title,nbins,xbins)
9881{
9882 fDimension = 1;
9884 if (fgDefaultSumw2) Sumw2();
9885}
9886
9887////////////////////////////////////////////////////////////////////////////////
9888/// Create a 1-Dim histogram with variable bins of type float
9889/// (see TH1::TH1 for explanation of parameters)
9890
9891TH1F::TH1F(const char *name,const char *title,Int_t nbins,const Double_t *xbins)
9892: TH1(name,title,nbins,xbins)
9893{
9894 fDimension = 1;
9896 if (fgDefaultSumw2) Sumw2();
9897}
9898
9899////////////////////////////////////////////////////////////////////////////////
9900/// Create a histogram from a TVectorF
9901/// by default the histogram name is "TVectorF" and title = ""
9902
9903TH1F::TH1F(const TVectorF &v)
9904: TH1("TVectorF","",v.GetNrows(),0,v.GetNrows())
9905{
9907 fDimension = 1;
9908 Int_t ivlow = v.GetLwb();
9909 for (Int_t i=0;i<fNcells-2;i++) {
9910 SetBinContent(i+1,v(i+ivlow));
9911 }
9913 if (fgDefaultSumw2) Sumw2();
9914}
9915
9916////////////////////////////////////////////////////////////////////////////////
9917/// Copy Constructor.
9918/// The list of functions is not copied. (Use Clone() if needed)
9919
9920TH1F::TH1F(const TH1F &h) : TH1(), TArrayF()
9921{
9922 ((TH1F&)h).Copy(*this);
9923}
9924
9925////////////////////////////////////////////////////////////////////////////////
9926/// Destructor.
9927
9929{
9930}
9931
9932////////////////////////////////////////////////////////////////////////////////
9933/// Copy this to newth1.
9934
9935void TH1F::Copy(TObject &newth1) const
9936{
9937 TH1::Copy(newth1);
9938}
9939
9940////////////////////////////////////////////////////////////////////////////////
9941/// Reset.
9942
9943void TH1F::Reset(Option_t *option)
9944{
9945 TH1::Reset(option);
9947}
9948
9949////////////////////////////////////////////////////////////////////////////////
9950/// Set total number of bins including under/overflow
9951/// Reallocate bin contents array
9952
9954{
9955 if (n < 0) n = fXaxis.GetNbins() + 2;
9956 fNcells = n;
9957 TArrayF::Set(n);
9958}
9959
9960////////////////////////////////////////////////////////////////////////////////
9961/// Operator =
9962
9963TH1F& TH1F::operator=(const TH1F &h1)
9964{
9965 if (this != &h1) ((TH1F&)h1).Copy(*this);
9966 return *this;
9967}
9968
9969////////////////////////////////////////////////////////////////////////////////
9970/// Operator *
9971
9973{
9974 TH1F hnew = h1;
9975 hnew.Scale(c1);
9976 hnew.SetDirectory(0);
9977 return hnew;
9978}
9979
9980////////////////////////////////////////////////////////////////////////////////
9981/// Operator +
9982
9983TH1F operator+(const TH1F &h1, const TH1F &h2)
9984{
9985 TH1F hnew = h1;
9986 hnew.Add(&h2,1);
9987 hnew.SetDirectory(0);
9988 return hnew;
9989}
9990
9991////////////////////////////////////////////////////////////////////////////////
9992/// Operator -
9993
9994TH1F operator-(const TH1F &h1, const TH1F &h2)
9995{
9996 TH1F hnew = h1;
9997 hnew.Add(&h2,-1);
9998 hnew.SetDirectory(0);
9999 return hnew;
10000}
10001
10002////////////////////////////////////////////////////////////////////////////////
10003/// Operator *
10004
10005TH1F operator*(const TH1F &h1, const TH1F &h2)
10006{
10007 TH1F hnew = h1;
10008 hnew.Multiply(&h2);
10009 hnew.SetDirectory(0);
10010 return hnew;
10011}
10012
10013////////////////////////////////////////////////////////////////////////////////
10014/// Operator /
10015
10016TH1F operator/(const TH1F &h1, const TH1F &h2)
10017{
10018 TH1F hnew = h1;
10019 hnew.Divide(&h2);
10020 hnew.SetDirectory(0);
10021 return hnew;
10022}
10023
10024//______________________________________________________________________________
10025// TH1D methods
10026// TH1D : histograms with one double per channel. Maximum precision 14 digits
10027//______________________________________________________________________________
10028
10029ClassImp(TH1D);
10030
10031////////////////////////////////////////////////////////////////////////////////
10032/// Constructor.
10033
10034TH1D::TH1D(): TH1(), TArrayD()
10035{
10036 fDimension = 1;
10037 SetBinsLength(3);
10038 if (fgDefaultSumw2) Sumw2();
10039}
10040
10041////////////////////////////////////////////////////////////////////////////////
10042/// Create a 1-Dim histogram with fix bins of type double
10043/// (see TH1::TH1 for explanation of parameters)
10044
10045TH1D::TH1D(const char *name,const char *title,Int_t nbins,Double_t xlow,Double_t xup)
10046: TH1(name,title,nbins,xlow,xup)
10047{
10048 fDimension = 1;
10050
10051 if (xlow >= xup) SetBuffer(fgBufferSize);
10052 if (fgDefaultSumw2) Sumw2();
10053}
10054
10055////////////////////////////////////////////////////////////////////////////////
10056/// Create a 1-Dim histogram with variable bins of type double
10057/// (see TH1::TH1 for explanation of parameters)
10058
10059TH1D::TH1D(const char *name,const char *title,Int_t nbins,const Float_t *xbins)
10060: TH1(name,title,nbins,xbins)
10061{
10062 fDimension = 1;
10064 if (fgDefaultSumw2) Sumw2();
10065}
10066
10067////////////////////////////////////////////////////////////////////////////////
10068/// Create a 1-Dim histogram with variable bins of type double
10069/// (see TH1::TH1 for explanation of parameters)
10070
10071TH1D::TH1D(const char *name,const char *title,Int_t nbins,const Double_t *xbins)
10072: TH1(name,title,nbins,xbins)
10073{
10074 fDimension = 1;
10076 if (fgDefaultSumw2) Sumw2();
10077}
10078
10079////////////////////////////////////////////////////////////////////////////////
10080/// Create a histogram from a TVectorD
10081/// by default the histogram name is "TVectorD" and title = ""
10082
10083TH1D::TH1D(const TVectorD &v)
10084: TH1("TVectorD","",v.GetNrows(),0,v.GetNrows())
10085{
10087 fDimension = 1;
10088 Int_t ivlow = v.GetLwb();
10089 for (Int_t i=0;i<fNcells-2;i++) {
10090 SetBinContent(i+1,v(i+ivlow));
10091 }
10093 if (fgDefaultSumw2) Sumw2();
10094}
10095
10096////////////////////////////////////////////////////////////////////////////////
10097/// Destructor.
10098
10100{
10101}
10102
10103////////////////////////////////////////////////////////////////////////////////
10104/// Constructor.
10105
10106TH1D::TH1D(const TH1D &h1d) : TH1(), TArrayD()
10107{
10108 ((TH1D&)h1d).Copy(*this);
10109}
10110
10111////////////////////////////////////////////////////////////////////////////////
10112/// Copy this to newth1
10113
10114void TH1D::Copy(TObject &newth1) const
10115{
10116 TH1::Copy(newth1);
10117}
10118
10119////////////////////////////////////////////////////////////////////////////////
10120/// Reset.
10121
10122void TH1D::Reset(Option_t *option)
10123{
10124 TH1::Reset(option);
10126}
10127
10128////////////////////////////////////////////////////////////////////////////////
10129/// Set total number of bins including under/overflow
10130/// Reallocate bin contents array
10131
10133{
10134 if (n < 0) n = fXaxis.GetNbins() + 2;
10135 fNcells = n;
10136 TArrayD::Set(n);
10137}
10138
10139////////////////////////////////////////////////////////////////////////////////
10140/// Operator =
10141
10142TH1D& TH1D::operator=(const TH1D &h1)
10143{
10144 if (this != &h1) ((TH1D&)h1).Copy(*this);
10145 return *this;
10146}
10147
10148////////////////////////////////////////////////////////////////////////////////
10149/// Operator *
10150
10152{
10153 TH1D hnew = h1;
10154 hnew.Scale(c1);
10155 hnew.SetDirectory(0);
10156 return hnew;
10157}
10158
10159////////////////////////////////////////////////////////////////////////////////
10160/// Operator +
10161
10162TH1D operator+(const TH1D &h1, const TH1D &h2)
10163{
10164 TH1D hnew = h1;
10165 hnew.Add(&h2,1);
10166 hnew.SetDirectory(0);
10167 return hnew;
10168}
10169
10170////////////////////////////////////////////////////////////////////////////////
10171/// Operator -
10172
10173TH1D operator-(const TH1D &h1, const TH1D &h2)
10174{
10175 TH1D hnew = h1;
10176 hnew.Add(&h2,-1);
10177 hnew.SetDirectory(0);
10178 return hnew;
10179}
10180
10181////////////////////////////////////////////////////////////////////////////////
10182/// Operator *
10183
10184TH1D operator*(const TH1D &h1, const TH1D &h2)
10185{
10186 TH1D hnew = h1;
10187 hnew.Multiply(&h2);
10188 hnew.SetDirectory(0);
10189 return hnew;
10190}
10191
10192////////////////////////////////////////////////////////////////////////////////
10193/// Operator /
10194
10195TH1D operator/(const TH1D &h1, const TH1D &h2)
10196{
10197 TH1D hnew = h1;
10198 hnew.Divide(&h2);
10199 hnew.SetDirectory(0);
10200 return hnew;
10201}
10202
10203////////////////////////////////////////////////////////////////////////////////
10204///return pointer to histogram with name
10205///hid if id >=0
10206///h_id if id <0
10207
10208TH1 *R__H(Int_t hid)
10209{
10210 TString hname;
10211 if(hid >= 0) hname.Form("h%d",hid);
10212 else hname.Form("h_%d",hid);
10213 return (TH1*)gDirectory->Get(hname);
10214}
10215
10216////////////////////////////////////////////////////////////////////////////////
10217///return pointer to histogram with name hname
10218
10219TH1 *R__H(const char * hname)
10220{
10221 return (TH1*)gDirectory->Get(hname);
10222}
10223
10224
10225/// \fn void TH1::SetBarOffset(Float_t offset)
10226/// Set the bar offset as fraction of the bin width for drawing mode "B".
10227/// This shifts bars to the right on the x axis, and helps to draw bars next to each other.
10228/// \see THistPainter, SetBarWidth()
10229
10230/// \fn void TH1::SetBarWidth(Float_t width)
10231/// Set the width of bars as fraction of the bin width for drawing mode "B".
10232/// This allows for making bars narrower than the bin width. With SetBarOffset(), this helps to draw multiple bars next to each other.
10233/// \see THistPainter, SetBarOffset()
#define b(i)
Definition RSha256.hxx:100
#define c(i)
Definition RSha256.hxx:101
#define a(i)
Definition RSha256.hxx:99
#define s1(x)
Definition RSha256.hxx:91
#define h(i)
Definition RSha256.hxx:106
#define e(i)
Definition RSha256.hxx:103
static const double x1[5]
int Int_t
Definition RtypesCore.h:45
short Version_t
Definition RtypesCore.h:65
char Char_t
Definition RtypesCore.h:37
unsigned int UInt_t
Definition RtypesCore.h:46
const Bool_t kFALSE
Definition RtypesCore.h:101
bool Bool_t
Definition RtypesCore.h:63
short Short_t
Definition RtypesCore.h:39
double Double_t
Definition RtypesCore.h:59
double Stat_t
Definition RtypesCore.h:86
short Color_t
Definition RtypesCore.h:92
long long Long64_t
Definition RtypesCore.h:80
short Style_t
Definition RtypesCore.h:89
float Float_t
Definition RtypesCore.h:57
const Bool_t kTRUE
Definition RtypesCore.h:100
const char Option_t
Definition RtypesCore.h:66
#define ClassImp(name)
Definition Rtypes.h:364
#define gDirectory
Definition TDirectory.h:385
include TDocParser_001 C image html pict1_TDocParser_001 png width
R__EXTERN TEnv * gEnv
Definition TEnv.h:170
#define R__ASSERT(e)
Definition TError.h:118
char name[80]
Definition TGX11.cxx:110
int type
Definition TGX11.cxx:121
static bool IsEquidistantBinning(const TAxis &axis)
Test if the binning is equidistant.
Definition TH1.cxx:5811
void H1LeastSquareLinearFit(Int_t ndata, Double_t &a0, Double_t &a1, Int_t &ifail)
Least square linear fit without weights.
Definition TH1.cxx:4759
void H1InitGaus()
Compute Initial values of parameters for a gaussian.
Definition TH1.cxx:4594
void H1InitExpo()
Compute Initial values of parameters for an exponential.
Definition TH1.cxx:4650
TH1C operator+(const TH1C &h1, const TH1C &h2)
Operator +.
Definition TH1.cxx:9435
TH1C operator-(const TH1C &h1, const TH1C &h2)
Operator -.
Definition TH1.cxx:9446
TH1C operator/(const TH1C &h1, const TH1C &h2)
Operator /.
Definition TH1.cxx:9468
void H1LeastSquareSeqnd(Int_t n, Double_t *a, Int_t idim, Int_t &ifail, Int_t k, Double_t *b)
Extracted from CERN Program library routine DSEQN.
Definition TH1.cxx:4805
static Bool_t AlmostEqual(Double_t a, Double_t b, Double_t epsilon=0.00000001)
Test if two double are almost equal.
Definition TH1.cxx:5794
static Bool_t AlmostInteger(Double_t a, Double_t epsilon=0.00000001)
Test if a double is almost an integer.
Definition TH1.cxx:5802
TF1 * gF1
Definition TH1.cxx:576
TH1 * R__H(Int_t hid)
return pointer to histogram with name hid if id >=0 h_id if id <0
Definition TH1.cxx:10206
TH1C operator*(Double_t c1, const TH1C &h1)
Operator *.
Definition TH1.cxx:9424
void H1LeastSquareFit(Int_t n, Int_t m, Double_t *a)
Least squares lpolynomial fitting without weights.
Definition TH1.cxx:4700
void H1InitPolynom()
Compute Initial values of parameters for a polynom.
Definition TH1.cxx:4670
float xmin
int nentries
float * q
float ymin
float xmax
float ymax
#define gInterpreter
Int_t gDebug
Definition TROOT.cxx:592
R__EXTERN TVirtualMutex * gROOTMutex
Definition TROOT.h:63
#define gROOT
Definition TROOT.h:404
R__EXTERN TRandom * gRandom
Definition TRandom.h:62
char * Form(const char *fmt,...)
void Printf(const char *fmt,...)
R__EXTERN TStyle * gStyle
Definition TStyle.h:413
#define R__LOCKGUARD(mutex)
#define gPad
#define R__WRITE_LOCKGUARD(mutex)
Class describing the binned data sets : vectors of x coordinates, y values and optionally error on y ...
Definition BinData.h:52
class describing the range in the coordinates it supports multiple range in a coordinate.
Definition DataRange.h:35
void AndersonDarling2SamplesTest(Double_t &pvalue, Double_t &testStat) const
Definition GoFTest.cxx:645
Array of chars or bytes (8 bits per element).
Definition TArrayC.h:27
void Set(Int_t n)
Set size of this array to n chars.
Definition TArrayC.cxx:105
Char_t * fArray
Definition TArrayC.h:30
void Copy(TArrayC &array) const
Definition TArrayC.h:42
void Reset(Char_t val=0)
Definition TArrayC.h:47
Array of doubles (64 bits per element).
Definition TArrayD.h:27
Double_t GetAt(Int_t i) const
Definition TArrayD.h:45
Double_t * fArray
Definition TArrayD.h:30
void Copy(TArrayD &array) const
Definition TArrayD.h:42
void Set(Int_t n)
Set size of this array to n doubles.
Definition TArrayD.cxx:106
const Double_t * GetArray() const
Definition TArrayD.h:43
void Reset()
Definition TArrayD.h:47
Array of floats (32 bits per element).
Definition TArrayF.h:27
void Copy(TArrayF &array) const
Definition TArrayF.h:42
void Reset()
Definition TArrayF.h:47
void Set(Int_t n)
Set size of this array to n floats.
Definition TArrayF.cxx:105
Array of integers (32 bits per element).
Definition TArrayI.h:27
Int_t * fArray
Definition TArrayI.h:30
void Set(Int_t n)
Set size of this array to n ints.
Definition TArrayI.cxx:105
void Reset()
Definition TArrayI.h:47
void Copy(TArrayI &array) const
Definition TArrayI.h:42
Array of shorts (16 bits per element).
Definition TArrayS.h:27
void Set(Int_t n)
Set size of this array to n shorts.
Definition TArrayS.cxx:105
void Reset()
Definition TArrayS.h:47
void Copy(TArrayS &array) const
Definition TArrayS.h:42
Short_t * fArray
Definition TArrayS.h:30
Abstract array base class.
Definition TArray.h:31
Int_t fN
Definition TArray.h:38
virtual void Set(Int_t n)=0
Int_t GetSize() const
Definition TArray.h:47
virtual Color_t GetTitleColor() const
Definition TAttAxis.h:46
virtual Color_t GetLabelColor() const
Definition TAttAxis.h:38
virtual Int_t GetNdivisions() const
Definition TAttAxis.h:36
virtual Color_t GetAxisColor() const
Definition TAttAxis.h:37
virtual void SetTitleOffset(Float_t offset=1)
Set distance between the axis and the axis title.
Definition TAttAxis.cxx:302
virtual Style_t GetTitleFont() const
Definition TAttAxis.h:47
virtual Float_t GetLabelOffset() const
Definition TAttAxis.h:40
virtual void SetAxisColor(Color_t color=1, Float_t alpha=1.)
Set color of the line axis and tick marks.
Definition TAttAxis.cxx:163
virtual void SetLabelSize(Float_t size=0.04)
Set size of axis labels.
Definition TAttAxis.cxx:205
virtual Style_t GetLabelFont() const
Definition TAttAxis.h:39
virtual void SetTitleFont(Style_t font=62)
Set the title font.
Definition TAttAxis.cxx:330
virtual void SetLabelOffset(Float_t offset=0.005)
Set distance between the axis and the labels.
Definition TAttAxis.cxx:194
virtual void SetLabelFont(Style_t font=62)
Set labels' font.
Definition TAttAxis.cxx:183
virtual void SetTitleSize(Float_t size=0.04)
Set size of axis title.
Definition TAttAxis.cxx:312
virtual void SetTitleColor(Color_t color=1)
Set color of axis title.
Definition TAttAxis.cxx:321
virtual Float_t GetTitleSize() const
Definition TAttAxis.h:44
virtual Float_t GetLabelSize() const
Definition TAttAxis.h:41
virtual Float_t GetTickLength() const
Definition TAttAxis.h:45
virtual void ResetAttAxis(Option_t *option="")
Reset axis attributes.
Definition TAttAxis.cxx:79
virtual Float_t GetTitleOffset() const
Definition TAttAxis.h:43
virtual void SetTickLength(Float_t length=0.03)
Set tick mark length.
Definition TAttAxis.cxx:288
virtual void SetNdivisions(Int_t n=510, Bool_t optim=kTRUE)
Set the number of divisions for this axis.
Definition TAttAxis.cxx:237
virtual void SetLabelColor(Color_t color=1, Float_t alpha=1.)
Set color of labels.
Definition TAttAxis.cxx:173
Fill Area Attributes class.
Definition TAttFill.h:19
virtual Color_t GetFillColor() const
Return the fill area color.
Definition TAttFill.h:30
void Copy(TAttFill &attfill) const
Copy this fill attributes to a new TAttFill.
Definition TAttFill.cxx:204
virtual Style_t GetFillStyle() const
Return the fill area style.
Definition TAttFill.h:31
virtual void SetFillColor(Color_t fcolor)
Set the fill area color.
Definition TAttFill.h:37
virtual void SetFillStyle(Style_t fstyle)
Set the fill area style.
Definition TAttFill.h:39
virtual void SaveFillAttributes(std::ostream &out, const char *name, Int_t coldef=1, Int_t stydef=1001)
Save fill attributes as C++ statement(s) on output stream out.
Definition TAttFill.cxx:236
Line Attributes class.
Definition TAttLine.h:18
virtual Color_t GetLineColor() const
Return the line color.
Definition TAttLine.h:33
virtual void SetLineStyle(Style_t lstyle)
Set the line style.
Definition TAttLine.h:42
virtual Width_t GetLineWidth() const
Return the line width.
Definition TAttLine.h:35
virtual void SetLineWidth(Width_t lwidth)
Set the line width.
Definition TAttLine.h:43
virtual void SetLineColor(Color_t lcolor)
Set the line color.
Definition TAttLine.h:40
virtual Style_t GetLineStyle() const
Return the line style.
Definition TAttLine.h:34
void Copy(TAttLine &attline) const
Copy this line attributes to a new TAttLine.
Definition TAttLine.cxx:175
virtual void SaveLineAttributes(std::ostream &out, const char *name, Int_t coldef=1, Int_t stydef=1, Int_t widdef=1)
Save line attributes as C++ statement(s) on output stream out.
Definition TAttLine.cxx:273
Marker Attributes class.
Definition TAttMarker.h:19
virtual void SaveMarkerAttributes(std::ostream &out, const char *name, Int_t coldef=1, Int_t stydef=1, Int_t sizdef=1)
Save line attributes as C++ statement(s) on output stream out.
virtual Style_t GetMarkerStyle() const
Return the marker style.
Definition TAttMarker.h:32
virtual void SetMarkerColor(Color_t mcolor=1)
Set the marker color.
Definition TAttMarker.h:38
virtual Color_t GetMarkerColor() const
Return the marker color.
Definition TAttMarker.h:31
virtual Size_t GetMarkerSize() const
Return the marker size.
Definition TAttMarker.h:33
virtual void SetMarkerStyle(Style_t mstyle=1)
Set the marker style.
Definition TAttMarker.h:40
void Copy(TAttMarker &attmarker) const
Copy this marker attributes to a new TAttMarker.
virtual void SetMarkerSize(Size_t msize=1)
Set the marker size.
Definition TAttMarker.h:41
Class to manage histogram axis.
Definition TAxis.h:30
virtual void GetCenter(Double_t *center) const
Return an array with the center of all bins.
Definition TAxis.cxx:553
virtual Bool_t GetTimeDisplay() const
Definition TAxis.h:126
Bool_t IsAlphanumeric() const
Definition TAxis.h:84
virtual Double_t GetBinCenter(Int_t bin) const
Return center of bin.
Definition TAxis.cxx:478
Bool_t CanExtend() const
Definition TAxis.h:82
virtual void SetParent(TObject *obj)
Definition TAxis.h:157
const TArrayD * GetXbins() const
Definition TAxis.h:130
void SetCanExtend(Bool_t canExtend)
Definition TAxis.h:86
Double_t GetXmax() const
Definition TAxis.h:134
virtual void SaveAttributes(std::ostream &out, const char *name, const char *subname)
Save axis attributes as C++ statement(s) on output stream out.
Definition TAxis.cxx:661
@ kLabelsUp
Definition TAxis.h:70
@ kLabelsDown
Definition TAxis.h:69
@ kLabelsHori
Definition TAxis.h:67
@ kAxisRange
Definition TAxis.h:61
@ kLabelsVert
Definition TAxis.h:68
const char * GetBinLabel(Int_t bin) const
Return label for bin.
Definition TAxis.cxx:440
virtual Int_t FindBin(Double_t x)
Find bin number corresponding to abscissa x.
Definition TAxis.cxx:293
virtual Double_t GetBinLowEdge(Int_t bin) const
Return low edge of bin.
Definition TAxis.cxx:518
virtual void SetTimeDisplay(Int_t value)
Definition TAxis.h:161
virtual void Set(Int_t nbins, Double_t xmin, Double_t xmax)
Initialize axis with fix bins.
Definition TAxis.cxx:731
virtual Int_t FindFixBin(Double_t x) const
Find bin number corresponding to abscissa x.
Definition TAxis.cxx:419
virtual void Copy(TObject &axis) const
Copy axis structure to another axis.
Definition TAxis.cxx:210
Int_t GetLast() const
Return last bin on the axis i.e.
Definition TAxis.cxx:469
virtual void SetLimits(Double_t xmin, Double_t xmax)
Definition TAxis.h:154
Double_t GetXmin() const
Definition TAxis.h:133
Int_t GetNbins() const
Definition TAxis.h:121
virtual void GetLowEdge(Double_t *edge) const
Return an array with the low edge of all bins.
Definition TAxis.cxx:562
virtual void SetRange(Int_t first=0, Int_t last=0)
Set the viewing range for the axis using bin numbers.
Definition TAxis.cxx:920
virtual Double_t GetBinWidth(Int_t bin) const
Return bin width.
Definition TAxis.cxx:540
virtual Double_t GetBinUpEdge(Int_t bin) const
Return up edge of bin.
Definition TAxis.cxx:528
Int_t GetFirst() const
Return first bin on the axis i.e.
Definition TAxis.cxx:458
THashList * GetLabels() const
Definition TAxis.h:117
Using a TBrowser one can browse all ROOT objects.
Definition TBrowser.h:37
Buffer base class used for serializing objects.
Definition TBuffer.h:43
Collection abstract base class.
Definition TCollection.h:65
virtual bool UseRWLock(Bool_t enable=true)
Set this collection to use a RW lock upon access, making it thread safe.
virtual void AddAll(const TCollection *col)
Add all objects from collection col to this collection.
virtual TObject * Clone(const char *newname="") const
Make a clone of an collection using the Streamer facility.
virtual Bool_t IsEmpty() const
virtual Int_t GetSize() const
Return the capacity of the collection, i.e.
Describe directory structure in memory.
Definition TDirectory.h:45
virtual void Append(TObject *obj, Bool_t replace=kFALSE)
Append object to this directory.
virtual TObject * Remove(TObject *)
Remove an object from the in-memory list.
virtual Int_t GetValue(const char *name, Int_t dflt) const
Returns the integer value for a resource.
Definition TEnv.cxx:491
1-Dim function class
Definition TF1.h:213
static void RejectPoint(Bool_t reject=kTRUE)
Static function to set the global flag to reject points the fgRejectPoint global flag is tested by al...
Definition TF1.cxx:3665
virtual TH1 * GetHistogram() const
Return a pointer to the histogram used to visualise the function Note that this histogram is managed ...
Definition TF1.cxx:1580
virtual Int_t GetNpar() const
Definition TF1.h:481
virtual Double_t Integral(Double_t a, Double_t b, Double_t epsrel=1.e-12)
IntegralOneDim or analytical integral.
Definition TF1.cxx:2521
virtual Double_t EvalPar(const Double_t *x, const Double_t *params=0)
Evaluate function with given coordinates and parameters.
Definition TF1.cxx:1469
virtual void InitArgs(const Double_t *x, const Double_t *params)
Initialize parameters addresses.
Definition TF1.cxx:2473
virtual void GetRange(Double_t *xmin, Double_t *xmax) const
Return range of a generic N-D function.
Definition TF1.cxx:2275
virtual void SetParLimits(Int_t ipar, Double_t parmin, Double_t parmax)
Set limits for parameter ipar.
Definition TF1.cxx:3518
static Bool_t RejectedPoint()
See TF1::RejectPoint above.
Definition TF1.cxx:3674
virtual Double_t Eval(Double_t x, Double_t y=0, Double_t z=0, Double_t t=0) const
Evaluate this function.
Definition TF1.cxx:1440
virtual void SetParameter(Int_t param, Double_t value)
Definition TF1.h:634
virtual Bool_t IsInside(const Double_t *x) const
return kTRUE if the point is inside the function range
Definition TF1.h:598
A 2-Dim function with parameters.
Definition TF2.h:29
A 3-Dim function with parameters.
Definition TF3.h:28
Provides an indirection to the TFitResult class and with a semantics identical to a TFitResult pointe...
1-D histogram with a byte per channel (see TH1 documentation)
Definition TH1.h:452
TH1C & operator=(const TH1C &h1)
Operator =.
Definition TH1.cxx:9415
TH1C()
Constructor.
Definition TH1.cxx:9304
virtual void Copy(TObject &hnew) const
Copy this to newth1.
Definition TH1.cxx:9387
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH1.cxx:9405
virtual void AddBinContent(Int_t bin)
Increment bin content by 1.
Definition TH1.cxx:9368
virtual ~TH1C()
Destructor.
Definition TH1.cxx:9352
virtual void Reset(Option_t *option="")
Reset.
Definition TH1.cxx:9395
1-D histogram with a double per channel (see TH1 documentation)}
Definition TH1.h:618
virtual void Copy(TObject &hnew) const
Copy this to newth1.
Definition TH1.cxx:10112
virtual ~TH1D()
Destructor.
Definition TH1.cxx:10097
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH1.cxx:10130
TH1D()
Constructor.
Definition TH1.cxx:10032
TH1D & operator=(const TH1D &h1)
Operator =.
Definition TH1.cxx:10140
1-D histogram with a float per channel (see TH1 documentation)}
Definition TH1.h:575
virtual Double_t RetrieveBinContent(Int_t bin) const
Raw retrieval of bin content on internal data structure see convention for numbering bins in TH1::Get...
Definition TH1.h:604
virtual ~TH1F()
Destructor.
Definition TH1.cxx:9926
TH1F & operator=(const TH1F &h1)
Operator =.
Definition TH1.cxx:9961
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH1.cxx:9951
virtual void Copy(TObject &hnew) const
Copy this to newth1.
Definition TH1.cxx:9933
TH1F()
Constructor.
Definition TH1.cxx:9852
1-D histogram with an int per channel (see TH1 documentation)}
Definition TH1.h:534
virtual void Copy(TObject &hnew) const
Copy this to newth1.
Definition TH1.cxx:9752
virtual void AddBinContent(Int_t bin)
Increment bin content by 1.
Definition TH1.cxx:9733
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH1.cxx:9770
virtual ~TH1I()
Destructor.
Definition TH1.cxx:9717
TH1I()
Constructor.
Definition TH1.cxx:9669
TH1I & operator=(const TH1I &h1)
Operator =.
Definition TH1.cxx:9780
1-D histogram with a short per channel (see TH1 documentation)
Definition TH1.h:493
virtual void AddBinContent(Int_t bin)
Increment bin content by 1.
Definition TH1.cxx:9550
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH1.cxx:9587
virtual ~TH1S()
Destructor.
Definition TH1.cxx:9534
TH1S & operator=(const TH1S &h1)
Operator =.
Definition TH1.cxx:9597
virtual void Copy(TObject &hnew) const
Copy this to newth1.
Definition TH1.cxx:9569
TH1S()
Constructor.
Definition TH1.cxx:9486
TH1 is the base class of all histogram classes in ROOT.
Definition TH1.h:58
virtual void SetError(const Double_t *error)
Replace bin errors by values in array error.
Definition TH1.cxx:8781
virtual void SetDirectory(TDirectory *dir)
By default, when a histogram is created, it is added to the list of histogram objects in the current ...
Definition TH1.cxx:8767
virtual void FitPanel()
Display a panel with all histogram fit options.
Definition TH1.cxx:4248
Double_t * fBuffer
[fBufferSize] entry buffer
Definition TH1.h:107
virtual Int_t AutoP2FindLimits(Double_t min, Double_t max)
Buffer-based estimate of the histogram range using the power of 2 algorithm.
Definition TH1.cxx:1332
virtual Double_t GetEffectiveEntries() const
Number of effective entries of the histogram.
Definition TH1.cxx:4412
virtual void SavePrimitive(std::ostream &out, Option_t *option="")
Save primitive as a C++ statement(s) on output stream out.
Definition TH1.cxx:7111
virtual void SetTitle(const char *title)
See GetStatOverflows for more information.
Definition TH1.cxx:6667
virtual void Smooth(Int_t ntimes=1, Option_t *option="")
Smooth bin contents of this histogram.
Definition TH1.cxx:6834
virtual void Print(Option_t *option="") const
Print some global quantities for this histogram.
Definition TH1.cxx:6964
virtual Double_t GetBinCenter(Int_t bin) const
Return bin center for 1D histogram.
Definition TH1.cxx:8971
virtual void Rebuild(Option_t *option="")
Using the current bin info, recompute the arrays for contents and errors.
Definition TH1.cxx:7042
virtual void SetBarOffset(Float_t offset=0.25)
Set the bar offset as fraction of the bin width for drawing mode "B".
Definition TH1.h:359
static Bool_t fgStatOverflows
! Flag to use under/overflows in statistics
Definition TH1.h:116
virtual Int_t FindLastBinAbove(Double_t threshold=0, Int_t axis=1, Int_t firstBin=1, Int_t lastBin=-1) const
Find last bin with content > threshold for axis (1=x, 2=y, 3=z) if no bins with content > threshold i...
Definition TH1.cxx:3806
TAxis * GetZaxis()
Definition TH1.h:322
virtual Bool_t Multiply(TF1 *f1, Double_t c1=1)
Performs the operation:
Definition TH1.cxx:5982
virtual void Browse(TBrowser *b)
Browse the Histogram object.
Definition TH1.cxx:759
@ kXaxis
Definition TH1.h:72
@ kNoAxis
NOTE: Must always be 0 !!!
Definition TH1.h:71
@ kZaxis
Definition TH1.h:74
@ kYaxis
Definition TH1.h:73
Int_t fNcells
Number of bins(1D), cells (2D) +U/Overflows.
Definition TH1.h:88
virtual void GetStats(Double_t *stats) const
fill the array stats from the contents of this histogram The array stats must be correctly dimensione...
Definition TH1.cxx:7708
Double_t fTsumw
Total Sum of weights.
Definition TH1.h:95
virtual Float_t GetBarWidth() const
Definition TH1.h:256
Double_t fTsumw2
Total Sum of squares of weights.
Definition TH1.h:96
static void StatOverflows(Bool_t flag=kTRUE)
if flag=kTRUE, underflows and overflows are used by the Fill functions in the computation of statisti...
Definition TH1.cxx:6880
virtual Float_t GetBarOffset() const
Definition TH1.h:255
virtual ~TH1()
Histogram default destructor.
Definition TH1.cxx:630
TList * fFunctions
->Pointer to list of functions (fits and user)
Definition TH1.h:105
static Bool_t fgAddDirectory
! Flag to add histograms to the directory
Definition TH1.h:115
virtual Int_t GetQuantiles(Int_t nprobSum, Double_t *q, const Double_t *probSum=0)
Compute Quantiles for this histogram Quantile x_q of a probability distribution Function F is defined...
Definition TH1.cxx:4544
static Int_t GetDefaultBufferSize()
Static function return the default buffer size for automatic histograms the parameter fgBufferSize ma...
Definition TH1.cxx:4370
virtual Double_t DoIntegral(Int_t ix1, Int_t ix2, Int_t iy1, Int_t iy2, Int_t iz1, Int_t iz2, Double_t &err, Option_t *opt, Bool_t doerr=kFALSE) const
Internal function compute integral and optionally the error between the limits specified by the bin n...
Definition TH1.cxx:7852
Double_t fTsumwx2
Total Sum of weight*X*X.
Definition TH1.h:98
virtual Double_t GetStdDev(Int_t axis=1) const
Returns the Standard Deviation (Sigma).
Definition TH1.cxx:7482
TH1()
Histogram default constructor.
Definition TH1.cxx:602
static TH1 * TransformHisto(TVirtualFFT *fft, TH1 *h_output, Option_t *option)
For a given transform (first parameter), fills the histogram (second parameter) with the transform ou...
Definition TH1.cxx:9150
virtual void LabelsOption(Option_t *option="h", Option_t *axis="X")
Sort bins with labels or set option(s) to draw axis with labels.
Definition TH1.cxx:5315
virtual Int_t GetNbinsY() const
Definition TH1.h:297
Short_t fBarOffset
(1000*offset) for bar charts or legos
Definition TH1.h:92
static bool CheckBinLimits(const TAxis *a1, const TAxis *a2)
Check bin limits.
Definition TH1.cxx:1528
virtual void AddBinContent(Int_t bin)
Increment bin content by 1.
Definition TH1.cxx:1258
virtual Double_t GetBinError(Int_t bin) const
Return value of error associated to bin number bin.
Definition TH1.cxx:8893
static Int_t FitOptionsMake(Option_t *option, Foption_t &Foption)
Decode string choptin and fill fitOption structure.
Definition TH1.cxx:4585
virtual Int_t GetNbinsZ() const
Definition TH1.h:298
virtual Double_t GetNormFactor() const
Definition TH1.h:300
virtual Double_t GetMean(Int_t axis=1) const
For axis = 1,2 or 3 returns the mean value of the histogram along X,Y or Z axis.
Definition TH1.cxx:7410
virtual Double_t GetSkewness(Int_t axis=1) const
Definition TH1.cxx:7546
virtual void ClearUnderflowAndOverflow()
Remove all the content from the underflow and overflow bins, without changing the number of entries A...
Definition TH1.cxx:2512
virtual Double_t GetContourLevelPad(Int_t level) const
Return the value of contour number "level" in Pad coordinates.
Definition TH1.cxx:8270
virtual TH1 * DrawNormalized(Option_t *option="", Double_t norm=1) const
Draw a normalized copy of this histogram.
Definition TH1.cxx:3151
@ kNeutral
Adapt to the global flag.
Definition TH1.h:82
virtual Double_t Chi2TestX(const TH1 *h2, Double_t &chi2, Int_t &ndf, Int_t &igood, Option_t *option="UU", Double_t *res=0) const
The computation routine of the Chisquare test.
Definition TH1.cxx:2065
virtual Int_t GetDimension() const
Definition TH1.h:282
static void AddDirectory(Bool_t add=kTRUE)
Sets the flag controlling the automatic add of histograms in memory.
Definition TH1.cxx:1283
@ kIsAverage
Bin contents are average (used by Add)
Definition TH1.h:170
@ kUserContour
User specified contour levels.
Definition TH1.h:165
@ kNoStats
Don't draw stats box.
Definition TH1.h:164
@ kAutoBinPTwo
Use Power(2)-based algorithm for autobinning.
Definition TH1.h:173
@ kIsNotW
Histogram is forced to be not weighted even when the histogram is filled with weighted different than...
Definition TH1.h:171
@ kIsHighlight
bit set if histo is highlight
Definition TH1.h:174
virtual void SetContourLevel(Int_t level, Double_t value)
Set value for one contour level.
Definition TH1.cxx:8352
virtual Bool_t CanExtendAllAxes() const
Returns true if all axes are extendable.
Definition TH1.cxx:6585
TDirectory * fDirectory
! Pointer to directory holding this histogram
Definition TH1.h:108
virtual void Reset(Option_t *option="")
Reset this histogram: contents, errors, etc.
Definition TH1.cxx:7058
TAxis * GetXaxis()
Get the behaviour adopted by the object about the statoverflows. See EStatOverflows for more informat...
Definition TH1.h:320
virtual void GetBinXYZ(Int_t binglobal, Int_t &binx, Int_t &biny, Int_t &binz) const
Return binx, biny, binz corresponding to the global bin number globalbin see TH1::GetBin function abo...
Definition TH1.cxx:4907
TH1 * GetCumulative(Bool_t forward=kTRUE, const char *suffix="_cumulative") const
Return a pointer to a histogram containing the cumulative content.
Definition TH1.cxx:2609
void UseCurrentStyle()
Copy current attributes from/to current style.
Definition TH1.cxx:7344
static Double_t AutoP2GetPower2(Double_t x, Bool_t next=kTRUE)
Auxiliary function to get the power of 2 next (larger) or previous (smaller) a given x.
Definition TH1.cxx:1297
virtual Int_t GetNcells() const
Definition TH1.h:299
virtual Int_t ShowPeaks(Double_t sigma=2, Option_t *option="", Double_t threshold=0.05)
Interface to TSpectrum::Search.
Definition TH1.cxx:9132
static Bool_t RecomputeAxisLimits(TAxis &destAxis, const TAxis &anAxis)
Finds new limits for the axis for the Merge function.
Definition TH1.cxx:5841
virtual void PutStats(Double_t *stats)
Replace current statistics with the values in array stats.
Definition TH1.cxx:7759
TVirtualHistPainter * GetPainter(Option_t *option="")
Return pointer to painter.
Definition TH1.cxx:4453
TObject * Clone(const char *newname=0) const
Make a complete copy of the underlying object.
Definition TH1.cxx:2741
virtual void FillRandom(const char *fname, Int_t ntimes=5000, TRandom *rng=nullptr)
Fill histogram following distribution in function fname.
Definition TH1.cxx:3526
static Bool_t GetDefaultSumw2()
Return kTRUE if TH1::Sumw2 must be called when creating new histograms.
Definition TH1.cxx:4379
virtual Int_t FindFirstBinAbove(Double_t threshold=0, Int_t axis=1, Int_t firstBin=1, Int_t lastBin=-1) const
Find first bin with content > threshold for axis (1=x, 2=y, 3=z) if no bins with content > threshold ...
Definition TH1.cxx:3743
virtual TFitResultPtr Fit(const char *formula, Option_t *option="", Option_t *goption="", Double_t xmin=0, Double_t xmax=0)
Fit histogram with function fname.
Definition TH1.cxx:3893
virtual Int_t GetBin(Int_t binx, Int_t biny=0, Int_t binz=0) const
Return Global bin number corresponding to binx,y,z.
Definition TH1.cxx:4894
virtual Double_t GetMaximum(Double_t maxval=FLT_MAX) const
Return maximum value smaller than maxval of bins in the range, unless the value has been overridden b...
Definition TH1.cxx:8375
virtual Int_t GetNbinsX() const
Definition TH1.h:296
virtual void SetMaximum(Double_t maximum=-1111)
Definition TH1.h:398
virtual TH1 * FFT(TH1 *h_output, Option_t *option)
This function allows to do discrete Fourier transforms of TH1 and TH2.
Definition TH1.cxx:3291
virtual void LabelsInflate(Option_t *axis="X")
Double the number of bins for axis.
Definition TH1.cxx:5248
virtual TH1 * ShowBackground(Int_t niter=20, Option_t *option="same")
This function calculates the background spectrum in this histogram.
Definition TH1.cxx:9117
virtual Double_t Chi2Test(const TH1 *h2, Option_t *option="UU", Double_t *res=0) const
test for comparing weighted and unweighted histograms
Definition TH1.cxx:2006
static Bool_t SameLimitsAndNBins(const TAxis &axis1, const TAxis &axis2)
Same limits and bins.
Definition TH1.cxx:5831
virtual Bool_t Add(TF1 *h1, Double_t c1=1, Option_t *option="")
Performs the operation: this = this + c1*f1 if errors are defined (see TH1::Sumw2),...
Definition TH1.cxx:823
Double_t fMaximum
Maximum value for plotting.
Definition TH1.h:99
Int_t fBufferSize
fBuffer size
Definition TH1.h:106
virtual void RecursiveRemove(TObject *obj)
Recursively remove object from the list of functions.
Definition TH1.cxx:6525
virtual Double_t RetrieveBinContent(Int_t bin) const
Raw retrieval of bin content on internal data structure see convention for numbering bins in TH1::Get...
Definition TH1.cxx:9270
virtual Double_t IntegralAndError(Int_t binx1, Int_t binx2, Double_t &err, Option_t *option="") const
Return integral of bin contents in range [binx1,binx2] and its error.
Definition TH1.cxx:7843
Int_t fDimension
! Histogram dimension (1, 2 or 3 dim)
Definition TH1.h:109
virtual void SetBinError(Int_t bin, Double_t error)
Set the bin Error Note that this resets the bin eror option to be of Normal Type and for the non-empt...
Definition TH1.cxx:9036
EBinErrorOpt fBinStatErrOpt
Option for bin statistical errors.
Definition TH1.h:112
static Int_t fgBufferSize
! Default buffer size for automatic histograms
Definition TH1.h:114
virtual void SetBinsLength(Int_t=-1)
Definition TH1.h:375
Double_t fNormFactor
Normalization factor.
Definition TH1.h:101
virtual Int_t Fill(Double_t x)
Increment bin with abscissa X by 1.
Definition TH1.cxx:3351
virtual TObject * FindObject(const char *name) const
Search object named name in the list of functions.
Definition TH1.cxx:3866
TAxis * GetYaxis()
Definition TH1.h:321
TArrayD fContour
Array to display contour levels.
Definition TH1.h:102
virtual Double_t GetBinErrorLow(Int_t bin) const
Return lower error associated to bin number bin.
Definition TH1.cxx:8909
virtual void SetContent(const Double_t *content)
Replace bin contents by the contents of array content.
Definition TH1.cxx:8228
virtual void SavePrimitiveHelp(std::ostream &out, const char *hname, Option_t *option="")
Helper function for the SavePrimitive functions from TH1 or classes derived from TH1,...
Definition TH1.cxx:7253
Short_t fBarWidth
(1000*width) for bar charts or legos
Definition TH1.h:93
virtual void SetContour(Int_t nlevels, const Double_t *levels=0)
Set the number and values of contour levels.
Definition TH1.cxx:8313
virtual Double_t GetBinErrorSqUnchecked(Int_t bin) const
Definition TH1.h:443
Int_t AxisChoice(Option_t *axis) const
Choose an axis according to "axis".
Definition Haxis.cxx:14
virtual void SetMinimum(Double_t minimum=-1111)
Definition TH1.h:399
Bool_t IsBinUnderflow(Int_t bin, Int_t axis=0) const
Return true if the bin is underflow.
Definition TH1.cxx:5147
static bool CheckBinLabels(const TAxis *a1, const TAxis *a2)
Check that axis have same labels.
Definition TH1.cxx:1557
virtual Double_t Interpolate(Double_t x) const
Given a point x, approximates the value via linear interpolation based on the two nearest bin centers...
Definition TH1.cxx:5048
static void SetDefaultSumw2(Bool_t sumw2=kTRUE)
When this static function is called with sumw2=kTRUE, all new histograms will automatically activate ...
Definition TH1.cxx:6652
Bool_t IsBinOverflow(Int_t bin, Int_t axis=0) const
Return true if the bin is overflow.
Definition TH1.cxx:5115
UInt_t GetAxisLabelStatus() const
Internal function used in TH1::Fill to see which axis is full alphanumeric i.e.
Definition TH1.cxx:6624
Double_t * fIntegral
! Integral of bins used by GetRandom
Definition TH1.h:110
Double_t fMinimum
Minimum value for plotting.
Definition TH1.h:100
virtual Double_t Integral(Option_t *option="") const
Return integral of bin contents.
Definition TH1.cxx:7816
virtual void SetBinContent(Int_t bin, Double_t content)
Set bin content see convention for numbering bins in TH1::GetBin In case the bin number is greater th...
Definition TH1.cxx:9052
virtual void DirectoryAutoAdd(TDirectory *)
Perform the automatic addition of the histogram to the given directory.
Definition TH1.cxx:2790
virtual void GetLowEdge(Double_t *edge) const
Fill array with low edge of bins for 1D histogram Better to use h1.GetXaxis()->GetLowEdge(edge)
Definition TH1.cxx:9017
virtual Double_t GetBinLowEdge(Int_t bin) const
Return bin lower edge for 1D histogram.
Definition TH1.cxx:8982
void Build()
Creates histogram basic data structure.
Definition TH1.cxx:768
virtual Double_t GetEntries() const
Return the current number of entries.
Definition TH1.cxx:4387
virtual TF1 * GetFunction(const char *name) const
Return pointer to function with name.
Definition TH1.cxx:8881
virtual Int_t BufferFill(Double_t x, Double_t w)
accumulate arguments in buffer.
Definition TH1.cxx:1493
virtual Double_t GetBinWithContent(Double_t c, Int_t &binx, Int_t firstx=0, Int_t lastx=0, Double_t maxdiff=0) const
Compute first binx in the range [firstx,lastx] for which diff = abs(bin_content-c) <= maxdiff.
Definition TH1.cxx:5019
virtual UInt_t SetCanExtend(UInt_t extendBitMask)
Make the histogram axes extendable / not extendable according to the bit mask returns the previous bi...
Definition TH1.cxx:6598
TList * GetListOfFunctions() const
Definition TH1.h:243
virtual TH1 * DrawCopy(Option_t *option="", const char *name_postfix="_copy") const
Copy this histogram and Draw in the current pad.
Definition TH1.cxx:3121
virtual void Copy(TObject &hnew) const
Copy this histogram structure to newth1.
Definition TH1.cxx:2664
Bool_t IsEmpty() const
Check if a histogram is empty (this is a protected method used mainly by TH1Merger )
Definition TH1.cxx:5097
virtual Double_t GetMeanError(Int_t axis=1) const
Return standard error of mean of this histogram along the X axis.
Definition TH1.cxx:7450
virtual void Draw(Option_t *option="")
Draw this histogram with options.
Definition TH1.cxx:3074
virtual Double_t AndersonDarlingTest(const TH1 *h2, Option_t *option="") const
Statistical test of compatibility in shape between this histogram and h2, using the Anderson-Darling ...
Definition TH1.cxx:7936
virtual void ResetStats()
Reset the statistics including the number of entries and replace with values calculated from bin cont...
Definition TH1.cxx:7777
static void SetDefaultBufferSize(Int_t buffersize=1000)
Static function to set the default buffer size for automatic histograms.
Definition TH1.cxx:6642
virtual void SetBinErrorOption(EBinErrorOpt type)
Definition TH1.h:376
virtual void SetBuffer(Int_t buffersize, Option_t *option="")
Set the maximum number of entries to be kept in the buffer.
Definition TH1.cxx:8288
virtual void DrawPanel()
Display a panel with all histogram drawing options.
Definition TH1.cxx:3182
virtual Double_t GetRandom(TRandom *rng=nullptr) const
Return a random number distributed according the histogram bin contents.
Definition TH1.cxx:4943
virtual Double_t Chisquare(TF1 *f1, Option_t *option="") const
Compute and return the chisquare of this histogram with respect to a function The chisquare is comput...
Definition TH1.cxx:2493
virtual void DoFillN(Int_t ntimes, const Double_t *x, const Double_t *w, Int_t stride=1)
Internal method to fill histogram content from a vector called directly by TH1::BufferEmpty.
Definition TH1.cxx:3480
virtual void GetMinimumAndMaximum(Double_t &min, Double_t &max) const
Retrieve the minimum and maximum values in the histogram.
Definition TH1.cxx:8561
@ kNstat
Size of statistics data (up to TProfile3D)
Definition TH1.h:183
virtual Int_t GetMaximumBin() const
Return location of bin with maximum value in the range.
Definition TH1.cxx:8407
static Int_t AutoP2GetBins(Int_t n)
Auxiliary function to get the next power of 2 integer value larger then n.
Definition TH1.cxx:1310
Double_t fEntries
Number of entries.
Definition TH1.h:94
virtual Long64_t Merge(TCollection *list)
Definition TH1.h:341
virtual void SetName(const char *name)
Change the name of this histogram.
Definition TH1.cxx:8790
virtual Double_t * GetIntegral()
Return a pointer to the array of bins integral.
Definition TH1.cxx:2579
TAxis fZaxis
Z axis descriptor.
Definition TH1.h:91
EStatOverflows fStatOverflows
Per object flag to use under/overflows in statistics.
Definition TH1.h:113
virtual void FillN(Int_t ntimes, const Double_t *x, const Double_t *w, Int_t stride=1)
Fill this histogram with an array x and weights w.
Definition TH1.cxx:3454
virtual void UpdateBinContent(Int_t bin, Double_t content)
Raw update of bin content on internal data structure see convention for numbering bins in TH1::GetBin...
Definition TH1.cxx:9280
static bool CheckEqualAxes(const TAxis *a1, const TAxis *a2)
Check that the axis are the same.
Definition TH1.cxx:1604
@ kPoisson2
Errors from Poisson interval at 95% CL (~ 2 sigma)
Definition TH1.h:66
@ kNormal
Errors with Normal (Wald) approximation: errorUp=errorLow= sqrt(N)
Definition TH1.h:64
virtual Double_t GetBinContent(Int_t bin) const
Return content of bin number bin.
Definition TH1.cxx:4994
TAxis fXaxis
X axis descriptor.
Definition TH1.h:89
virtual void ExecuteEvent(Int_t event, Int_t px, Int_t py)
Execute action corresponding to one event.
Definition TH1.cxx:3247
virtual Bool_t IsHighlight() const
Definition TH1.h:334
virtual void ExtendAxis(Double_t x, TAxis *axis)
Histogram is resized along axis such that x is in the axis range.
Definition TH1.cxx:6453
virtual void SetNameTitle(const char *name, const char *title)
Change the name and title of this histogram.
Definition TH1.cxx:8804
virtual Double_t GetBinWidth(Int_t bin) const
Return bin width for 1D histogram.
Definition TH1.cxx:8993
static bool CheckConsistency(const TH1 *h1, const TH1 *h2)
Check histogram compatibility.
Definition TH1.cxx:1677
TArrayD fSumw2
Array of sum of squares of weights.
Definition TH1.h:103
TH1 * GetAsymmetry(TH1 *h2, Double_t c2=1, Double_t dc2=0)
Return a histogram containing the asymmetry of this histogram with h2, where the asymmetry is defined...
Definition TH1.cxx:4303
virtual Double_t GetContourLevel(Int_t level) const
Return value of contour number level.
Definition TH1.cxx:8260
virtual void SetHighlight(Bool_t set=kTRUE)
Set highlight (enable/disable) mode for the histogram by default highlight mode is disable.
Definition TH1.cxx:4423
virtual Double_t GetBinErrorUp(Int_t bin) const
Return upper error associated to bin number bin.
Definition TH1.cxx:8940
virtual void Scale(Double_t c1=1, Option_t *option="")
Multiply this histogram by a constant c1.
Definition TH1.cxx:6553
virtual void Paint(Option_t *option="")
Control routine to paint any kind of histograms.
Definition TH1.cxx:6157
virtual Int_t GetMinimumBin() const
Return location of bin with minimum value in the range.
Definition TH1.cxx:8495
virtual Int_t GetSumw2N() const
Definition TH1.h:314
virtual Int_t FindBin(Double_t x, Double_t y=0, Double_t z=0)
Return Global bin number corresponding to x,y,z.
Definition TH1.cxx:3681
Bool_t GetStatOverflowsBehaviour() const
Definition TH1.h:152
virtual Double_t GetStdDevError(Int_t axis=1) const
Return error of standard deviation estimation for Normal distribution.
Definition TH1.cxx:7530
virtual Bool_t Divide(TF1 *f1, Double_t c1=1)
Performs the operation: this = this/(c1*f1) if errors are defined (see TH1::Sumw2),...
Definition TH1.cxx:2829
virtual Double_t GetMinimum(Double_t minval=-FLT_MAX) const
Return minimum value larger than minval of bins in the range, unless the value has been overridden by...
Definition TH1.cxx:8465
static bool CheckConsistentSubAxes(const TAxis *a1, Int_t firstBin1, Int_t lastBin1, const TAxis *a2, Int_t firstBin2=0, Int_t lastBin2=0)
Check that two sub axis are the same.
Definition TH1.cxx:1640
TAxis fYaxis
Y axis descriptor.
Definition TH1.h:90
virtual Double_t KolmogorovTest(const TH1 *h2, Option_t *option="") const
Statistical test of compatibility in shape between this histogram and h2, using Kolmogorov test.
Definition TH1.cxx:8050
virtual Double_t GetSumOfWeights() const
Return the sum of weights excluding under/overflows.
Definition TH1.cxx:7792
static void SmoothArray(Int_t NN, Double_t *XX, Int_t ntimes=1)
Smooth array xx, translation of Hbook routine hsmoof.F based on algorithm 353QH twice presented by J.
Definition TH1.cxx:6716
virtual void GetCenter(Double_t *center) const
Fill array with center of bins for 1D histogram Better to use h1.GetXaxis()->GetCenter(center)
Definition TH1.cxx:9004
TVirtualHistPainter * fPainter
! Pointer to histogram painter
Definition TH1.h:111
virtual void SetBins(Int_t nx, Double_t xmin, Double_t xmax)
Redefine x axis parameters.
Definition TH1.cxx:8597
virtual Int_t FindFixBin(Double_t x, Double_t y=0, Double_t z=0) const
Return Global bin number corresponding to x,y,z.
Definition TH1.cxx:3714
virtual char * GetObjectInfo(Int_t px, Int_t py) const
Redefines TObject::GetObjectInfo.
Definition TH1.cxx:4444
virtual void Sumw2(Bool_t flag=kTRUE)
Create structure to store sum of squares of weights.
Definition TH1.cxx:8850
virtual void SetEntries(Double_t n)
Definition TH1.h:385
virtual Bool_t FindNewAxisLimits(const TAxis *axis, const Double_t point, Double_t &newMin, Double_t &newMax)
finds new limits for the axis so that point is within the range and the limits are compatible with th...
Definition TH1.cxx:6409
static bool CheckAxisLimits(const TAxis *a1, const TAxis *a2)
Check that the axis limits of the histograms are the same.
Definition TH1.cxx:1589
static Bool_t AddDirectoryStatus()
Static function: cannot be inlined on Windows/NT.
Definition TH1.cxx:751
static Bool_t fgDefaultSumw2
! Flag to call TH1::Sumw2 automatically at histogram creation time
Definition TH1.h:117
virtual Int_t DistancetoPrimitive(Int_t px, Int_t py)
Compute distance from point px,py to a line.
Definition TH1.cxx:2812
Double_t fTsumwx
Total Sum of weight*X.
Definition TH1.h:97
virtual void LabelsDeflate(Option_t *axis="X")
Reduce the number of bins for the axis passed in the option to the number of bins having a label.
Definition TH1.cxx:5178
virtual Double_t ComputeIntegral(Bool_t onlyPositive=false)
Compute integral (cumulative sum of bins) The result stored in fIntegral is used by the GetRandom fun...
Definition TH1.cxx:2531
TString fOption
Histogram options.
Definition TH1.h:104
virtual Int_t GetContour(Double_t *levels=0)
Return contour values into array levels if pointer levels is non zero.
Definition TH1.cxx:8241
virtual void Eval(TF1 *f1, Option_t *option="")
Evaluate function f1 at the center of bins of this histogram.
Definition TH1.cxx:3199
virtual void SetBarWidth(Float_t width=0.5)
Set the width of bars as fraction of the bin width for drawing mode "B".
Definition TH1.h:360
virtual Int_t BufferEmpty(Int_t action=0)
Fill histogram with all entries in the buffer.
Definition TH1.cxx:1403
virtual void SetStats(Bool_t stats=kTRUE)
Set statistics option on/off.
Definition TH1.cxx:8820
virtual TH1 * Rebin(Int_t ngroup=2, const char *newname="", const Double_t *xbins=0)
Rebin this histogram.
Definition TH1.cxx:6224
virtual Double_t GetKurtosis(Int_t axis=1) const
Definition TH1.cxx:7619
2-D histogram with a double per channel (see TH1 documentation)}
Definition TH2.h:292
static THLimitsFinder * GetLimitsFinder()
Return pointer to the current finder.
virtual Int_t FindGoodLimits(TH1 *h, Double_t xmin, Double_t xmax)
Compute the best axis limits for the X axis.
THashList implements a hybrid collection class consisting of a hash table and a list to store TObject...
Definition THashList.h:34
void Clear(Option_t *option="")
Remove all objects from the list.
A doubly linked list.
Definition TList.h:38
virtual void Add(TObject *obj)
Definition TList.h:81
virtual TObject * Remove(TObject *obj)
Remove object from the list.
Definition TList.cxx:822
virtual TObject * FindObject(const char *name) const
Find an object in this list using its name.
Definition TList.cxx:578
virtual TObjLink * FirstLink() const
Definition TList.h:102
virtual TObject * At(Int_t idx) const
Returns the object at position idx. Returns 0 if idx is out of range.
Definition TList.cxx:357
virtual void RecursiveRemove(TObject *obj)
Remove object from this collection and recursively remove the object from all other objects (and coll...
Definition TList.cxx:764
virtual void Delete(Option_t *option="")
Remove all objects from the list AND delete all heap based objects.
Definition TList.cxx:470
virtual TObject * First() const
Return the first object in the list. Returns 0 when list is empty.
Definition TList.cxx:659
The TNamed class is the base class for all named ROOT classes.
Definition TNamed.h:29
virtual void Copy(TObject &named) const
Copy this to obj.
Definition TNamed.cxx:94
virtual void SetTitle(const char *title="")
Set the title of the TNamed.
Definition TNamed.cxx:164
TString fTitle
Definition TNamed.h:33
TString fName
Definition TNamed.h:32
virtual void SetName(const char *name)
Set the name of the TNamed.
Definition TNamed.cxx:140
virtual const char * GetTitle() const
Returns title of object.
Definition TNamed.h:48
virtual const char * GetName() const
Returns name of object.
Definition TNamed.h:47
Mother of all ROOT objects.
Definition TObject.h:41
void AbstractMethod(const char *method) const
Use this method to implement an "abstract" method that you don't want to leave purely abstract.
Definition TObject.cxx:1005
virtual const char * GetName() const
Returns name of object.
Definition TObject.cxx:429
R__ALWAYS_INLINE Bool_t TestBit(UInt_t f) const
Definition TObject.h:201
virtual UInt_t GetUniqueID() const
Return the unique object id.
Definition TObject.cxx:447
virtual const char * ClassName() const
Returns name of class to which the object belongs.
Definition TObject.cxx:200
virtual void UseCurrentStyle()
Set current style settings in this object This function is called when either TCanvas::UseCurrentStyl...
Definition TObject.cxx:787
virtual void Warning(const char *method, const char *msgfmt,...) const
Issue warning message.
Definition TObject.cxx:949
virtual void AppendPad(Option_t *option="")
Append graphics object to current pad.
Definition TObject.cxx:177
virtual void SavePrimitive(std::ostream &out, Option_t *option="")
Save a primitive as a C++ statement(s) on output stream "out".
Definition TObject.cxx:736
void SetBit(UInt_t f, Bool_t set)
Set or unset the user status bits as specified in f.
Definition TObject.cxx:766
virtual Bool_t InheritsFrom(const char *classname) const
Returns kTRUE if object inherits from class "classname".
Definition TObject.cxx:515
virtual void Error(const char *method, const char *msgfmt,...) const
Issue error message.
Definition TObject.cxx:963
virtual void SetUniqueID(UInt_t uid)
Set the unique object id.
Definition TObject.cxx:777
void ResetBit(UInt_t f)
Definition TObject.h:200
@ kCanDelete
if object in a list can be deleted
Definition TObject.h:62
@ kInvalidObject
if object ctor succeeded but object should not be used
Definition TObject.h:72
@ kMustCleanup
if object destructor must call RecursiveRemove()
Definition TObject.h:64
virtual void Info(const char *method, const char *msgfmt,...) const
Issue info message.
Definition TObject.cxx:937
Longptr_t ExecPlugin(int nargs, const T &... params)
Int_t LoadPlugin()
Load the plugin library for this handler.
This is the base class for the ROOT Random number generators.
Definition TRandom.h:27
virtual Int_t Poisson(Double_t mean)
Generates a random integer N according to a Poisson law.
Definition TRandom.cxx:402
virtual Double_t PoissonD(Double_t mean)
Generates a random number according to a Poisson law.
Definition TRandom.cxx:454
virtual Double_t Rndm()
Machine independent random number generator.
Definition TRandom.cxx:552
Basic string class.
Definition TString.h:136
Ssiz_t Length() const
Definition TString.h:410
void ToLower()
Change string to lower-case.
Definition TString.cxx:1150
void Clear()
Clear string without changing its capacity.
Definition TString.cxx:1201
const char * Data() const
Definition TString.h:369
TString & ReplaceAll(const TString &s1, const TString &s2)
Definition TString.h:692
void ToUpper()
Change string to upper case.
Definition TString.cxx:1163
Bool_t IsNull() const
Definition TString.h:407
TString & Remove(Ssiz_t pos)
Definition TString.h:673
TString & Append(const char *cs)
Definition TString.h:564
static TString Format(const char *fmt,...)
Static method which formats a string using a printf style format descriptor and return a TString.
Definition TString.cxx:2336
void Form(const char *fmt,...)
Formats a string using a printf style format descriptor.
Definition TString.cxx:2314
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
Definition TString.h:624
Ssiz_t Index(const char *pat, Ssiz_t i=0, ECaseCompare cmp=kExact) const
Definition TString.h:639
Int_t GetOptStat() const
Definition TStyle.h:236
void SetOptStat(Int_t stat=1)
The type of information printed in the histogram statistics box can be selected via the parameter mod...
Definition TStyle.cxx:1589
void SetHistFillColor(Color_t color=1)
Definition TStyle.h:362
Color_t GetHistLineColor() const
Definition TStyle.h:224
Bool_t IsReading() const
Definition TStyle.h:282
Float_t GetBarOffset() const
Definition TStyle.h:174
void SetHistLineStyle(Style_t styl=0)
Definition TStyle.h:365
Style_t GetHistFillStyle() const
Definition TStyle.h:225
Color_t GetHistFillColor() const
Definition TStyle.h:223
Float_t GetBarWidth() const
Definition TStyle.h:175
Bool_t GetCanvasPreferGL() const
Definition TStyle.h:179
void SetHistLineColor(Color_t color=1)
Definition TStyle.h:363
void SetBarOffset(Float_t baroff=0.5)
Definition TStyle.h:319
Style_t GetHistLineStyle() const
Definition TStyle.h:226
void SetBarWidth(Float_t barwidth=0.5)
Definition TStyle.h:320
void SetHistFillStyle(Style_t styl=0)
Definition TStyle.h:364
Width_t GetHistLineWidth() const
Definition TStyle.h:227
Int_t GetOptFit() const
Definition TStyle.h:235
void SetHistLineWidth(Width_t width=1)
Definition TStyle.h:366
TVectorT.
Definition TVectorT.h:27
TVirtualFFT is an interface class for Fast Fourier Transforms.
Definition TVirtualFFT.h:88
static TVirtualFFT * FFT(Int_t ndim, Int_t *n, Option_t *option)
Returns a pointer to the FFT of requested size and type.
virtual Int_t GetNdim() const =0
static TVirtualFFT * SineCosine(Int_t ndim, Int_t *n, Int_t *r2rkind, Option_t *option)
Returns a pointer to a sine or cosine transform of requested size and kind.
virtual Option_t * GetType() const =0
virtual void Transform()=0
virtual void GetPointComplex(Int_t ipoint, Double_t &re, Double_t &im, Bool_t fromInput=kFALSE) const =0
virtual Int_t * GetN() const =0
virtual Double_t GetPointReal(Int_t ipoint, Bool_t fromInput=kFALSE) const =0
virtual void SetPoint(Int_t ipoint, Double_t re, Double_t im=0)=0
Abstract Base Class for Fitting.
virtual Int_t GetXlast() const
virtual TObject * GetObjectFit() const
virtual Int_t GetXfirst() const
static TVirtualFitter * GetFitter()
static: return the current Fitter
virtual TObject * GetUserFunc() const
Abstract interface to a histogram painter.
virtual void DrawPanel()=0
virtual void ExecuteEvent(Int_t event, Int_t px, Int_t py)=0
Execute action corresponding to an event at (px,py).
virtual void Paint(Option_t *option="")=0
This method must be overridden if a class wants to paint itself.
virtual Int_t DistancetoPrimitive(Int_t px, Int_t py)=0
Computes distance from point (px,py) to the object.
virtual void SetHighlight()=0
static TVirtualHistPainter * HistPainter(TH1 *obj)
Static function returning a pointer to the current histogram painter.
virtual void SetParent(TObject *)=0
double gamma_quantile_c(double z, double alpha, double theta)
Inverse ( ) of the cumulative distribution function of the upper tail of the gamma distribution (gamm...
double gamma_quantile(double z, double alpha, double theta)
Inverse ( ) of the cumulative distribution function of the lower tail of the gamma distribution (gamm...
const Double_t sigma
return c1
Definition legend1.C:41
Double_t y[n]
Definition legend1.C:17
Double_t x[n]
Definition legend1.C:17
const Int_t n
Definition legend1.C:16
TH1F * h1
Definition legend1.C:5
TF1 * f1
Definition legend1.C:11
return c2
Definition legend2.C:14
R__ALWAYS_INLINE bool HasBeenDeleted(const TObject *obj)
Check if the TObject's memory has been deleted.
Definition TObject.h:404
TFitResultPtr FitObject(TH1 *h1, TF1 *f1, Foption_t &option, const ROOT::Math::MinimizerOptions &moption, const char *goption, ROOT::Fit::DataRange &range)
fitting function for a TH1 (called from TH1::Fit)
Definition HFitImpl.cxx:965
void FitOptionsMake(EFitObjectType type, const char *option, Foption_t &fitOption)
Decode list of options into fitOption.
Definition HFitImpl.cxx:684
void FillData(BinData &dv, const TH1 *hist, TF1 *func=0)
fill the data vector from a TH1.
double Chisquare(const TH1 &h1, TF1 &f1, bool useRange, bool usePL=false)
compute the chi2 value for an histogram given a function (see TH1::Chisquare for the documentation)
R__EXTERN TVirtualRWMutex * gCoreMutex
Bool_t IsNaN(Double_t x)
Definition TMath.h:842
Int_t Nint(T x)
Round to nearest integer. Rounds half integers to the nearest even integer.
Definition TMath.h:663
Short_t Max(Short_t a, Short_t b)
Definition TMathBase.h:208
Double_t Prob(Double_t chi2, Int_t ndf)
Computation of the probability for a certain Chi-squared (chi2) and number of degrees of freedom (ndf...
Definition TMath.cxx:614
Double_t QuietNaN()
Returns a quiet NaN as defined by IEEE 754
Definition TMath.h:851
Double_t Floor(Double_t x)
Definition TMath.h:653
Double_t ATan(Double_t)
Definition TMath.h:625
Double_t Ceil(Double_t x)
Definition TMath.h:645
T MinElement(Long64_t n, const T *a)
Return minimum of array a of length n.
Definition TMath.h:902
Double_t Log(Double_t x)
Definition TMath.h:710
Double_t Sqrt(Double_t x)
Definition TMath.h:641
LongDouble_t Power(LongDouble_t x, LongDouble_t y)
Definition TMath.h:685
Short_t Min(Short_t a, Short_t b)
Definition TMathBase.h:176
constexpr Double_t Pi()
Definition TMath.h:37
Bool_t AreEqualRel(Double_t af, Double_t bf, Double_t relPrec)
Definition TMath.h:430
Bool_t AreEqualAbs(Double_t af, Double_t bf, Double_t epsilon)
Definition TMath.h:424
Double_t KolmogorovProb(Double_t z)
Calculates the Kolmogorov distribution function,.
Definition TMath.cxx:656
void Sort(Index n, const Element *a, Index *index, Bool_t down=kTRUE)
Definition TMathBase.h:358
Double_t Median(Long64_t n, const T *a, const Double_t *w=0, Long64_t *work=0)
Return the median of the array a where each entry i has weight w[i] .
Definition TMath.h:1197
Long64_t BinarySearch(Long64_t n, const T *array, T value)
Definition TMathBase.h:274
Double_t Log10(Double_t x)
Definition TMath.h:714
Short_t Abs(Short_t d)
Definition TMathBase.h:120
Double_t Infinity()
Returns an infinity as defined by the IEEE standard.
Definition TMath.h:864
Definition first.py:1
th1 Draw()
auto * m
Definition textangle.C:8
auto * l
Definition textangle.C:4
static uint64_t sum(uint64_t i)
Definition Factory.cxx:2345
REAL epsilon
Definition triangle.c:618