Logo ROOT  
Reference Guide
 
Loading...
Searching...
No Matches
TH3.cxx
Go to the documentation of this file.
1// @(#)root/hist:$Id$
2// Author: Rene Brun 27/10/95
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 "TROOT.h"
13#include "TBuffer.h"
14#include "TClass.h"
15#include "THashList.h"
16#include "TH3.h"
17#include "TProfile2D.h"
18#include "TH2.h"
19#include "TF3.h"
20#include "TVirtualPad.h"
21#include "TVirtualHistPainter.h"
22#include "THLimitsFinder.h"
23#include "TRandom.h"
24#include "TError.h"
25#include "TMath.h"
26#include "TObjString.h"
27
29
30/** \addtogroup Hist
31@{
32\class TH3C
33\brief 3-D histogram with a byte per channel (see TH1 documentation)
34\class TH3S
35\brief 3-D histogram with a short per channel (see TH1 documentation)
36\class TH3I
37\brief 3-D histogram with an int per channel (see TH1 documentation)}
38\class TH3F
39\brief 3-D histogram with a float per channel (see TH1 documentation)}
40\class TH3D
41\brief 3-D histogram with a double per channel (see TH1 documentation)}
42@}
43*/
44
45/** \class TH3
46 \ingroup Hist
47The 3-D histogram classes derived from the 1-D histogram classes.
48All operations are supported (fill, fit).
49Drawing is currently restricted to one single option.
50A cloud of points is drawn. The number of points is proportional to
51cell content.
52
53- TH3C a 3-D histogram with one byte per cell (char)
54- TH3S a 3-D histogram with two bytes per cell (short integer)
55- TH3I a 3-D histogram with four bytes per cell (32 bits integer)
56- TH3F a 3-D histogram with four bytes per cell (float)
57- TH3D a 3-D histogram with eight bytes per cell (double)
58*/
59
60
61////////////////////////////////////////////////////////////////////////////////
62/// Default constructor.
63
65{
66 fDimension = 3;
69}
70
71
72////////////////////////////////////////////////////////////////////////////////
73/// Normal constructor for fix bin size 3-D histograms.
74
75TH3::TH3(const char *name,const char *title,Int_t nbinsx,Double_t xlow,Double_t xup
76 ,Int_t nbinsy,Double_t ylow,Double_t yup
77 ,Int_t nbinsz,Double_t zlow,Double_t zup)
78 :TH1(name,title,nbinsx,xlow,xup),
79 TAtt3D()
81 fDimension = 3;
82 if (nbinsy <= 0) {
83 Warning("TH3","nbinsy is <=0 - set to nbinsy = 1");
84 nbinsy = 1;
85 }
86 if (nbinsz <= 0) {
87 Warning("TH3","nbinsz is <=0 - set to nbinsz = 1");
88 nbinsz = 1;
89 }
90 fYaxis.Set(nbinsy,ylow,yup);
91 fZaxis.Set(nbinsz,zlow,zup);
92 fNcells = (nbinsx+2)*(nbinsy+2)*(nbinsz+2);
93 fTsumwy = fTsumwy2 = fTsumwxy = 0;
94 fTsumwz = fTsumwz2 = fTsumwxz = fTsumwyz = 0;
95}
96
97
98////////////////////////////////////////////////////////////////////////////////
99/// Normal constructor for variable bin size 3-D histograms.
100
101TH3::TH3(const char *name,const char *title,Int_t nbinsx,const Float_t *xbins
102 ,Int_t nbinsy,const Float_t *ybins
103 ,Int_t nbinsz,const Float_t *zbins)
104 :TH1(name,title,nbinsx,xbins),
105 TAtt3D()
106{
107 fDimension = 3;
108 if (nbinsy <= 0) {Warning("TH3","nbinsy is <=0 - set to nbinsy = 1"); nbinsy = 1; }
109 if (nbinsz <= 0) nbinsz = 1;
110 if (ybins) fYaxis.Set(nbinsy,ybins);
111 else fYaxis.Set(nbinsy,0,1);
112 if (zbins) fZaxis.Set(nbinsz,zbins);
113 else fZaxis.Set(nbinsz,0,1);
114 fNcells = (nbinsx+2)*(nbinsy+2)*(nbinsz+2);
115 fTsumwy = fTsumwy2 = fTsumwxy = 0;
117}
118
119
120////////////////////////////////////////////////////////////////////////////////
121/// Normal constructor for variable bin size 3-D histograms.
122
123TH3::TH3(const char *name,const char *title,Int_t nbinsx,const Double_t *xbins
124 ,Int_t nbinsy,const Double_t *ybins
125 ,Int_t nbinsz,const Double_t *zbins)
126 :TH1(name,title,nbinsx,xbins),
127 TAtt3D()
128{
129 fDimension = 3;
130 if (nbinsy <= 0) {Warning("TH3","nbinsy is <=0 - set to nbinsy = 1"); nbinsy = 1; }
131 if (nbinsz <= 0) nbinsz = 1;
132 if (ybins) fYaxis.Set(nbinsy,ybins);
133 else fYaxis.Set(nbinsy,0,1);
134 if (zbins) fZaxis.Set(nbinsz,zbins);
135 else fZaxis.Set(nbinsz,0,1);
136 fNcells = (nbinsx+2)*(nbinsy+2)*(nbinsz+2);
137 fTsumwy = fTsumwy2 = fTsumwxy = 0;
139}
140
141
142////////////////////////////////////////////////////////////////////////////////
143/// Copy constructor.
144/// The list of functions is not copied. (Use Clone if needed)
145
146TH3::TH3(const TH3 &h) : TH1(), TAtt3D()
147{
148 ((TH3&)h).Copy(*this);
149}
150
151
152////////////////////////////////////////////////////////////////////////////////
153/// Destructor.
154
156{
157}
158
159
160////////////////////////////////////////////////////////////////////////////////
161/// Copy.
162
163void TH3::Copy(TObject &obj) const
164{
165 TH1::Copy(obj);
166 ((TH3&)obj).fTsumwy = fTsumwy;
167 ((TH3&)obj).fTsumwy2 = fTsumwy2;
168 ((TH3&)obj).fTsumwxy = fTsumwxy;
169 ((TH3&)obj).fTsumwz = fTsumwz;
170 ((TH3&)obj).fTsumwz2 = fTsumwz2;
171 ((TH3&)obj).fTsumwxz = fTsumwxz;
172 ((TH3&)obj).fTsumwyz = fTsumwyz;
173}
174
175
176////////////////////////////////////////////////////////////////////////////////
177/// Fill histogram with all entries in the buffer.
178/// action = -1 histogram is reset and refilled from the buffer (called by THistPainter::Paint)
179/// action = 0 histogram is filled from the buffer
180/// action = 1 histogram is filled and buffer is deleted
181/// The buffer is automatically deleted when the number of entries
182/// in the buffer is greater than the number of entries in the histogram
183
185{
186 // do we need to compute the bin size?
187 if (!fBuffer) return 0;
188 Int_t nbentries = (Int_t)fBuffer[0];
189 if (!nbentries) return 0;
190 Double_t *buffer = fBuffer;
191 if (nbentries < 0) {
192 if (action == 0) return 0;
193 nbentries = -nbentries;
194 fBuffer=0;
195 Reset("ICES");
196 fBuffer = buffer;
197 }
198 if (CanExtendAllAxes() || fXaxis.GetXmax() <= fXaxis.GetXmin() ||
199 fYaxis.GetXmax() <= fYaxis.GetXmin() ||
200 fZaxis.GetXmax() <= fZaxis.GetXmin()) {
201 //find min, max of entries in buffer
202 Double_t xmin = fBuffer[2];
204 Double_t ymin = fBuffer[3];
206 Double_t zmin = fBuffer[4];
207 Double_t zmax = zmin;
208 for (Int_t i=1;i<nbentries;i++) {
209 Double_t x = fBuffer[4*i+2];
210 if (x < xmin) xmin = x;
211 if (x > xmax) xmax = x;
212 Double_t y = fBuffer[4*i+3];
213 if (y < ymin) ymin = y;
214 if (y > ymax) ymax = y;
215 Double_t z = fBuffer[4*i+4];
216 if (z < zmin) zmin = z;
217 if (z > zmax) zmax = z;
218 }
221 } else {
222 fBuffer = 0;
223 Int_t keep = fBufferSize; fBufferSize = 0;
228 if (zmin < fZaxis.GetXmin()) ExtendAxis(zmin,&fZaxis);
229 if (zmax >= fZaxis.GetXmax()) ExtendAxis(zmax,&fZaxis);
230 fBuffer = buffer;
231 fBufferSize = keep;
232 }
233 }
234 fBuffer = 0;
235
236 for (Int_t i=0;i<nbentries;i++) {
237 Fill(buffer[4*i+2],buffer[4*i+3],buffer[4*i+4],buffer[4*i+1]);
238 }
239 fBuffer = buffer;
240
241 if (action > 0) { delete [] fBuffer; fBuffer = 0; fBufferSize = 0;}
242 else {
243 if (nbentries == (Int_t)fEntries) fBuffer[0] = -nbentries;
244 else fBuffer[0] = 0;
245 }
246 return nbentries;
247}
248
249
250////////////////////////////////////////////////////////////////////////////////
251/// accumulate arguments in buffer. When buffer is full, empty the buffer
252/// fBuffer[0] = number of entries in buffer
253/// fBuffer[1] = w of first entry
254/// fBuffer[2] = x of first entry
255/// fBuffer[3] = y of first entry
256/// fBuffer[4] = z of first entry
257
259{
260 if (!fBuffer) return -3;
261 Int_t nbentries = (Int_t)fBuffer[0];
262 if (nbentries < 0) {
263 nbentries = -nbentries;
264 fBuffer[0] = nbentries;
265 if (fEntries > 0) {
266 Double_t *buffer = fBuffer; fBuffer=0;
267 Reset("ICES");
268 fBuffer = buffer;
269 }
270 }
271 if (4*nbentries+4 >= fBufferSize) {
272 BufferEmpty(1);
273 return Fill(x,y,z,w);
274 }
275 fBuffer[4*nbentries+1] = w;
276 fBuffer[4*nbentries+2] = x;
277 fBuffer[4*nbentries+3] = y;
278 fBuffer[4*nbentries+4] = z;
279 fBuffer[0] += 1;
280 return -3;
281}
282
283
284////////////////////////////////////////////////////////////////////////////////
285/// Invalid Fill method
286
288{
289 Error("Fill", "Invalid signature - do nothing");
290 return -1;
291}
292
293
294////////////////////////////////////////////////////////////////////////////////
295/// Increment cell defined by x,y,z by 1 .
296///
297/// The function returns the corresponding global bin number which has its content
298/// incremented by 1
299
301{
302 if (fBuffer) return BufferFill(x,y,z,1);
303
304 Int_t binx, biny, binz, bin;
305 fEntries++;
306 binx = fXaxis.FindBin(x);
307 biny = fYaxis.FindBin(y);
308 binz = fZaxis.FindBin(z);
309 if (binx <0 || biny <0 || binz<0) return -1;
310 bin = binx + (fXaxis.GetNbins()+2)*(biny + (fYaxis.GetNbins()+2)*binz);
311 if (fSumw2.fN) ++fSumw2.fArray[bin];
312 AddBinContent(bin);
313 if (binx == 0 || binx > fXaxis.GetNbins()) {
314 if (!GetStatOverflowsBehaviour()) return -1;
315 }
316
317 if (biny == 0 || biny > fYaxis.GetNbins()) {
318 if (!GetStatOverflowsBehaviour()) return -1;
319 }
320 if (binz == 0 || binz > fZaxis.GetNbins()) {
321 if (!GetStatOverflowsBehaviour()) return -1;
322 }
323 ++fTsumw;
324 ++fTsumw2;
325 fTsumwx += x;
326 fTsumwx2 += x*x;
327 fTsumwy += y;
328 fTsumwy2 += y*y;
329 fTsumwxy += x*y;
330 fTsumwz += z;
331 fTsumwz2 += z*z;
332 fTsumwxz += x*z;
333 fTsumwyz += y*z;
334 return bin;
335}
336
337
338////////////////////////////////////////////////////////////////////////////////
339/// Increment cell defined by x,y,z by a weight w.
340///
341/// If the weight is not equal to 1, the storage of the sum of squares of
342/// weights is automatically triggered and the sum of the squares of weights is incremented
343/// by w^2 in the cell corresponding to x,y,z.
344///
345/// The function returns the corresponding global bin number which has its content
346/// incremented by w
347
349{
350 if (fBuffer) return BufferFill(x,y,z,w);
351
352 Int_t binx, biny, binz, bin;
353 fEntries++;
354 binx = fXaxis.FindBin(x);
355 biny = fYaxis.FindBin(y);
356 binz = fZaxis.FindBin(z);
357 if (binx <0 || biny <0 || binz<0) return -1;
358 bin = binx + (fXaxis.GetNbins()+2)*(biny + (fYaxis.GetNbins()+2)*binz);
359 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW)) Sumw2(); // must be called before AddBinContent
360 if (fSumw2.fN) fSumw2.fArray[bin] += w*w;
361 AddBinContent(bin,w);
362 if (binx == 0 || binx > fXaxis.GetNbins()) {
363 if (!GetStatOverflowsBehaviour()) return -1;
364 }
365 if (biny == 0 || biny > fYaxis.GetNbins()) {
366 if (!GetStatOverflowsBehaviour()) return -1;
367 }
368 if (binz == 0 || binz > fZaxis.GetNbins()) {
369 if (!GetStatOverflowsBehaviour()) return -1;
370 }
371 fTsumw += w;
372 fTsumw2 += w*w;
373 fTsumwx += w*x;
374 fTsumwx2 += w*x*x;
375 fTsumwy += w*y;
376 fTsumwy2 += w*y*y;
377 fTsumwxy += w*x*y;
378 fTsumwz += w*z;
379 fTsumwz2 += w*z*z;
380 fTsumwxz += w*x*z;
381 fTsumwyz += w*y*z;
382 return bin;
383}
384
385
386////////////////////////////////////////////////////////////////////////////////
387/// Increment cell defined by namex,namey,namez by a weight w
388///
389/// If the weight is not equal to 1, the storage of the sum of squares of
390/// weights is automatically triggered and the sum of the squares of weights is incremented
391/// by w^2 in the corresponding cell.
392/// The function returns the corresponding global bin number which has its content
393/// incremented by w
394
395Int_t TH3::Fill(const char *namex, const char *namey, const char *namez, Double_t w)
396{
397 Int_t binx, biny, binz, bin;
398 fEntries++;
399 binx = fXaxis.FindBin(namex);
400 biny = fYaxis.FindBin(namey);
401 binz = fZaxis.FindBin(namez);
402 if (binx <0 || biny <0 || binz<0) return -1;
403 bin = binx + (fXaxis.GetNbins()+2)*(biny + (fYaxis.GetNbins()+2)*binz);
404 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW)) Sumw2(); // must be called before AddBinContent
405 if (fSumw2.fN) fSumw2.fArray[bin] += w*w;
406 AddBinContent(bin,w);
407 if (binx == 0 || binx > fXaxis.GetNbins()) return -1;
408 if (biny == 0 || biny > fYaxis.GetNbins()) return -1;
409 if (binz == 0 || binz > fZaxis.GetNbins()) return -1;
410
411 Double_t v = w;
412 fTsumw += v;
413 fTsumw2 += v*v;
414 // skip computation of the statistics along axis that have labels (can be extended and are aphanumeric)
415 UInt_t labelBitMask = GetAxisLabelStatus();
416 if (labelBitMask != TH1::kAllAxes) {
417 Double_t x = (labelBitMask & TH1::kXaxis) ? 0 : fXaxis.GetBinCenter(binx);
418 Double_t y = (labelBitMask & TH1::kYaxis) ? 0 : fYaxis.GetBinCenter(biny);
419 Double_t z = (labelBitMask & TH1::kZaxis) ? 0 : fZaxis.GetBinCenter(binz);
420 fTsumwx += v * x;
421 fTsumwx2 += v * x * x;
422 fTsumwy += v * y;
423 fTsumwy2 += v * y * y;
424 fTsumwxy += v * x * y;
425 fTsumwz += v * z;
426 fTsumwz2 += v * z * z;
427 fTsumwxz += v * x * z;
428 fTsumwyz += v * y * z;
429 }
430 return bin;
431}
432
433
434////////////////////////////////////////////////////////////////////////////////
435/// Increment cell defined by namex,y,namez by a weight w
436///
437/// If the weight is not equal to 1, the storage of the sum of squares of
438/// weights is automatically triggered and the sum of the squares of weights is incremented
439/// by w^2 in the corresponding cell.
440/// The function returns the corresponding global bin number which has its content
441/// incremented by w
442
443Int_t TH3::Fill(const char *namex, Double_t y, const char *namez, Double_t w)
444{
445 Int_t binx, biny, binz, bin;
446 fEntries++;
447 binx = fXaxis.FindBin(namex);
448 biny = fYaxis.FindBin(y);
449 binz = fZaxis.FindBin(namez);
450 if (binx <0 || biny <0 || binz<0) return -1;
451 bin = binx + (fXaxis.GetNbins()+2)*(biny + (fYaxis.GetNbins()+2)*binz);
452 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW)) Sumw2(); // must be called before AddBinContent
453 if (fSumw2.fN) fSumw2.fArray[bin] += w*w;
454 AddBinContent(bin,w);
455 if (binx == 0 || binx > fXaxis.GetNbins()) return -1;
456 if (biny == 0 || biny > fYaxis.GetNbins()) {
457 if (!GetStatOverflowsBehaviour()) return -1;
458 }
459 if (binz == 0 || binz > fZaxis.GetNbins()) return -1;
460 Double_t v = w;
461 fTsumw += v;
462 fTsumw2 += v*v;
463 fTsumwy += v*y;
464 fTsumwy2 += v*y*y;
465 // skip computation of the statistics along axis that have labels (can be extended and are aphanumeric)
466 UInt_t labelBitMask = GetAxisLabelStatus();
467 if (labelBitMask != (TH1::kXaxis | TH1::kZaxis) ) {
468 Double_t x = (labelBitMask & TH1::kXaxis) ? 0 : fXaxis.GetBinCenter(binx);
469 Double_t z = (labelBitMask & TH1::kZaxis) ? 0 : fZaxis.GetBinCenter(binz);
470 fTsumwx += v * x;
471 fTsumwx2 += v * x * x;
472 fTsumwxy += v * x * y;
473 fTsumwz += v * z;
474 fTsumwz2 += v * z * z;
475 fTsumwxz += v * x * z;
476 fTsumwyz += v * y * z;
477 }
478 return bin;
479}
480
481
482////////////////////////////////////////////////////////////////////////////////
483/// Increment cell defined by namex,namey,z by a weight w
484///
485/// If the weight is not equal to 1, the storage of the sum of squares of
486/// weights is automatically triggered and the sum of the squares of weights is incremented
487/// by w^2 in the corresponding cell.
488/// The function returns the corresponding global bin number which has its content
489/// incremented by w
490
491Int_t TH3::Fill(const char *namex, const char *namey, Double_t z, Double_t w)
492{
493 Int_t binx, biny, binz, bin;
494 fEntries++;
495 binx = fXaxis.FindBin(namex);
496 biny = fYaxis.FindBin(namey);
497 binz = fZaxis.FindBin(z);
498 if (binx <0 || biny <0 || binz<0) return -1;
499 bin = binx + (fXaxis.GetNbins()+2)*(biny + (fYaxis.GetNbins()+2)*binz);
500 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW)) Sumw2(); // must be called before AddBinContent
501 if (fSumw2.fN) fSumw2.fArray[bin] += w*w;
502 AddBinContent(bin,w);
503 if (binx == 0 || binx > fXaxis.GetNbins()) return -1;
504 if (biny == 0 || biny > fYaxis.GetNbins()) return -1;
505 if (binz == 0 || binz > fZaxis.GetNbins()) {
506 if (!GetStatOverflowsBehaviour()) return -1;
507 }
508 Double_t v = w;
509 fTsumw += v;
510 fTsumw2 += v*v;
511 fTsumwz += v*z;
512 fTsumwz2 += v*z*z;
513 // skip computation of the statistics along axis that have labels (can be extended and are aphanumeric)
514 UInt_t labelBitMask = GetAxisLabelStatus();
515 if (labelBitMask != (TH1::kXaxis | TH1::kYaxis)) {
516 Double_t x = (labelBitMask & TH1::kXaxis) ? 0 : fXaxis.GetBinCenter(binx);
517 Double_t y = (labelBitMask & TH1::kYaxis) ? 0 : fYaxis.GetBinCenter(biny);
518 fTsumwx += v * x;
519 fTsumwx2 += v * x * x;
520 fTsumwy += v * y;
521 fTsumwy2 += v * y * y;
522 fTsumwxy += v * x * y;
523 fTsumwxz += v * x * z;
524 fTsumwyz += v * y * z;
525 }
526 return bin;
527}
528
529
530////////////////////////////////////////////////////////////////////////////////
531/// Increment cell defined by x,namey,namez by a weight w
532///
533/// If the weight is not equal to 1, the storage of the sum of squares of
534/// weights is automatically triggered and the sum of the squares of weights is incremented
535/// by w^2 in the corresponding cell.
536/// The function returns the corresponding global bin number which has its content
537/// incremented by w
538
539Int_t TH3::Fill(Double_t x, const char *namey, const char *namez, Double_t w)
540{
541 Int_t binx, biny, binz, bin;
542 fEntries++;
543 binx = fXaxis.FindBin(x);
544 biny = fYaxis.FindBin(namey);
545 binz = fZaxis.FindBin(namez);
546 if (binx <0 || biny <0 || binz<0) return -1;
547 bin = binx + (fXaxis.GetNbins()+2)*(biny + (fYaxis.GetNbins()+2)*binz);
548 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW)) Sumw2(); // must be called before AddBinContent
549 if (fSumw2.fN) fSumw2.fArray[bin] += w*w;
550 AddBinContent(bin,w);
551 if (binx == 0 || binx > fXaxis.GetNbins()) {
552 if (!GetStatOverflowsBehaviour()) return -1;
553 }
554 if (biny == 0 || biny > fYaxis.GetNbins()) return -1;
555 if (binz == 0 || binz > fZaxis.GetNbins()) return -1;
556
557 // skip computation of the statistics along axis that have labels (can be extended and are aphanumeric)
558 UInt_t labelBitMask = GetAxisLabelStatus();
559 Double_t y = (labelBitMask & TH1::kYaxis) ? 0 : fYaxis.GetBinCenter(biny);
560 Double_t z = (labelBitMask & TH1::kZaxis) ? 0 : fZaxis.GetBinCenter(binz);
561 Double_t v = w;
562 fTsumw += v;
563 fTsumw2 += v * v;
564 fTsumwx += v * x;
565 fTsumwx2 += v * x * x;
566 fTsumwy += v * y;
567 fTsumwy2 += v * y * y;
568 fTsumwxy += v * x * y;
569 fTsumwz += v * z;
570 fTsumwz2 += v * z * z;
571 fTsumwxz += v * x * z;
572 fTsumwyz += v * y * z;
573 return bin;
574}
575
576////////////////////////////////////////////////////////////////////////////////
577/// Increment cell defined by namex , y ,z by a weight w
578///
579/// If the weight is not equal to 1, the storage of the sum of squares of
580/// weights is automatically triggered and the sum of the squares of weights is incremented
581/// by w^2 in the corresponding cell.
582/// The function returns the corresponding global bin number which has its content
583/// incremented by w
584
585Int_t TH3::Fill(const char * namex, Double_t y, Double_t z, Double_t w)
586{
587 Int_t binx, biny, binz, bin;
588 fEntries++;
589 binx = fXaxis.FindBin(namex);
590 biny = fYaxis.FindBin(y);
591 binz = fZaxis.FindBin(z);
592 if (binx < 0 || biny < 0 || binz < 0)
593 return -1;
594 bin = binx + (fXaxis.GetNbins() + 2) * (biny + (fYaxis.GetNbins() + 2) * binz);
595 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW))
596 Sumw2(); // must be called before AddBinContent
597 if (fSumw2.fN)
598 fSumw2.fArray[bin] += w * w;
599 AddBinContent(bin, w);
600 if (binx == 0 || binx > fXaxis.GetNbins()) {
601 return -1;
602 }
603 if (biny == 0 || biny > fYaxis.GetNbins()) {
605 return -1;
606 }
607 if (binz == 0 || binz > fZaxis.GetNbins()) {
609 return -1;
610 }
611 UInt_t labelBitMask = GetAxisLabelStatus();
612 Double_t x = (labelBitMask & TH1::kXaxis) ? 0 : fXaxis.GetBinCenter(binx);
613 Double_t v = w;
614 fTsumw += v;
615 fTsumw2 += v * v;
616 fTsumwx += v * x;
617 fTsumwx2 += v * x * x;
618 fTsumwy += v * y;
619 fTsumwy2 += v * y * y;
620 fTsumwxy += v * x * y;
621 fTsumwz += v * z;
622 fTsumwz2 += v * z * z;
623 fTsumwxz += v * x * z;
624 fTsumwyz += v * y * z;
625 return bin;
626}
627
628////////////////////////////////////////////////////////////////////////////////
629/// Increment cell defined by x,namey,z by a weight w
630///
631/// If the weight is not equal to 1, the storage of the sum of squares of
632/// weights is automatically triggered and the sum of the squares of weights is incremented
633/// by w^2 in the corresponding cell.
634/// The function returns the corresponding global bin number which has its content
635/// incremented by w
636
637Int_t TH3::Fill(Double_t x, const char *namey, Double_t z, Double_t w)
638{
639 Int_t binx, biny, binz, bin;
640 fEntries++;
641 binx = fXaxis.FindBin(x);
642 biny = fYaxis.FindBin(namey);
643 binz = fZaxis.FindBin(z);
644 if (binx <0 || biny <0 || binz<0) return -1;
645 bin = binx + (fXaxis.GetNbins()+2)*(biny + (fYaxis.GetNbins()+2)*binz);
646 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW)) Sumw2(); // must be called before AddBinContent
647 if (fSumw2.fN) fSumw2.fArray[bin] += w*w;
648 AddBinContent(bin,w);
649 if (binx == 0 || binx > fXaxis.GetNbins()) {
650 if (!GetStatOverflowsBehaviour()) return -1;
651 }
652 if (biny == 0 || biny > fYaxis.GetNbins()) return -1;
653 if (binz == 0 || binz > fZaxis.GetNbins()) {
654 if (!GetStatOverflowsBehaviour()) return -1;
655 }
656 UInt_t labelBitMask = GetAxisLabelStatus();
657 Double_t y = (labelBitMask & TH1::kYaxis) ? 0 : fYaxis.GetBinCenter(biny);
658 Double_t v = w;
659 fTsumw += v;
660 fTsumw2 += v*v;
661 fTsumwx += v*x;
662 fTsumwx2 += v*x*x;
663 fTsumwy += v*y;
664 fTsumwy2 += v*y*y;
665 fTsumwxy += v*x*y;
666 fTsumwz += v*z;
667 fTsumwz2 += v*z*z;
668 fTsumwxz += v*x*z;
669 fTsumwyz += v*y*z;
670 return bin;
671}
672
673
674////////////////////////////////////////////////////////////////////////////////
675/// Increment cell defined by x,y,namez by a weight w
676///
677/// If the weight is not equal to 1, the storage of the sum of squares of
678/// weights is automatically triggered and the sum of the squares of weights is incremented
679/// by w^2 in the corresponding cell.
680/// The function returns the corresponding global bin number which has its content
681/// incremented by w
682
683Int_t TH3::Fill(Double_t x, Double_t y, const char *namez, Double_t w)
684{
685 Int_t binx, biny, binz, bin;
686 fEntries++;
687 binx = fXaxis.FindBin(x);
688 biny = fYaxis.FindBin(y);
689 binz = fZaxis.FindBin(namez);
690 if (binx <0 || biny <0 || binz<0) return -1;
691 bin = binx + (fXaxis.GetNbins()+2)*(biny + (fYaxis.GetNbins()+2)*binz);
692 if (!fSumw2.fN && w != 1.0 && !TestBit(TH1::kIsNotW)) Sumw2(); // must be called before AddBinContent
693 if (fSumw2.fN) fSumw2.fArray[bin] += w*w;
694 AddBinContent(bin,w);
695 if (binx == 0 || binx > fXaxis.GetNbins()) {
696 if (!GetStatOverflowsBehaviour()) return -1;
697 }
698 if (biny == 0 || biny > fYaxis.GetNbins()) {
699 if (!GetStatOverflowsBehaviour()) return -1;
700 }
701 if (binz == 0 || binz > fZaxis.GetNbins()) return -1;
702 UInt_t labelBitMask = GetAxisLabelStatus();
703 Double_t z = (labelBitMask & TH1::kZaxis) ? 0 : fZaxis.GetBinCenter(binz);
704 Double_t v = w;
705 fTsumw += v;
706 fTsumw2 += v*v;
707 fTsumwx += v*x;
708 fTsumwx2 += v*x*x;
709 fTsumwy += v*y;
710 fTsumwy2 += v*y*y;
711 fTsumwxy += v*x*y;
712 fTsumwz += v*z;
713 fTsumwz2 += v*z*z;
714 fTsumwxz += v*x*z;
715 fTsumwyz += v*y*z;
716 return bin;
717}
718
719
720////////////////////////////////////////////////////////////////////////////////
721/// Fill histogram following distribution in function fname.
722///
723/// @param fname : Function name used for filling the historam
724/// @param ntimes : number of times the histogram is filled
725/// @param rng : (optional) Random number generator used to sample
726///
727/// The distribution contained in the function fname (TF1) is integrated
728/// over the channel contents.
729/// It is normalized to 1.
730/// Getting one random number implies:
731/// - Generating a random number between 0 and 1 (say r1)
732/// - Look in which bin in the normalized integral r1 corresponds to
733/// - Fill histogram channel
734/// ntimes random numbers are generated
735///
736/// N.B. By dfault this methods approximates the integral of the function in each bin with the
737/// function value at the center of the bin, mutiplied by the bin width
738///
739///
740/// One can also call TF1::GetRandom to get a random variate from a function.
741
742void TH3::FillRandom(const char *fname, Int_t ntimes, TRandom * rng)
743{
744 Int_t bin, binx, biny, binz, ibin, loop;
745 Double_t r1, x, y,z, xv[3];
746 // Search for fname in the list of ROOT defined functions
747 TObject *fobj = gROOT->GetFunction(fname);
748 if (!fobj) { Error("FillRandom", "Unknown function: %s",fname); return; }
749 TF3 *f1 = dynamic_cast<TF3*>( fobj );
750 if (!f1) { Error("FillRandom", "Function: %s is not a TF3, is a %s",fname,fobj->IsA()->GetName()); return; }
751
752 TAxis & xAxis = fXaxis;
753 TAxis & yAxis = fYaxis;
754 TAxis & zAxis = fZaxis;
755
756 // in case axes of histogram are not defined use the function axis
758 Double_t xmin,xmax,ymin,ymax,zmin,zmax;
759 f1->GetRange(xmin,ymin,zmin,xmax,ymax,zmax);
760 Info("FillRandom","Using function axis and range ([%g,%g],[%g,%g],[%g,%g])",xmin, xmax,ymin,ymax,zmin,zmax);
761 xAxis = *(f1->GetHistogram()->GetXaxis());
762 yAxis = *(f1->GetHistogram()->GetYaxis());
763 zAxis = *(f1->GetHistogram()->GetZaxis());
764 }
765
766 // Allocate temporary space to store the integral and compute integral
767 Int_t nbinsx = xAxis.GetNbins();
768 Int_t nbinsy = yAxis.GetNbins();
769 Int_t nbinsz = zAxis.GetNbins();
770 Int_t nxy = nbinsx*nbinsy;
771 Int_t nbins = nbinsx*nbinsy*nbinsz;
772
773 Double_t *integral = new Double_t[nbins+1];
774 ibin = 0;
775 integral[ibin] = 0;
776 // approximate integral with function value at bin center
777 for (binz=1;binz<=nbinsz;binz++) {
778 xv[2] = zAxis.GetBinCenter(binz);
779 for (biny=1;biny<=nbinsy;biny++) {
780 xv[1] = yAxis.GetBinCenter(biny);
781 for (binx=1;binx<=nbinsx;binx++) {
782 xv[0] = xAxis.GetBinCenter(binx);
783 ibin++;
784 Double_t fint = f1->EvalPar(xv, nullptr);
785 // uncomment this line to have the integral computation in a bin
786 // Double_t fint = f1->Integral(xAxis.GetBinLowEdge(binx), xAxis.GetBinUpEdge(binx),
787 // yAxis.GetBinLowEdge(biny), yAxis.GetBinUpEdge(biny),
788 // zAxis.GetBinLowEdge(binz), zAxis.GetBinUpEdge(binz));
789 integral[ibin] = integral[ibin-1] + fint;
790 }
791 }
792 }
793
794 // Normalize integral to 1
795 if (integral[nbins] == 0 ) {
796 delete [] integral;
797 Error("FillRandom", "Integral = zero"); return;
798 }
799 for (bin=1;bin<=nbins;bin++) integral[bin] /= integral[nbins];
800
801 // Start main loop ntimes
802 if (fDimension < 2) nbinsy = -1;
803 if (fDimension < 3) nbinsz = -1;
804 for (loop=0;loop<ntimes;loop++) {
805 r1 = (rng) ? rng->Rndm() : gRandom->Rndm();
806 ibin = TMath::BinarySearch(nbins,&integral[0],r1);
807 binz = ibin/nxy;
808 biny = (ibin - nxy*binz)/nbinsx;
809 binx = 1 + ibin - nbinsx*(biny + nbinsy*binz);
810 if (nbinsz) binz++;
811 if (nbinsy) biny++;
812 x = xAxis.GetBinCenter(binx);
813 y = yAxis.GetBinCenter(biny);
814 z = zAxis.GetBinCenter(binz);
815 Fill(x,y,z, 1.);
816 }
817 delete [] integral;
818}
819
820
821////////////////////////////////////////////////////////////////////////////////
822/// Fill histogram following distribution in histogram h.
823///
824/// @param h : Histogram pointer used for smpling random number
825/// @param ntimes : number of times the histogram is filled
826/// @param rng : (optional) Random number generator used for sampling
827///
828/// The distribution contained in the histogram h (TH3) is integrated
829/// over the channel contents.
830/// It is normalized to 1.
831/// Getting one random number implies:
832/// - Generating a random number between 0 and 1 (say r1)
833/// - Look in which bin in the normalized integral r1 corresponds to
834/// - Fill histogram channel
835/// ntimes random numbers are generated
836
837void TH3::FillRandom(TH1 *h, Int_t ntimes, TRandom * rng)
838{
839 if (!h) { Error("FillRandom", "Null histogram"); return; }
840 if (fDimension != h->GetDimension()) {
841 Error("FillRandom", "Histograms with different dimensions"); return;
842 }
843
844 if (h->ComputeIntegral() == 0) return;
845
846 TH3 *h3 = (TH3*)h;
847 Int_t loop;
848 Double_t x,y,z;
849 for (loop=0;loop<ntimes;loop++) {
850 h3->GetRandom3(x,y,z,rng);
851 Fill(x,y,z);
852 }
853}
854
855////////////////////////////////////////////////////////////////////////////////
856/// Project slices along Z in case of a 3-D histogram, then fit each slice
857/// with function f1 and make a 2-d histogram for each fit parameter
858/// Only cells in the bin range [binminx,binmaxx] and [binminy,binmaxy] are considered.
859/// if f1=0, a gaussian is assumed
860/// Before invoking this function, one can set a subrange to be fitted along Z
861/// via f1->SetRange(zmin,zmax)
862/// The argument option (default="QNR") can be used to change the fit options.
863/// "Q" means Quiet mode
864/// "N" means do not show the result of the fit
865/// "R" means fit the function in the specified function range
866///
867/// Note that the generated histograms are added to the list of objects
868/// in the current directory. It is the user's responsibility to delete
869/// these histograms.
870///
871/// Example: Assume a 3-d histogram h3
872/// Root > h3->FitSlicesZ(); produces 4 TH2D histograms
873/// with h3_0 containing parameter 0(Constant) for a Gaus fit
874/// of each cell in X,Y projected along Z
875/// with h3_1 containing parameter 1(Mean) for a gaus fit
876/// with h3_2 containing parameter 2(StdDev) for a gaus fit
877/// with h3_chi2 containing the chisquare/number of degrees of freedom for a gaus fit
878///
879/// Root > h3->Fit(0,15,22,0,0,10);
880/// same as above, but only for bins 15 to 22 along X
881/// and only for cells in X,Y for which the corresponding projection
882/// along Z has more than cut bins filled.
883///
884/// NOTE: To access the generated histograms in the current directory, do eg:
885/// TH2D *h3_1 = (TH2D*)gDirectory->Get("h3_1");
886
887void TH3::FitSlicesZ(TF1 *f1, Int_t binminx, Int_t binmaxx, Int_t binminy, Int_t binmaxy, Int_t cut, Option_t *option)
888{
889 //Int_t nbinsz = fZaxis.GetNbins();
890
891 // get correct first and last bins for outer axes used in the loop doing the slices
892 // when using default values (0,-1) check if an axis range is set in outer axis
893 // do same as in DoProjection for inner axis
894 auto computeFirstAndLastBin = [](const TAxis & outerAxis, Int_t &firstbin, Int_t &lastbin) {
895 Int_t nbins = outerAxis.GetNbins();
896 if ( lastbin < firstbin && outerAxis.TestBit(TAxis::kAxisRange) ) {
897 firstbin = outerAxis.GetFirst();
898 lastbin = outerAxis.GetLast();
899 // For special case of TAxis::SetRange, when first == 1 and last
900 // = N and the range bit has been set, the TAxis will return 0
901 // for both.
902 if (firstbin == 0 && lastbin == 0) {
903 firstbin = 1;
904 lastbin = nbins;
905 }
906 }
907 if (firstbin < 0) firstbin = 0;
908 if (lastbin < 0 || lastbin > nbins + 1) lastbin = nbins + 1;
909 if (lastbin < firstbin) {firstbin = 0; lastbin = nbins + 1;}
910 };
911
912 computeFirstAndLastBin(fXaxis, binminx, binmaxx);
913 computeFirstAndLastBin(fYaxis, binminy, binmaxy);
914
915 // limits for the axis of the fit results histograms are different
916 auto computeAxisLimits = [](const TAxis & outerAxis, Int_t firstbin, Int_t lastbin,
917 Int_t &nBins, Double_t &xMin, Double_t & xMax) {
918 Int_t firstOutBin = std::max(firstbin,1);
919 Int_t lastOutBin = std::min(lastbin,outerAxis.GetNbins() ) ;
920 nBins = lastOutBin-firstOutBin+1;
921 xMin = outerAxis.GetBinLowEdge(firstOutBin);
922 xMax = outerAxis.GetBinUpEdge(lastOutBin);
923 // return first bin that is used in case of variable bin size axis
924 return firstOutBin;
925 };
926 Int_t nbinsX = 0;
927 Double_t xMin, xMax = 0;
928 Int_t firstBinXaxis = computeAxisLimits(fXaxis, binminx, binmaxx, nbinsX, xMin, xMax);
929 Int_t nbinsY = 0;
930 Double_t yMin, yMax = 0;
931 Int_t firstBinYaxis = computeAxisLimits(fYaxis, binminy, binmaxy, nbinsY, yMin, yMax);
932
933 //default is to fit with a gaussian
934 if (f1 == 0) {
935 f1 = (TF1*)gROOT->GetFunction("gaus");
936 if (f1 == 0) f1 = new TF1("gaus","gaus",fZaxis.GetXmin(),fZaxis.GetXmax());
938 }
939 const char *fname = f1->GetName();
940 Int_t npar = f1->GetNpar();
941 Double_t *parsave = new Double_t[npar];
942 f1->GetParameters(parsave);
943
944 //Create one 2-d histogram for each function parameter
945 Int_t ipar;
947 TString title;
948 std::vector<TH1*> hlist(npar+1); // include also chi2 histogram
949 const TArrayD *xbins = fXaxis.GetXbins();
950 const TArrayD *ybins = fYaxis.GetXbins();
951 for (ipar=0;ipar<= npar;ipar++) {
952 if (ipar < npar) {
953 // fitted parameter histograms
954 name = TString::Format("%s_%d",GetName(),ipar);
955 title = TString::Format("Fitted value of par[%d]=%s",ipar,f1->GetParName(ipar));
956 } else {
957 // chi2 histograms
958 name = TString::Format("%s_chi2",GetName());
959 title = "chisquare";
960 }
961 if (xbins->fN == 0 && ybins->fN == 0) {
962 hlist[ipar] = new TH2D(name, title,
963 nbinsX, xMin, xMax,
964 nbinsY, yMin, yMax);
965 } else if (xbins->fN > 0 && ybins->fN > 0 ) {
966 hlist[ipar] = new TH2D(name, title,
967 nbinsX, &xbins->fArray[firstBinXaxis],
968 nbinsY, &ybins->fArray[firstBinYaxis]);
969 }
970 // mixed case do not exist for TH3
971 R__ASSERT(hlist[ipar]);
972
973 hlist[ipar]->GetXaxis()->SetTitle(fXaxis.GetTitle());
974 hlist[ipar]->GetYaxis()->SetTitle(fYaxis.GetTitle());
975 }
976 TH1 * hchi2 = hlist.back();
977
978 //Loop on all cells in X,Y generate a projection along Z
979 TH1D *hpz = nullptr;
980 TString opt(option);
981 // add option "N" when fitting the 2D histograms
982 opt += " N ";
983
984 for (Int_t biny=binminy; biny<=binmaxy; biny++) {
985 for (Int_t binx=binminx; binx<=binmaxx; binx++) {
986 // use TH3::ProjectionZ
987 hpz = ProjectionZ("R_temp",binx,binx,biny,biny);
988
990 if ( nentries <= 0 || nentries < cut) {
991 if (!opt.Contains("Q"))
992 Info("FitSlicesZ","Slice (%d,%d) skipped, the number of entries is zero or smaller than the given cut value, n=%f",binx,biny,nentries);
993 continue;
994 }
995 f1->SetParameters(parsave);
996 Int_t bin = hlist[0]->FindBin( fXaxis.GetBinCenter(binx), fYaxis.GetBinCenter(biny) );
997 if (!opt.Contains("Q")) {
998 int ibx,iby,ibz = 0;
999 hlist[0]->GetBinXYZ(bin,ibx,iby,ibz);
1000 Info("DoFitSlices","Slice fit [(%f,%f),(%f,%f)]",hlist[0]->GetXaxis()->GetBinLowEdge(ibx), hlist[0]->GetXaxis()->GetBinUpEdge(ibx),
1001 hlist[0]->GetYaxis()->GetBinLowEdge(iby), hlist[0]->GetYaxis()->GetBinUpEdge(iby));
1002 }
1003 hpz->Fit(fname,opt.Data());
1004 Int_t npfits = f1->GetNumberFitPoints();
1005 if (npfits > npar && npfits >= cut) {
1006 for (ipar=0;ipar<npar;ipar++) {
1007 hlist[ipar]->SetBinContent(bin,f1->GetParameter(ipar));
1008 hlist[ipar]->SetBinError(bin,f1->GetParError(ipar));
1009 }
1010 hchi2->SetBinContent(bin,f1->GetChisquare()/(npfits-npar));
1011 }
1012 else {
1013 if (!opt.Contains("Q"))
1014 Info("FitSlicesZ","Fitted slice (%d,%d) skipped, the number of fitted points is too small, n=%d",binx,biny,npfits);
1015 }
1016 }
1017 }
1018 delete [] parsave;
1019 delete hpz;
1020}
1021
1022
1023////////////////////////////////////////////////////////////////////////////////
1024/// See comments in TH1::GetBin
1025
1026Int_t TH3::GetBin(Int_t binx, Int_t biny, Int_t binz) const
1027{
1028 Int_t ofy = fYaxis.GetNbins() + 1; // code duplication unavoidable because TH3 does not inherit from TH2
1029 if (biny < 0) biny = 0;
1030 if (biny > ofy) biny = ofy;
1031
1032 Int_t ofz = fZaxis.GetNbins() + 1; // overflow bin
1033 if (binz < 0) binz = 0;
1034 if (binz > ofz) binz = ofz;
1035
1036 return TH1::GetBin(binx) + (fXaxis.GetNbins() + 2) * (biny + (fYaxis.GetNbins() + 2) * binz);
1037}
1038
1039
1040////////////////////////////////////////////////////////////////////////////////
1041/// Compute first cell (binx,biny,binz) in the range [firstx,lastx](firsty,lasty][firstz,lastz] for which
1042/// diff = abs(cell_content-c) <= maxdiff
1043/// In case several cells in the specified range with diff=0 are found
1044/// the first cell found is returned in binx,biny,binz.
1045/// In case several cells in the specified range satisfy diff <=maxdiff
1046/// the cell with the smallest difference is returned in binx,biny,binz.
1047/// In all cases the function returns the smallest difference.
1048///
1049/// NOTE1: if firstx <= 0, firstx is set to bin 1
1050/// if (lastx < firstx then firstx is set to the number of bins in X
1051/// ie if firstx=0 and lastx=0 (default) the search is on all bins in X.
1052/// if firsty <= 0, firsty is set to bin 1
1053/// if (lasty < firsty then firsty is set to the number of bins in Y
1054/// ie if firsty=0 and lasty=0 (default) the search is on all bins in Y.
1055/// if firstz <= 0, firstz is set to bin 1
1056/// if (lastz < firstz then firstz is set to the number of bins in Z
1057/// ie if firstz=0 and lastz=0 (default) the search is on all bins in Z.
1058/// NOTE2: if maxdiff=0 (default), the first cell with content=c is returned.
1059
1061 Int_t firstx, Int_t lastx,
1062 Int_t firsty, Int_t lasty,
1063 Int_t firstz, Int_t lastz,
1064 Double_t maxdiff) const
1065{
1066 if (fDimension != 3) {
1067 binx = 0;
1068 biny = 0;
1069 binz = 0;
1070 Error("GetBinWithContent3","function is only valid for 3-D histograms");
1071 return 0;
1072 }
1073 if (firstx <= 0) firstx = 1;
1074 if (lastx < firstx) lastx = fXaxis.GetNbins();
1075 if (firsty <= 0) firsty = 1;
1076 if (lasty < firsty) lasty = fYaxis.GetNbins();
1077 if (firstz <= 0) firstz = 1;
1078 if (lastz < firstz) lastz = fZaxis.GetNbins();
1079 Int_t binminx = 0, binminy=0, binminz=0;
1080 Double_t diff, curmax = 1.e240;
1081 for (Int_t k=firstz;k<=lastz;k++) {
1082 for (Int_t j=firsty;j<=lasty;j++) {
1083 for (Int_t i=firstx;i<=lastx;i++) {
1084 diff = TMath::Abs(GetBinContent(i,j,k)-c);
1085 if (diff <= 0) {binx = i; biny=j; binz=k; return diff;}
1086 if (diff < curmax && diff <= maxdiff) {curmax = diff, binminx=i; binminy=j;binminz=k;}
1087 }
1088 }
1089 }
1090 binx = binminx;
1091 biny = binminy;
1092 binz = binminz;
1093 return curmax;
1094}
1095
1096
1097////////////////////////////////////////////////////////////////////////////////
1098/// Return correlation factor between axis1 and axis2.
1099
1101{
1102 if (axis1 < 1 || axis2 < 1 || axis1 > 3 || axis2 > 3) {
1103 Error("GetCorrelationFactor","Wrong parameters");
1104 return 0;
1105 }
1106 if (axis1 == axis2) return 1;
1107 Double_t stddev1 = GetStdDev(axis1);
1108 if (stddev1 == 0) return 0;
1109 Double_t stddev2 = GetStdDev(axis2);
1110 if (stddev2 == 0) return 0;
1111 return GetCovariance(axis1,axis2)/stddev1/stddev2;
1112}
1113
1114
1115////////////////////////////////////////////////////////////////////////////////
1116/// Return covariance between axis1 and axis2.
1117
1119{
1120 if (axis1 < 1 || axis2 < 1 || axis1 > 3 || axis2 > 3) {
1121 Error("GetCovariance","Wrong parameters");
1122 return 0;
1123 }
1124 Double_t stats[kNstat];
1125 GetStats(stats);
1126 Double_t sumw = stats[0];
1127 Double_t sumwx = stats[2];
1128 Double_t sumwx2 = stats[3];
1129 Double_t sumwy = stats[4];
1130 Double_t sumwy2 = stats[5];
1131 Double_t sumwxy = stats[6];
1132 Double_t sumwz = stats[7];
1133 Double_t sumwz2 = stats[8];
1134 Double_t sumwxz = stats[9];
1135 Double_t sumwyz = stats[10];
1136
1137 if (sumw == 0) return 0;
1138 if (axis1 == 1 && axis2 == 1) {
1139 return TMath::Abs(sumwx2/sumw - sumwx*sumwx/(sumw*sumw));
1140 }
1141 if (axis1 == 2 && axis2 == 2) {
1142 return TMath::Abs(sumwy2/sumw - sumwy*sumwy/(sumw*sumw));
1143 }
1144 if (axis1 == 3 && axis2 == 3) {
1145 return TMath::Abs(sumwz2/sumw - sumwz*sumwz/(sumw*sumw));
1146 }
1147 if ((axis1 == 1 && axis2 == 2) || (axis1 == 2 && axis2 == 1)) {
1148 return sumwxy/sumw - sumwx*sumwy/(sumw*sumw);
1149 }
1150 if ((axis1 == 1 && axis2 == 3) || (axis1 == 3 && axis2 == 1)) {
1151 return sumwxz/sumw - sumwx*sumwz/(sumw*sumw);
1152 }
1153 if ((axis1 == 2 && axis2 == 3) || (axis1 == 3 && axis2 == 2)) {
1154 return sumwyz/sumw - sumwy*sumwz/(sumw*sumw);
1155 }
1156 return 0;
1157}
1158
1159
1160////////////////////////////////////////////////////////////////////////////////
1161/// Return 3 random numbers along axis x , y and z distributed according
1162/// to the cell-contents of this 3-dim histogram
1163/// @param[out] x reference to random generated x value
1164/// @param[out] y reference to random generated y value
1165/// @param[out] z reference to random generated z value
1166/// @param[in] rng (optional) Random number generator pointer used (default is gRandom)
1167
1169{
1170 Int_t nbinsx = GetNbinsX();
1171 Int_t nbinsy = GetNbinsY();
1172 Int_t nbinsz = GetNbinsZ();
1173 Int_t nxy = nbinsx*nbinsy;
1174 Int_t nbins = nxy*nbinsz;
1175 Double_t integral;
1176 // compute integral checking that all bins have positive content (see ROOT-5894)
1177 if (fIntegral) {
1178 if (fIntegral[nbins+1] != fEntries) integral = ComputeIntegral(true);
1179 else integral = fIntegral[nbins];
1180 } else {
1181 integral = ComputeIntegral(true);
1182 }
1183 if (integral == 0 ) { x = 0; y = 0; z = 0; return;}
1184 // case histogram has negative bins
1185 if (integral == TMath::QuietNaN() ) { x = TMath::QuietNaN(); y = TMath::QuietNaN(); z = TMath::QuietNaN(); return;}
1186
1187 if (!rng) rng = gRandom;
1188 Double_t r1 = rng->Rndm();
1189 Int_t ibin = TMath::BinarySearch(nbins,fIntegral,(Double_t) r1);
1190 Int_t binz = ibin/nxy;
1191 Int_t biny = (ibin - nxy*binz)/nbinsx;
1192 Int_t binx = ibin - nbinsx*(biny + nbinsy*binz);
1193 x = fXaxis.GetBinLowEdge(binx+1);
1194 if (r1 > fIntegral[ibin]) x +=
1195 fXaxis.GetBinWidth(binx+1)*(r1-fIntegral[ibin])/(fIntegral[ibin+1] - fIntegral[ibin]);
1196 y = fYaxis.GetBinLowEdge(biny+1) + fYaxis.GetBinWidth(biny+1)*rng->Rndm();
1197 z = fZaxis.GetBinLowEdge(binz+1) + fZaxis.GetBinWidth(binz+1)*rng->Rndm();
1198}
1199
1200
1201////////////////////////////////////////////////////////////////////////////////
1202/// Fill the array stats from the contents of this histogram
1203/// The array stats must be correctly dimensioned in the calling program.
1204/// stats[0] = sumw
1205/// stats[1] = sumw2
1206/// stats[2] = sumwx
1207/// stats[3] = sumwx2
1208/// stats[4] = sumwy
1209/// stats[5] = sumwy2
1210/// stats[6] = sumwxy
1211/// stats[7] = sumwz
1212/// stats[8] = sumwz2
1213/// stats[9] = sumwxz
1214/// stats[10]= sumwyz
1215
1216void TH3::GetStats(Double_t *stats) const
1217{
1218 if (fBuffer) ((TH3*)this)->BufferEmpty();
1219
1220 Int_t bin, binx, biny, binz;
1221 Double_t w,err;
1222 Double_t x,y,z;
1224 for (bin=0;bin<11;bin++) stats[bin] = 0;
1225
1226 Int_t firstBinX = fXaxis.GetFirst();
1227 Int_t lastBinX = fXaxis.GetLast();
1228 Int_t firstBinY = fYaxis.GetFirst();
1229 Int_t lastBinY = fYaxis.GetLast();
1230 Int_t firstBinZ = fZaxis.GetFirst();
1231 Int_t lastBinZ = fZaxis.GetLast();
1232 // include underflow/overflow if TH1::StatOverflows(kTRUE) in case no range is set on the axis
1235 if (firstBinX == 1) firstBinX = 0;
1236 if (lastBinX == fXaxis.GetNbins() ) lastBinX += 1;
1237 }
1239 if (firstBinY == 1) firstBinY = 0;
1240 if (lastBinY == fYaxis.GetNbins() ) lastBinY += 1;
1241 }
1243 if (firstBinZ == 1) firstBinZ = 0;
1244 if (lastBinZ == fZaxis.GetNbins() ) lastBinZ += 1;
1245 }
1246 }
1247
1248 // check for labels axis . In that case corresponsing statistics do not make sense and it is set to zero
1249 Bool_t labelXaxis = ((const_cast<TAxis&>(fXaxis)).GetLabels() && fXaxis.CanExtend() );
1250 Bool_t labelYaxis = ((const_cast<TAxis&>(fYaxis)).GetLabels() && fYaxis.CanExtend() );
1251 Bool_t labelZaxis = ((const_cast<TAxis&>(fZaxis)).GetLabels() && fZaxis.CanExtend() );
1252
1253 for (binz = firstBinZ; binz <= lastBinZ; binz++) {
1254 z = (!labelZaxis) ? fZaxis.GetBinCenter(binz) : 0;
1255 for (biny = firstBinY; biny <= lastBinY; biny++) {
1256 y = (!labelYaxis) ? fYaxis.GetBinCenter(biny) : 0;
1257 for (binx = firstBinX; binx <= lastBinX; binx++) {
1258 bin = GetBin(binx,biny,binz);
1259 x = (!labelXaxis) ? fXaxis.GetBinCenter(binx) : 0;
1260 //w = TMath::Abs(GetBinContent(bin));
1261 w = RetrieveBinContent(bin);
1262 err = TMath::Abs(GetBinError(bin));
1263 stats[0] += w;
1264 stats[1] += err*err;
1265 stats[2] += w*x;
1266 stats[3] += w*x*x;
1267 stats[4] += w*y;
1268 stats[5] += w*y*y;
1269 stats[6] += w*x*y;
1270 stats[7] += w*z;
1271 stats[8] += w*z*z;
1272 stats[9] += w*x*z;
1273 stats[10]+= w*y*z;
1274 }
1275 }
1276 }
1277 } else {
1278 stats[0] = fTsumw;
1279 stats[1] = fTsumw2;
1280 stats[2] = fTsumwx;
1281 stats[3] = fTsumwx2;
1282 stats[4] = fTsumwy;
1283 stats[5] = fTsumwy2;
1284 stats[6] = fTsumwxy;
1285 stats[7] = fTsumwz;
1286 stats[8] = fTsumwz2;
1287 stats[9] = fTsumwxz;
1288 stats[10]= fTsumwyz;
1289 }
1290}
1291
1292
1293////////////////////////////////////////////////////////////////////////////////
1294/// Return integral of bin contents. Only bins in the bins range are considered.
1295/// By default the integral is computed as the sum of bin contents in the range.
1296/// if option "width" is specified, the integral is the sum of
1297/// the bin contents multiplied by the bin width in x, y and in z.
1298
1300{
1303 fZaxis.GetFirst(),fZaxis.GetLast(),option);
1304}
1305
1306
1307////////////////////////////////////////////////////////////////////////////////
1308/// Return integral of bin contents in range [binx1,binx2],[biny1,biny2],[binz1,binz2]
1309/// for a 3-D histogram
1310/// By default the integral is computed as the sum of bin contents in the range.
1311/// if option "width" is specified, the integral is the sum of
1312/// the bin contents multiplied by the bin width in x, y and in z.
1313
1314Double_t TH3::Integral(Int_t binx1, Int_t binx2, Int_t biny1, Int_t biny2,
1315 Int_t binz1, Int_t binz2, Option_t *option) const
1316{
1317 Double_t err = 0;
1318 return DoIntegral(binx1,binx2,biny1,biny2,binz1,binz2,err,option);
1319}
1320
1321
1322////////////////////////////////////////////////////////////////////////////////
1323/// Return integral of bin contents in range [binx1,binx2],[biny1,biny2],[binz1,binz2]
1324/// for a 3-D histogram. Calculates also the integral error using error propagation
1325/// from the bin errors assuming that all the bins are uncorrelated.
1326/// By default the integral is computed as the sum of bin contents in the range.
1327/// if option "width" is specified, the integral is the sum of
1328/// the bin contents multiplied by the bin width in x, y and in z.
1329
1331 Int_t binz1, Int_t binz2,
1332 Double_t & error, Option_t *option) const
1333{
1334 return DoIntegral(binx1,binx2,biny1,biny2,binz1,binz2,error,option,kTRUE);
1335}
1336
1337////////////////////////////////////////////////////////////////////////////////
1338///Not yet implemented
1339
1341{
1342 Error("Interpolate","This function must be called with 3 arguments for a TH3");
1343 return 0;
1344}
1345
1346
1347////////////////////////////////////////////////////////////////////////////////
1348///Not yet implemented
1349
1351{
1352 Error("Interpolate","This function must be called with 3 arguments for a TH3");
1353 return 0;
1354}
1355
1356
1357////////////////////////////////////////////////////////////////////////////////
1358/// Given a point P(x,y,z), Interpolate approximates the value via trilinear interpolation
1359/// based on the 8 nearest bin center points (corner of the cube surrounding the points)
1360/// The Algorithm is described in http://en.wikipedia.org/wiki/Trilinear_interpolation
1361/// The given values (x,y,z) must be between first bin center and last bin center for each coordinate:
1362///
1363/// fXAxis.GetBinCenter(1) < x < fXaxis.GetBinCenter(nbinX) AND
1364/// fYAxis.GetBinCenter(1) < y < fYaxis.GetBinCenter(nbinY) AND
1365/// fZAxis.GetBinCenter(1) < z < fZaxis.GetBinCenter(nbinZ)
1366
1368{
1369 Int_t ubx = fXaxis.FindFixBin(x);
1370 if ( x < fXaxis.GetBinCenter(ubx) ) ubx -= 1;
1371 Int_t obx = ubx + 1;
1372
1373 Int_t uby = fYaxis.FindFixBin(y);
1374 if ( y < fYaxis.GetBinCenter(uby) ) uby -= 1;
1375 Int_t oby = uby + 1;
1376
1377 Int_t ubz = fZaxis.FindFixBin(z);
1378 if ( z < fZaxis.GetBinCenter(ubz) ) ubz -= 1;
1379 Int_t obz = ubz + 1;
1380
1381
1382// if ( IsBinUnderflow(GetBin(ubx, uby, ubz)) ||
1383// IsBinOverflow (GetBin(obx, oby, obz)) ) {
1384 if (ubx <=0 || uby <=0 || ubz <= 0 ||
1385 obx > fXaxis.GetNbins() || oby > fYaxis.GetNbins() || obz > fZaxis.GetNbins() ) {
1386 Error("Interpolate","Cannot interpolate outside histogram domain.");
1387 return 0;
1388 }
1389
1393
1394 Double_t xd = (x - fXaxis.GetBinCenter(ubx)) / xw;
1395 Double_t yd = (y - fYaxis.GetBinCenter(uby)) / yw;
1396 Double_t zd = (z - fZaxis.GetBinCenter(ubz)) / zw;
1397
1398
1399 Double_t v[] = { GetBinContent( ubx, uby, ubz ), GetBinContent( ubx, uby, obz ),
1400 GetBinContent( ubx, oby, ubz ), GetBinContent( ubx, oby, obz ),
1401 GetBinContent( obx, uby, ubz ), GetBinContent( obx, uby, obz ),
1402 GetBinContent( obx, oby, ubz ), GetBinContent( obx, oby, obz ) };
1403
1404
1405 Double_t i1 = v[0] * (1 - zd) + v[1] * zd;
1406 Double_t i2 = v[2] * (1 - zd) + v[3] * zd;
1407 Double_t j1 = v[4] * (1 - zd) + v[5] * zd;
1408 Double_t j2 = v[6] * (1 - zd) + v[7] * zd;
1409
1410
1411 Double_t w1 = i1 * (1 - yd) + i2 * yd;
1412 Double_t w2 = j1 * (1 - yd) + j2 * yd;
1413
1414
1415 Double_t result = w1 * (1 - xd) + w2 * xd;
1416
1417 return result;
1418}
1419
1420
1421////////////////////////////////////////////////////////////////////////////////
1422/// Statistical test of compatibility in shape between
1423/// THIS histogram and h2, using Kolmogorov test.
1424/// Default: Ignore under- and overflow bins in comparison
1425///
1426/// option is a character string to specify options
1427/// "U" include Underflows in test
1428/// "O" include Overflows
1429/// "N" include comparison of normalizations
1430/// "D" Put out a line of "Debug" printout
1431/// "M" Return the Maximum Kolmogorov distance instead of prob
1432///
1433/// The returned function value is the probability of test
1434/// (much less than one means NOT compatible)
1435///
1436/// The KS test uses the distance between the pseudo-CDF's obtained
1437/// from the histogram. Since in more than 1D the order for generating the pseudo-CDF is
1438/// arbitrary, we use the pseudo-CDF's obtained from all the possible 6 combinations of the 3 axis.
1439/// The average of all the maximum distances obtained is used in the tests.
1440
1441Double_t TH3::KolmogorovTest(const TH1 *h2, Option_t *option) const
1442{
1443 TString opt = option;
1444 opt.ToUpper();
1445
1446 Double_t prb = 0;
1447 TH1 *h1 = (TH1*)this;
1448 if (h2 == 0) return 0;
1449 const TAxis *xaxis1 = h1->GetXaxis();
1450 const TAxis *xaxis2 = h2->GetXaxis();
1451 const TAxis *yaxis1 = h1->GetYaxis();
1452 const TAxis *yaxis2 = h2->GetYaxis();
1453 const TAxis *zaxis1 = h1->GetZaxis();
1454 const TAxis *zaxis2 = h2->GetZaxis();
1455 Int_t ncx1 = xaxis1->GetNbins();
1456 Int_t ncx2 = xaxis2->GetNbins();
1457 Int_t ncy1 = yaxis1->GetNbins();
1458 Int_t ncy2 = yaxis2->GetNbins();
1459 Int_t ncz1 = zaxis1->GetNbins();
1460 Int_t ncz2 = zaxis2->GetNbins();
1461
1462 // Check consistency of dimensions
1463 if (h1->GetDimension() != 3 || h2->GetDimension() != 3) {
1464 Error("KolmogorovTest","Histograms must be 3-D\n");
1465 return 0;
1466 }
1467
1468 // Check consistency in number of channels
1469 if (ncx1 != ncx2) {
1470 Error("KolmogorovTest","Number of channels in X is different, %d and %d\n",ncx1,ncx2);
1471 return 0;
1472 }
1473 if (ncy1 != ncy2) {
1474 Error("KolmogorovTest","Number of channels in Y is different, %d and %d\n",ncy1,ncy2);
1475 return 0;
1476 }
1477 if (ncz1 != ncz2) {
1478 Error("KolmogorovTest","Number of channels in Z is different, %d and %d\n",ncz1,ncz2);
1479 return 0;
1480 }
1481
1482 // Check consistency in channel edges
1483 Bool_t afunc1 = kFALSE;
1484 Bool_t afunc2 = kFALSE;
1485 Double_t difprec = 1e-5;
1486 Double_t diff1 = TMath::Abs(xaxis1->GetXmin() - xaxis2->GetXmin());
1487 Double_t diff2 = TMath::Abs(xaxis1->GetXmax() - xaxis2->GetXmax());
1488 if (diff1 > difprec || diff2 > difprec) {
1489 Error("KolmogorovTest","histograms with different binning along X");
1490 return 0;
1491 }
1492 diff1 = TMath::Abs(yaxis1->GetXmin() - yaxis2->GetXmin());
1493 diff2 = TMath::Abs(yaxis1->GetXmax() - yaxis2->GetXmax());
1494 if (diff1 > difprec || diff2 > difprec) {
1495 Error("KolmogorovTest","histograms with different binning along Y");
1496 return 0;
1497 }
1498 diff1 = TMath::Abs(zaxis1->GetXmin() - zaxis2->GetXmin());
1499 diff2 = TMath::Abs(zaxis1->GetXmax() - zaxis2->GetXmax());
1500 if (diff1 > difprec || diff2 > difprec) {
1501 Error("KolmogorovTest","histograms with different binning along Z");
1502 return 0;
1503 }
1504
1505 // Should we include Uflows, Oflows?
1506 Int_t ibeg = 1, jbeg = 1, kbeg = 1;
1507 Int_t iend = ncx1, jend = ncy1, kend = ncz1;
1508 if (opt.Contains("U")) {ibeg = 0; jbeg = 0; kbeg = 0;}
1509 if (opt.Contains("O")) {iend = ncx1+1; jend = ncy1+1; kend = ncz1+1;}
1510
1511 Int_t i,j,k,bin;
1512 Double_t sum1 = 0;
1513 Double_t sum2 = 0;
1514 Double_t w1 = 0;
1515 Double_t w2 = 0;
1516 for (i = ibeg; i <= iend; i++) {
1517 for (j = jbeg; j <= jend; j++) {
1518 for (k = kbeg; k <= kend; k++) {
1519 bin = h1->GetBin(i,j,k);
1520 sum1 += h1->GetBinContent(bin);
1521 sum2 += h2->GetBinContent(bin);
1522 Double_t ew1 = h1->GetBinError(bin);
1523 Double_t ew2 = h2->GetBinError(bin);
1524 w1 += ew1*ew1;
1525 w2 += ew2*ew2;
1526 }
1527 }
1528 }
1529
1530
1531 // Check that both scatterplots contain events
1532 if (sum1 == 0) {
1533 Error("KolmogorovTest","Integral is zero for h1=%s\n",h1->GetName());
1534 return 0;
1535 }
1536 if (sum2 == 0) {
1537 Error("KolmogorovTest","Integral is zero for h2=%s\n",h2->GetName());
1538 return 0;
1539 }
1540 // calculate the effective entries.
1541 // the case when errors are zero (w1 == 0 or w2 ==0) are equivalent to
1542 // compare to a function. In that case the rescaling is done only on sqrt(esum2) or sqrt(esum1)
1543 Double_t esum1 = 0, esum2 = 0;
1544 if (w1 > 0)
1545 esum1 = sum1 * sum1 / w1;
1546 else
1547 afunc1 = kTRUE; // use later for calculating z
1548
1549 if (w2 > 0)
1550 esum2 = sum2 * sum2 / w2;
1551 else
1552 afunc2 = kTRUE; // use later for calculating z
1553
1554 if (afunc2 && afunc1) {
1555 Error("KolmogorovTest","Errors are zero for both histograms\n");
1556 return 0;
1557 }
1558
1559 // Find Kolmogorov distance
1560 // order is arbitrary take average of all possible 6 starting orders x,y,z
1561 int order[3] = {0,1,2};
1562 int binbeg[3];
1563 int binend[3];
1564 int ibin[3];
1565 binbeg[0] = ibeg; binbeg[1] = jbeg; binbeg[2] = kbeg;
1566 binend[0] = iend; binend[1] = jend; binend[2] = kend;
1567 Double_t vdfmax[6]; // there are in total 6 combinations
1568 int icomb = 0;
1569 Double_t s1 = 1./(6.*sum1);
1570 Double_t s2 = 1./(6.*sum2);
1571 Double_t rsum1=0, rsum2=0;
1572 do {
1573 // loop on bins
1574 Double_t dmax = 0;
1575 for (i = binbeg[order[0] ]; i <= binend[order[0] ]; i++) {
1576 for ( j = binbeg[order[1] ]; j <= binend[order[1] ]; j++) {
1577 for ( k = binbeg[order[2] ]; k <= binend[order[2] ]; k++) {
1578 ibin[ order[0] ] = i;
1579 ibin[ order[1] ] = j;
1580 ibin[ order[2] ] = k;
1581 bin = h1->GetBin(ibin[0],ibin[1],ibin[2]);
1582 rsum1 += s1*h1->GetBinContent(bin);
1583 rsum2 += s2*h2->GetBinContent(bin);
1584 dmax = TMath::Max(dmax, TMath::Abs(rsum1-rsum2));
1585 }
1586 }
1587 }
1588 vdfmax[icomb] = dmax;
1589 icomb++;
1590 } while (TMath::Permute(3,order) );
1591
1592
1593 // get average of distances
1594 Double_t dfmax = TMath::Mean(6,vdfmax);
1595
1596 // Get Kolmogorov probability
1597 Double_t factnm;
1598 if (afunc1) factnm = TMath::Sqrt(sum2);
1599 else if (afunc2) factnm = TMath::Sqrt(sum1);
1600 else factnm = TMath::Sqrt(sum1*sum2/(sum1+sum2));
1601 Double_t z = dfmax*factnm;
1602
1603 prb = TMath::KolmogorovProb(z);
1604
1605 Double_t prb1 = 0, prb2 = 0;
1606 // option N to combine normalization makes sense if both afunc1 and afunc2 are false
1607 if (opt.Contains("N") && !(afunc1 || afunc2 ) ) {
1608 // Combine probabilities for shape and normalization
1609 prb1 = prb;
1610 Double_t d12 = esum1-esum2;
1611 Double_t chi2 = d12*d12/(esum1+esum2);
1612 prb2 = TMath::Prob(chi2,1);
1613 // see Eadie et al., section 11.6.2
1614 if (prb > 0 && prb2 > 0) prb = prb*prb2*(1-TMath::Log(prb*prb2));
1615 else prb = 0;
1616 }
1617
1618 // debug printout
1619 if (opt.Contains("D")) {
1620 printf(" Kolmo Prob h1 = %s, sum1=%g\n",h1->GetName(),sum1);
1621 printf(" Kolmo Prob h2 = %s, sum2=%g\n",h2->GetName(),sum2);
1622 printf(" Kolmo Probabil = %f, Max Dist = %g\n",prb,dfmax);
1623 if (opt.Contains("N"))
1624 printf(" Kolmo Probabil = %f for shape alone, =%f for normalisation alone\n",prb1,prb2);
1625 }
1626 // This numerical error condition should never occur:
1627 if (TMath::Abs(rsum1-1) > 0.002) Warning("KolmogorovTest","Numerical problems with h1=%s\n",h1->GetName());
1628 if (TMath::Abs(rsum2-1) > 0.002) Warning("KolmogorovTest","Numerical problems with h2=%s\n",h2->GetName());
1629
1630 if (opt.Contains("M")) return dfmax; // return average of max distance
1631
1632 return prb;
1633}
1634
1635
1636////////////////////////////////////////////////////////////////////////////////
1637/// Project a 3-D histogram into a 1-D histogram along X.
1638///
1639/// The projection is always of the type TH1D.
1640/// The projection is made from the cells along the X axis
1641/// ranging from iymin to iymax and izmin to izmax included.
1642/// By default, underflow and overflows are included in both the Y and Z axis.
1643/// By Setting iymin=1 and iymax=NbinsY the underflow and/or overflow in Y will be excluded
1644/// By setting izmin=1 and izmax=NbinsZ the underflow and/or overflow in Z will be excluded
1645///
1646/// if option "e" is specified, the errors are computed.
1647/// if option "d" is specified, the projection is drawn in the current pad.
1648/// if option "o" original axis range of the target axes will be
1649/// kept, but only bins inside the selected range will be filled.
1650///
1651/// NOTE that if a TH1D named "name" exists in the current directory or pad
1652/// the histogram is reset and filled again with the projected contents of the TH3.
1653///
1654/// implemented using Project3D
1655
1656TH1D *TH3::ProjectionX(const char *name, Int_t iymin, Int_t iymax,
1657 Int_t izmin, Int_t izmax, Option_t *option) const
1658{
1659 // in case of default name append the parent name
1660 TString hname = name;
1661 if (hname == "_px") hname = TString::Format("%s%s", GetName(), name);
1662 TString title = TString::Format("%s ( Projection X )",GetTitle());
1663
1664 // when projecting in Z outer axis are Y and Z (order is important. It is defined in the DoProject1D function)
1665 return DoProject1D(hname, title, iymin, iymax, izmin, izmax, &fXaxis, &fYaxis, &fZaxis, option);
1666}
1667
1668
1669////////////////////////////////////////////////////////////////////////////////
1670/// Project a 3-D histogram into a 1-D histogram along Y.
1671///
1672/// The projection is always of the type TH1D.
1673/// The projection is made from the cells along the Y axis
1674/// ranging from ixmin to ixmax and izmin to izmax included.
1675/// By default, underflow and overflow are included in both the X and Z axis.
1676/// By setting ixmin=1 and ixmax=NbinsX the underflow and/or overflow in X will be excluded
1677/// By setting izmin=1 and izmax=NbinsZ the underflow and/or overflow in Z will be excluded
1678///
1679/// if option "e" is specified, the errors are computed.
1680/// if option "d" is specified, the projection is drawn in the current pad.
1681/// if option "o" original axis range of the target axes will be
1682/// kept, but only bins inside the selected range will be filled.
1683///
1684/// NOTE that if a TH1D named "name" exists in the current directory or pad,
1685/// the histogram is reset and filled again with the projected contents of the TH3.
1686///
1687/// implemented using Project3D
1688
1689TH1D *TH3::ProjectionY(const char *name, Int_t ixmin, Int_t ixmax,
1690 Int_t izmin, Int_t izmax, Option_t *option) const
1691{
1692 TString hname = name;
1693 if (hname == "_py") hname = TString::Format("%s%s", GetName(), name);
1694 TString title = TString::Format("%s ( Projection Y )",GetTitle());
1695
1696 // when projecting in Z outer axis are X and Y (order is important. It is defined in the DoProject1D function)
1697 return DoProject1D(hname, title, ixmin, ixmax, izmin, izmax, &fYaxis, &fXaxis, &fZaxis, option);
1698}
1699
1700////////////////////////////////////////////////////////////////////////////////
1701/// Project a 3-D histogram into a 1-D histogram along Z.
1702///
1703/// The projection is always of the type TH1D.
1704/// The projection is made from the cells along the Z axis
1705/// ranging from ixmin to ixmax and iymin to iymax included.
1706/// By default, bins 1 to nx and 1 to ny are included
1707/// By default, underflow and overflow are included in both the X and Y axis.
1708/// By Setting ixmin=1 and ixmax=NbinsX the underflow and/or overflow in X will be excluded
1709/// By setting iymin=1 and/or iymax=NbinsY the underflow and/or overflow in Y will be excluded
1710///
1711/// if option "e" is specified, the errors are computed.
1712/// if option "d" is specified, the projection is drawn in the current pad.
1713/// if option "o" original axis range of the target axes will be
1714/// kept, but only bins inside the selected range will be filled.
1715///
1716/// NOTE that if a TH1D named "name" exists in the current directory or pad,
1717/// the histogram is reset and filled again with the projected contents of the TH3.
1718///
1719/// implemented using Project3D
1720
1721TH1D *TH3::ProjectionZ(const char *name, Int_t ixmin, Int_t ixmax,
1722 Int_t iymin, Int_t iymax, Option_t *option) const
1723{
1724
1725 TString hname = name;
1726 if (hname == "_pz") hname = TString::Format("%s%s", GetName(), name);
1727 TString title = TString::Format("%s ( Projection Z )",GetTitle());
1728
1729 // when projecting in Z outer axis are X and Y (order is important. It is defined in the DoProject1D function)
1730 return DoProject1D(hname, title, ixmin, ixmax, iymin, iymax, &fZaxis, &fXaxis, &fYaxis, option);
1731}
1732
1733
1734////////////////////////////////////////////////////////////////////////////////
1735/// internal method performing the projection to 1D histogram
1736/// called from TH3::Project3D
1737
1738TH1D *TH3::DoProject1D(const char* name, const char * title, int imin1, int imax1, int imin2, int imax2,
1739 const TAxis* projAxis, const TAxis * axis1, const TAxis * axis2, Option_t * option) const
1740{
1741
1742 TString opt = option;
1743 opt.ToLower();
1744
1745 // save previous axis range and bits
1746 // Int_t iminOld1 = axis1->GetFirst();
1747 // Int_t imaxOld1 = axis1->GetLast();
1748 // Int_t iminOld2 = axis2->GetFirst();
1749 // Int_t imaxOld2 = axis2->GetLast();
1750 // Bool_t hadRange1 = axis1->TestBit(TAxis::kAxisRange);
1751 // Bool_t hadRange2 = axis2->TestBit(TAxis::kAxisRange);
1752
1753 // need to cast-away constness to set range
1754 TAxis out1(*axis1);
1755 TAxis out2(*axis2);
1756 // const_cast<TAxis *>(axis1)->SetRange(imin1, imax1);
1757 // const_cast<TAxis*>(axis2)->SetRange(imin2,imax2);
1758 out1.SetRange(imin1, imax1);
1759 out2.SetRange(imin2, imax2);
1760
1761 Bool_t computeErrors = GetSumw2N();
1762 if (opt.Contains("e") ) {
1763 computeErrors = kTRUE;
1764 opt.Remove(opt.First("e"),1);
1765 }
1766 Bool_t originalRange = kFALSE;
1767 if (opt.Contains('o') ) {
1768 originalRange = kTRUE;
1769 opt.Remove(opt.First("o"),1);
1770 }
1771
1772 TH1D * h1 = DoProject1D(name, title, projAxis, &out1, &out2, computeErrors, originalRange,true,true);
1773
1774 // // restore original range
1775 // if (axis1->TestBit(TAxis::kAxisRange)) {
1776 // if (hadRange1) const_cast<TAxis*>(axis1)->SetRange(iminOld1,imaxOld1);
1777 // if (axis2->TestBit(TAxis::kAxisRange)) const_cast<TAxis*>(axis2)->SetRange(iminOld2,imaxOld2);
1778 // // we need also to restore the original bits
1779
1780 // draw in current pad
1781 if (h1 && opt.Contains("d")) {
1782 opt.Remove(opt.First("d"),1);
1783 TVirtualPad *padsav = gPad;
1785 if (pad) pad->cd();
1786 if (!gPad || !gPad->FindObject(h1)) {
1787 h1->Draw(opt);
1788 } else {
1789 h1->Paint(opt);
1790 }
1791 if (padsav) padsav->cd();
1792 }
1793
1794 return h1;
1795}
1796
1797////////////////////////////////////////////////////////////////////////////////
1798/// internal methdod performing the projection to 1D histogram
1799/// called from other TH3::DoProject1D
1800
1801TH1D *TH3::DoProject1D(const char* name, const char * title, const TAxis* projX,
1802 const TAxis * out1, const TAxis * out2,
1803 bool computeErrors, bool originalRange,
1804 bool useUF, bool useOF) const
1805{
1806 // Create the projection histogram
1807 TH1D *h1 = 0;
1808
1809 // Get range to use as well as bin limits
1810 // Projected range must be inside and not outside original one (ROOT-8781)
1811 Int_t ixmin = std::max(projX->GetFirst(),1);
1812 Int_t ixmax = std::min(projX->GetLast(),projX->GetNbins());
1813 Int_t nx = ixmax-ixmin+1;
1814
1815 // Create the histogram, either reseting a preexisting one
1816 TObject *h1obj = gROOT->FindObject(name);
1817 if (h1obj && h1obj->InheritsFrom(TH1::Class())) {
1818 if (h1obj->IsA() != TH1D::Class() ) {
1819 Error("DoProject1D","Histogram with name %s must be a TH1D and is a %s",name,h1obj->ClassName());
1820 return 0;
1821 }
1822 h1 = (TH1D*)h1obj;
1823 // reset histogram and re-set the axis in any case
1824 h1->Reset();
1825 const TArrayD *bins = projX->GetXbins();
1826 if ( originalRange )
1827 {
1828 if (bins->fN == 0) {
1829 h1->SetBins(projX->GetNbins(),projX->GetXmin(),projX->GetXmax());
1830 } else {
1831 h1->SetBins(projX->GetNbins(),bins->fArray);
1832 }
1833 } else {
1834 if (bins->fN == 0) {
1835 h1->SetBins(nx,projX->GetBinLowEdge(ixmin),projX->GetBinUpEdge(ixmax));
1836 } else {
1837 h1->SetBins(nx,&bins->fArray[ixmin-1]);
1838 }
1839 }
1840 }
1841
1842 if (!h1) {
1843 const TArrayD *bins = projX->GetXbins();
1844 if ( originalRange )
1845 {
1846 if (bins->fN == 0) {
1847 h1 = new TH1D(name,title,projX->GetNbins(),projX->GetXmin(),projX->GetXmax());
1848 } else {
1849 h1 = new TH1D(name,title,projX->GetNbins(),bins->fArray);
1850 }
1851 } else {
1852 if (bins->fN == 0) {
1853 h1 = new TH1D(name,title,nx,projX->GetBinLowEdge(ixmin),projX->GetBinUpEdge(ixmax));
1854 } else {
1855 h1 = new TH1D(name,title,nx,&bins->fArray[ixmin-1]);
1856 }
1857 }
1858 }
1859
1860 // Copy the axis attributes and the axis labels if needed.
1861 h1->GetXaxis()->ImportAttributes(projX);
1862 THashList* labels = projX->GetLabels();
1863 if (labels) {
1864 TIter iL(labels);
1865 TObjString* lb;
1866 Int_t i = 1;
1867 while ((lb=(TObjString*)iL())) {
1868 h1->GetXaxis()->SetBinLabel(i,lb->String().Data());
1869 i++;
1870 }
1871 }
1872 h1->SetLineColor(this->GetLineColor());
1873 h1->SetFillColor(this->GetFillColor());
1874 h1->SetMarkerColor(this->GetMarkerColor());
1875 h1->SetMarkerStyle(this->GetMarkerStyle());
1876
1877 // Activate errors
1878 if ( computeErrors && (h1->GetSumw2N() != h1->GetNcells() ) ) h1->Sumw2();
1879
1880 // Set references to the axies in case out1 or out2 ar enot provided
1881 // and one can use the histogram axis given projX
1882 if (out1 == nullptr && out2 == nullptr) {
1883 if (projX == GetXaxis()) {
1884 out1 = GetYaxis();
1885 out2 = GetZaxis();
1886 } else if (projX == GetYaxis()) {
1887 out1 = GetXaxis();
1888 out2 = GetZaxis();
1889 } else {
1890 out1 = GetXaxis();
1891 out2 = GetYaxis();
1892 }
1893 }
1894 R__ASSERT(out1 != nullptr && out2 != nullptr);
1895
1896 Int_t *refX = 0, *refY = 0, *refZ = 0;
1897 Int_t ixbin, out1bin, out2bin;
1898 if (projX == GetXaxis()) {
1899 refX = &ixbin;
1900 refY = &out1bin;
1901 refZ = &out2bin;
1902 }
1903 if (projX == GetYaxis()) {
1904 refX = &out1bin;
1905 refY = &ixbin;
1906 refZ = &out2bin;
1907 }
1908 if (projX == GetZaxis()) {
1909 refX = &out1bin;
1910 refY = &out2bin;
1911 refZ = &ixbin;
1912 }
1913 R__ASSERT (refX != 0 && refY != 0 && refZ != 0);
1914
1915 // Fill the projected histogram excluding underflow/overflows if considered in the option
1916 // if specified in the option (by default they considered)
1917 Double_t totcont = 0;
1918
1919 Int_t out1min = out1->GetFirst();
1920 Int_t out1max = out1->GetLast();
1921 // GetFirst(), GetLast() can return (0,0) when the range bit is set artificially (see TAxis::SetRange)
1922 //if (out1min == 0 && out1max == 0) { out1min = 1; out1max = out1->GetNbins(); }
1923 // correct for underflow/overflows
1924 if (useUF && !out1->TestBit(TAxis::kAxisRange) ) out1min -= 1;
1925 if (useOF && !out1->TestBit(TAxis::kAxisRange) ) out1max += 1;
1926 Int_t out2min = out2->GetFirst();
1927 Int_t out2max = out2->GetLast();
1928// if (out2min == 0 && out2max == 0) { out2min = 1; out2max = out2->GetNbins(); }
1929 if (useUF && !out2->TestBit(TAxis::kAxisRange) ) out2min -= 1;
1930 if (useOF && !out2->TestBit(TAxis::kAxisRange) ) out2max += 1;
1931
1932 for (ixbin=0;ixbin<=1+projX->GetNbins();ixbin++) {
1933 if ( projX->TestBit(TAxis::kAxisRange) && ( ixbin < ixmin || ixbin > ixmax )) continue;
1934
1935 Double_t cont = 0;
1936 Double_t err2 = 0;
1937
1938 // loop on the bins to be integrated (outbin should be called inbin)
1939 for (out1bin = out1min; out1bin <= out1max; out1bin++) {
1940 for (out2bin = out2min; out2bin <= out2max; out2bin++) {
1941
1942 Int_t bin = GetBin(*refX, *refY, *refZ);
1943
1944 // sum the bin contents and errors if needed
1945 cont += RetrieveBinContent(bin);
1946 if (computeErrors) {
1947 Double_t exyz = GetBinError(bin);
1948 err2 += exyz*exyz;
1949 }
1950 }
1951 }
1952 Int_t ix = h1->FindBin( projX->GetBinCenter(ixbin) );
1953 h1->SetBinContent(ix ,cont);
1954 if (computeErrors) h1->SetBinError(ix, TMath::Sqrt(err2) );
1955 // sum all content
1956 totcont += cont;
1957
1958 }
1959
1960 // since we use a combination of fill and SetBinError we need to reset and recalculate the statistics
1961 // for weighted histograms otherwise sumw2 will be wrong.
1962 // We can keep the original statistics from the TH3 if the projected sumw is consistent with original one
1963 // i.e. when no events are thrown away
1964 bool resetStats = true;
1965 double eps = 1.E-12;
1966 if (IsA() == TH3F::Class() ) eps = 1.E-6;
1967 if (fTsumw != 0 && TMath::Abs( fTsumw - totcont) < TMath::Abs(fTsumw) * eps) resetStats = false;
1968
1969 bool resetEntries = resetStats;
1970 // entries are calculated using underflow/overflow. If excluded entries must be reset
1971 resetEntries |= !useUF || !useOF;
1972
1973
1974 if (!resetStats) {
1975 Double_t stats[kNstat];
1976 GetStats(stats);
1977 if ( projX == GetYaxis() ) {
1978 stats[2] = stats[4];
1979 stats[3] = stats[5];
1980 }
1981 else if ( projX == GetZaxis() ) {
1982 stats[2] = stats[7];
1983 stats[3] = stats[8];
1984 }
1985 h1->PutStats(stats);
1986 }
1987 else {
1988 // reset statistics
1989 h1->ResetStats();
1990 }
1991 if (resetEntries) {
1992 // in case of error calculation (i.e. when Sumw2() is set)
1993 // use the effective entries for the entries
1994 // since this is the only way to estimate them
1995 Double_t entries = TMath::Floor( totcont + 0.5); // to avoid numerical rounding
1996 if (computeErrors) entries = h1->GetEffectiveEntries();
1997 h1->SetEntries( entries );
1998 }
1999 else {
2001 }
2002
2003 return h1;
2004}
2005
2006
2007////////////////////////////////////////////////////////////////////////////////
2008/// internal method performing the projection to a 2D histogram
2009/// called from TH3::Project3D
2010
2011TH2D *TH3::DoProject2D(const char* name, const char * title, const TAxis* projX, const TAxis* projY,
2012 bool computeErrors, bool originalRange,
2013 bool useUF, bool useOF) const
2014{
2015 TH2D *h2 = 0;
2016
2017 // Get range to use as well as bin limits
2018 Int_t ixmin = std::max(projX->GetFirst(),1);
2019 Int_t ixmax = std::min(projX->GetLast(),projX->GetNbins());
2020 Int_t iymin = std::max(projY->GetFirst(),1);
2021 Int_t iymax = std::min(projY->GetLast(),projY->GetNbins());
2022
2023 Int_t nx = ixmax-ixmin+1;
2024 Int_t ny = iymax-iymin+1;
2025
2026 // Create the histogram, either reseting a preexisting one
2027 // or creating one from scratch.
2028 // Does an object with the same name exists?
2029 TObject *h2obj = gROOT->FindObject(name);
2030 if (h2obj && h2obj->InheritsFrom(TH1::Class())) {
2031 if ( h2obj->IsA() != TH2D::Class() ) {
2032 Error("DoProject2D","Histogram with name %s must be a TH2D and is a %s",name,h2obj->ClassName());
2033 return 0;
2034 }
2035 h2 = (TH2D*)h2obj;
2036 // reset histogram and its axes
2037 h2->Reset();
2038 const TArrayD *xbins = projX->GetXbins();
2039 const TArrayD *ybins = projY->GetXbins();
2040 if ( originalRange ) {
2041 h2->SetBins(projY->GetNbins(),projY->GetXmin(),projY->GetXmax()
2042 ,projX->GetNbins(),projX->GetXmin(),projX->GetXmax());
2043 // set bins for mixed axis do not exists - need to set afterwards the variable bins
2044 if (ybins->fN != 0)
2045 h2->GetXaxis()->Set(projY->GetNbins(),&ybins->fArray[iymin-1]);
2046 if (xbins->fN != 0)
2047 h2->GetYaxis()->Set(projX->GetNbins(),&xbins->fArray[ixmin-1]);
2048 } else {
2049 h2->SetBins(ny,projY->GetBinLowEdge(iymin),projY->GetBinUpEdge(iymax)
2050 ,nx,projX->GetBinLowEdge(ixmin),projX->GetBinUpEdge(ixmax));
2051 if (ybins->fN != 0)
2052 h2->GetXaxis()->Set(ny,&ybins->fArray[iymin-1]);
2053 if (xbins->fN != 0)
2054 h2->GetYaxis()->Set(nx,&xbins->fArray[ixmin-1]);
2055 }
2056 }
2057
2058
2059 if (!h2) {
2060 const TArrayD *xbins = projX->GetXbins();
2061 const TArrayD *ybins = projY->GetXbins();
2062 if ( originalRange )
2063 {
2064 if (xbins->fN == 0 && ybins->fN == 0) {
2065 h2 = new TH2D(name,title,projY->GetNbins(),projY->GetXmin(),projY->GetXmax()
2066 ,projX->GetNbins(),projX->GetXmin(),projX->GetXmax());
2067 } else if (ybins->fN == 0) {
2068 h2 = new TH2D(name,title,projY->GetNbins(),projY->GetXmin(),projY->GetXmax()
2069 ,projX->GetNbins(),&xbins->fArray[ixmin-1]);
2070 } else if (xbins->fN == 0) {
2071 h2 = new TH2D(name,title,projY->GetNbins(),&ybins->fArray[iymin-1]
2072 ,projX->GetNbins(),projX->GetXmin(),projX->GetXmax());
2073 } else {
2074 h2 = new TH2D(name,title,projY->GetNbins(),&ybins->fArray[iymin-1],projX->GetNbins(),&xbins->fArray[ixmin-1]);
2075 }
2076 } else {
2077 if (xbins->fN == 0 && ybins->fN == 0) {
2078 h2 = new TH2D(name,title,ny,projY->GetBinLowEdge(iymin),projY->GetBinUpEdge(iymax)
2079 ,nx,projX->GetBinLowEdge(ixmin),projX->GetBinUpEdge(ixmax));
2080 } else if (ybins->fN == 0) {
2081 h2 = new TH2D(name,title,ny,projY->GetBinLowEdge(iymin),projY->GetBinUpEdge(iymax)
2082 ,nx,&xbins->fArray[ixmin-1]);
2083 } else if (xbins->fN == 0) {
2084 h2 = new TH2D(name,title,ny,&ybins->fArray[iymin-1]
2085 ,nx,projX->GetBinLowEdge(ixmin),projX->GetBinUpEdge(ixmax));
2086 } else {
2087 h2 = new TH2D(name,title,ny,&ybins->fArray[iymin-1],nx,&xbins->fArray[ixmin-1]);
2088 }
2089 }
2090 }
2091
2092 // Copy the axis attributes and the axis labels if needed.
2093 THashList* labels1 = 0;
2094 THashList* labels2 = 0;
2095 // "xy"
2096 h2->GetXaxis()->ImportAttributes(projY);
2097 h2->GetYaxis()->ImportAttributes(projX);
2098 labels1 = projY->GetLabels();
2099 labels2 = projX->GetLabels();
2100 if (labels1) {
2101 TIter iL(labels1);
2102 TObjString* lb;
2103 Int_t i = 1;
2104 while ((lb=(TObjString*)iL())) {
2105 h2->GetXaxis()->SetBinLabel(i,lb->String().Data());
2106 i++;
2107 }
2108 }
2109 if (labels2) {
2110 TIter iL(labels2);
2111 TObjString* lb;
2112 Int_t i = 1;
2113 while ((lb=(TObjString*)iL())) {
2114 h2->GetYaxis()->SetBinLabel(i,lb->String().Data());
2115 i++;
2116 }
2117 }
2118 h2->SetLineColor(this->GetLineColor());
2119 h2->SetFillColor(this->GetFillColor());
2120 h2->SetMarkerColor(this->GetMarkerColor());
2121 h2->SetMarkerStyle(this->GetMarkerStyle());
2122
2123 // Activate errors
2124 if ( computeErrors && (h2->GetSumw2N() != h2->GetNcells()) ) h2->Sumw2();
2125
2126 // Set references to the axis, so that the bucle has no branches.
2127 const TAxis* out = 0;
2128 if ( projX != GetXaxis() && projY != GetXaxis() ) {
2129 out = GetXaxis();
2130 } else if ( projX != GetYaxis() && projY != GetYaxis() ) {
2131 out = GetYaxis();
2132 } else {
2133 out = GetZaxis();
2134 }
2135
2136 Int_t *refX = 0, *refY = 0, *refZ = 0;
2137 Int_t ixbin, iybin, outbin;
2138 if ( projX == GetXaxis() && projY == GetYaxis() ) { refX = &ixbin; refY = &iybin; refZ = &outbin; }
2139 if ( projX == GetYaxis() && projY == GetXaxis() ) { refX = &iybin; refY = &ixbin; refZ = &outbin; }
2140 if ( projX == GetXaxis() && projY == GetZaxis() ) { refX = &ixbin; refY = &outbin; refZ = &iybin; }
2141 if ( projX == GetZaxis() && projY == GetXaxis() ) { refX = &iybin; refY = &outbin; refZ = &ixbin; }
2142 if ( projX == GetYaxis() && projY == GetZaxis() ) { refX = &outbin; refY = &ixbin; refZ = &iybin; }
2143 if ( projX == GetZaxis() && projY == GetYaxis() ) { refX = &outbin; refY = &iybin; refZ = &ixbin; }
2144 R__ASSERT (refX != 0 && refY != 0 && refZ != 0);
2145
2146 // Fill the projected histogram excluding underflow/overflows if considered in the option
2147 // if specified in the option (by default they considered)
2148 Double_t totcont = 0;
2149
2150 Int_t outmin = out->GetFirst();
2151 Int_t outmax = out->GetLast();
2152 // GetFirst(), GetLast() can return (0,0) when the range bit is set artificially (see TAxis::SetRange)
2153 if (outmin == 0 && outmax == 0) { outmin = 1; outmax = out->GetNbins(); }
2154 // correct for underflow/overflows
2155 if (useUF && !out->TestBit(TAxis::kAxisRange) ) outmin -= 1;
2156 if (useOF && !out->TestBit(TAxis::kAxisRange) ) outmax += 1;
2157
2158 for (ixbin=0;ixbin<=1+projX->GetNbins();ixbin++) {
2159 if ( projX->TestBit(TAxis::kAxisRange) && ( ixbin < ixmin || ixbin > ixmax )) continue;
2160 Int_t ix = h2->GetYaxis()->FindBin( projX->GetBinCenter(ixbin) );
2161
2162 for (iybin=0;iybin<=1+projY->GetNbins();iybin++) {
2163 if ( projY->TestBit(TAxis::kAxisRange) && ( iybin < iymin || iybin > iymax )) continue;
2164 Int_t iy = h2->GetXaxis()->FindBin( projY->GetBinCenter(iybin) );
2165
2166 Double_t cont = 0;
2167 Double_t err2 = 0;
2168
2169 // loop on the bins to be integrated (outbin should be called inbin)
2170 for (outbin = outmin; outbin <= outmax; outbin++) {
2171
2172 Int_t bin = GetBin(*refX,*refY,*refZ);
2173
2174 // sum the bin contents and errors if needed
2175 cont += RetrieveBinContent(bin);
2176 if (computeErrors) {
2177 Double_t exyz = GetBinError(bin);
2178 err2 += exyz*exyz;
2179 }
2180
2181 }
2182
2183 // remember axis are inverted
2184 h2->SetBinContent(iy , ix, cont);
2185 if (computeErrors) h2->SetBinError(iy, ix, TMath::Sqrt(err2) );
2186 // sum all content
2187 totcont += cont;
2188
2189 }
2190 }
2191
2192 // since we use fill we need to reset and recalculate the statistics (see comment in DoProject1D )
2193 // or keep original statistics if consistent sumw2
2194 bool resetStats = true;
2195 double eps = 1.E-12;
2196 if (IsA() == TH3F::Class() ) eps = 1.E-6;
2197 if (fTsumw != 0 && TMath::Abs( fTsumw - totcont) < TMath::Abs(fTsumw) * eps) resetStats = false;
2198
2199 bool resetEntries = resetStats;
2200 // entries are calculated using underflow/overflow. If excluded entries must be reset
2201 resetEntries |= !useUF || !useOF;
2202
2203 if (!resetStats) {
2204 Double_t stats[kNstat];
2205 Double_t oldst[kNstat]; // old statistics
2206 for (Int_t i = 0; i < kNstat; ++i) { oldst[i] = 0; }
2207 GetStats(oldst);
2208 std::copy(oldst,oldst+kNstat,stats);
2209 // not that projX refer to Y axis and projX refer to the X axis of projected histogram
2210 // nothing to do for projection in Y vs X
2211 if ( projY == GetXaxis() && projX == GetZaxis() ) { // case XZ
2212 stats[4] = oldst[7];
2213 stats[5] = oldst[8];
2214 stats[6] = oldst[9];
2215 }
2216 if ( projY == GetYaxis() ) {
2217 stats[2] = oldst[4];
2218 stats[3] = oldst[5];
2219 if ( projX == GetXaxis() ) { // case YX
2220 stats[4] = oldst[2];
2221 stats[5] = oldst[3];
2222 }
2223 if ( projX == GetZaxis() ) { // case YZ
2224 stats[4] = oldst[7];
2225 stats[5] = oldst[8];
2226 stats[6] = oldst[10];
2227 }
2228 }
2229 else if ( projY == GetZaxis() ) {
2230 stats[2] = oldst[7];
2231 stats[3] = oldst[8];
2232 if ( projX == GetXaxis() ) { // case ZX
2233 stats[4] = oldst[2];
2234 stats[5] = oldst[3];
2235 stats[6] = oldst[9];
2236 }
2237 if ( projX == GetYaxis() ) { // case ZY
2238 stats[4] = oldst[4];
2239 stats[5] = oldst[5];
2240 stats[6] = oldst[10];
2241 }
2242 }
2243 // set the new statistics
2244 h2->PutStats(stats);
2245 }
2246 else {
2247 // recalculate the statistics
2248 h2->ResetStats();
2249 }
2250
2251 if (resetEntries) {
2252 // use the effective entries for the entries
2253 // since this is the only way to estimate them
2254 Double_t entries = h2->GetEffectiveEntries();
2255 if (!computeErrors) entries = TMath::Floor( entries + 0.5); // to avoid numerical rounding
2256 h2->SetEntries( entries );
2257 }
2258 else {
2259 h2->SetEntries( fEntries );
2260 }
2261
2262
2263 return h2;
2264}
2265
2266
2267////////////////////////////////////////////////////////////////////////////////
2268/// Project a 3-d histogram into 1 or 2-d histograms depending on the
2269/// option parameter, which may contain a combination of the characters x,y,z,e
2270/// - option = "x" return the x projection into a TH1D histogram
2271/// - option = "y" return the y projection into a TH1D histogram
2272/// - option = "z" return the z projection into a TH1D histogram
2273/// - option = "xy" return the x versus y projection into a TH2D histogram
2274/// - option = "yx" return the y versus x projection into a TH2D histogram
2275/// - option = "xz" return the x versus z projection into a TH2D histogram
2276/// - option = "zx" return the z versus x projection into a TH2D histogram
2277/// - option = "yz" return the y versus z projection into a TH2D histogram
2278/// - option = "zy" return the z versus y projection into a TH2D histogram
2279///
2280/// NB: the notation "a vs b" means "a" vertical and "b" horizontal
2281///
2282/// option = "o" original axis range of the target axes will be
2283/// kept, but only bins inside the selected range will be filled.
2284///
2285/// If option contains the string "e", errors are computed
2286///
2287/// The projection is made for the selected bins only.
2288/// To select a bin range along an axis, use TAxis::SetRange, eg
2289/// h3.GetYaxis()->SetRange(23,56);
2290///
2291/// NOTE 1: The generated histogram is named th3name + option
2292/// eg if the TH3* h histogram is named "myhist", then
2293/// h->Project3D("xy"); produces a TH2D histogram named "myhist_xy"
2294/// if a histogram of the same type already exists, it is overwritten.
2295/// The following sequence
2296/// h->Project3D("xy");
2297/// h->Project3D("xy2");
2298/// will generate two TH2D histograms named "myhist_xy" and "myhist_xy2"
2299/// A different name can be generated by attaching a string to the option
2300/// For example h->Project3D("name_xy") will generate an histogram with the name: h3dname_name_xy.
2301///
2302/// NOTE 2: If an histogram of the same type already exists,
2303/// the histogram is reset and filled again with the projected contents of the TH3.
2304///
2305/// NOTE 3: The number of entries in the projected histogram is estimated from the number of
2306/// effective entries for all the cells included in the projection.
2307///
2308/// NOTE 4: underflow/overflow are included by default in the projection
2309/// To exclude underflow and/or overflow (for both axis in case of a projection to a 1D histogram) use option "NUF" and/or "NOF"
2310/// With SetRange() you can have all bins except underflow/overflow only if you set the axis bit range as
2311/// following after having called SetRange: axis->SetRange(1, axis->GetNbins());
2312
2314{
2315 TString opt = option; opt.ToLower();
2316 Int_t pcase = 0;
2317 TString ptype;
2318 if (opt.Contains("x")) { pcase = 1; ptype = "x"; }
2319 if (opt.Contains("y")) { pcase = 2; ptype = "y"; }
2320 if (opt.Contains("z")) { pcase = 3; ptype = "z"; }
2321 if (opt.Contains("xy")) { pcase = 4; ptype = "xy"; }
2322 if (opt.Contains("yx")) { pcase = 5; ptype = "yx"; }
2323 if (opt.Contains("xz")) { pcase = 6; ptype = "xz"; }
2324 if (opt.Contains("zx")) { pcase = 7; ptype = "zx"; }
2325 if (opt.Contains("yz")) { pcase = 8; ptype = "yz"; }
2326 if (opt.Contains("zy")) { pcase = 9; ptype = "zy"; }
2327
2328 if (pcase == 0) {
2329 Error("Project3D","No projection axis specified - return a NULL pointer");
2330 return 0;
2331 }
2332 // do not remove ptype from opt to use later in the projected histo name
2333
2334 Bool_t computeErrors = GetSumw2N();
2335 if (opt.Contains("e") ) {
2336 computeErrors = kTRUE;
2337 opt.Remove(opt.First("e"),1);
2338 }
2339
2340 Bool_t useUF = kTRUE;
2341 Bool_t useOF = kTRUE;
2342 if (opt.Contains("nuf") ) {
2343 useUF = kFALSE;
2344 opt.Remove(opt.Index("nuf"),3);
2345 }
2346 if (opt.Contains("nof") ) {
2347 useOF = kFALSE;
2348 opt.Remove(opt.Index("nof"),3);
2349 }
2350
2351 Bool_t originalRange = kFALSE;
2352 if (opt.Contains('o') ) {
2353 originalRange = kTRUE;
2354 opt.Remove(opt.First("o"),1);
2355 }
2356
2357
2358 // Create the projection histogram
2359 TH1 *h = 0;
2360
2361 TString name = GetName();
2362 TString title = GetTitle();
2363 name += "_"; name += opt; // opt may include a user defined name
2364 title += " "; title += ptype; title += " projection";
2365
2366 switch (pcase) {
2367 case 1:
2368 // "x"
2369 h = DoProject1D(name, title, this->GetXaxis(), nullptr, nullptr,
2370 computeErrors, originalRange, useUF, useOF);
2371 break;
2372
2373 case 2:
2374 // "y"
2375 h = DoProject1D(name, title, this->GetYaxis(), nullptr, nullptr,
2376 computeErrors, originalRange, useUF, useOF);
2377 break;
2378
2379 case 3:
2380 // "z"
2381 h = DoProject1D(name, title, this->GetZaxis(), nullptr, nullptr,
2382 computeErrors, originalRange, useUF, useOF);
2383 break;
2384
2385 case 4:
2386 // "xy"
2387 h = DoProject2D(name, title, this->GetXaxis(),this->GetYaxis(),
2388 computeErrors, originalRange, useUF, useOF);
2389 break;
2390
2391 case 5:
2392 // "yx"
2393 h = DoProject2D(name, title, this->GetYaxis(),this->GetXaxis(),
2394 computeErrors, originalRange, useUF, useOF);
2395 break;
2396
2397 case 6:
2398 // "xz"
2399 h = DoProject2D(name, title, this->GetXaxis(),this->GetZaxis(),
2400 computeErrors, originalRange, useUF, useOF);
2401 break;
2402
2403 case 7:
2404 // "zx"
2405 h = DoProject2D(name, title, this->GetZaxis(),this->GetXaxis(),
2406 computeErrors, originalRange, useUF, useOF);
2407 break;
2408
2409 case 8:
2410 // "yz"
2411 h = DoProject2D(name, title, this->GetYaxis(),this->GetZaxis(),
2412 computeErrors, originalRange, useUF, useOF);
2413 break;
2414
2415 case 9:
2416 // "zy"
2417 h = DoProject2D(name, title, this->GetZaxis(),this->GetYaxis(),
2418 computeErrors, originalRange, useUF, useOF);
2419 break;
2420
2421 }
2422
2423 // draw in current pad
2424 if (h && opt.Contains("d")) {
2425 opt.Remove(opt.First("d"),1);
2426 TVirtualPad *padsav = gPad;
2428 if (pad) pad->cd();
2429 if (!gPad || !gPad->FindObject(h)) {
2430 h->Draw(opt);
2431 } else {
2432 h->Paint(opt);
2433 }
2434 if (padsav) padsav->cd();
2435 }
2436
2437 return h;
2438}
2439
2440
2441////////////////////////////////////////////////////////////////////////////////
2442/// internal function to fill the bins of the projected profile 2D histogram
2443/// called from DoProjectProfile2D
2444
2446 const TAxis & a1, const TAxis & a2, const TAxis & a3,
2447 Int_t bin1, Int_t bin2, Int_t bin3,
2448 Int_t inBin, Bool_t useWeights ) const {
2449 Double_t cont = GetBinContent(inBin);
2450 if (!cont) return;
2451 TArrayD & binSumw2 = *(p2->GetBinSumw2());
2452 if (useWeights && binSumw2.fN <= 0) useWeights = false;
2453 if (!useWeights) p2->SetBit(TH1::kIsNotW); // to use Fill for setting the bin contents of the Profile
2454 // the following fill update wrongly the fBinSumw2- need to save it before
2455 Double_t u = a1.GetBinCenter(bin1);
2456 Double_t v = a2.GetBinCenter(bin2);
2457 Double_t w = a3.GetBinCenter(bin3);
2458 Int_t outBin = p2->FindBin(u, v);
2459 if (outBin <0) return;
2460 Double_t tmp = 0;
2461 if ( useWeights ) tmp = binSumw2.fArray[outBin];
2462 p2->Fill( u , v, w, cont);
2463 if (useWeights ) binSumw2.fArray[outBin] = tmp + fSumw2.fArray[inBin];
2464}
2465
2466
2467////////////////////////////////////////////////////////////////////////////////
2468/// internal method to project to a 2D Profile
2469/// called from TH3::Project3DProfile
2470
2471TProfile2D *TH3::DoProjectProfile2D(const char* name, const char * title, const TAxis* projX, const TAxis* projY,
2472 bool originalRange, bool useUF, bool useOF) const
2473{
2474 // Get the ranges where we will work.
2475 Int_t ixmin = std::max(projX->GetFirst(),1);
2476 Int_t ixmax = std::min(projX->GetLast(),projX->GetNbins());
2477 Int_t iymin = std::max(projY->GetFirst(),1);
2478 Int_t iymax = std::min(projY->GetLast(),projY->GetNbins());
2479
2480 Int_t nx = ixmax-ixmin+1;
2481 Int_t ny = iymax-iymin+1;
2482
2483 // Create the projected profiles
2484 TProfile2D *p2 = 0;
2485
2486 // Create the histogram, either reseting a preexisting one
2487 // Does an object with the same name exists?
2488 TObject *p2obj = gROOT->FindObject(name);
2489 if (p2obj && p2obj->InheritsFrom(TH1::Class())) {
2490 if (p2obj->IsA() != TProfile2D::Class() ) {
2491 Error("DoProjectProfile2D","Histogram with name %s must be a TProfile2D and is a %s",name,p2obj->ClassName());
2492 return 0;
2493 }
2494 p2 = (TProfile2D*)p2obj;
2495 // reset existing profile and re-set bins
2496 p2->Reset();
2497 const TArrayD *xbins = projX->GetXbins();
2498 const TArrayD *ybins = projY->GetXbins();
2499 if ( originalRange ) {
2500 p2->SetBins(projY->GetNbins(),projY->GetXmin(),projY->GetXmax()
2501 ,projX->GetNbins(),projX->GetXmin(),projX->GetXmax());
2502 // set bins for mixed axis do not exists - need to set afterwards the variable bins
2503 if (ybins->fN != 0)
2504 p2->GetXaxis()->Set(projY->GetNbins(),&ybins->fArray[iymin-1]);
2505 if (xbins->fN != 0)
2506 p2->GetYaxis()->Set(projX->GetNbins(),&xbins->fArray[ixmin-1]);
2507 } else {
2508 p2->SetBins(ny,projY->GetBinLowEdge(iymin),projY->GetBinUpEdge(iymax)
2509 ,nx,projX->GetBinLowEdge(ixmin),projX->GetBinUpEdge(ixmax));
2510 if (ybins->fN != 0)
2511 p2->GetXaxis()->Set(ny,&ybins->fArray[iymin-1]);
2512 if (xbins->fN != 0)
2513 p2->GetYaxis()->Set(nx,&xbins->fArray[ixmin-1]);
2514 }
2515 }
2516
2517 if (!p2) {
2518 const TArrayD *xbins = projX->GetXbins();
2519 const TArrayD *ybins = projY->GetXbins();
2520 if ( originalRange ) {
2521 if (xbins->fN == 0 && ybins->fN == 0) {
2522 p2 = new TProfile2D(name,title,projY->GetNbins(),projY->GetXmin(),projY->GetXmax()
2523 ,projX->GetNbins(),projX->GetXmin(),projX->GetXmax());
2524 } else if (ybins->fN == 0) {
2525 p2 = new TProfile2D(name,title,projY->GetNbins(),projY->GetXmin(),projY->GetXmax()
2526 ,projX->GetNbins(),&xbins->fArray[ixmin-1]);
2527 } else if (xbins->fN == 0) {
2528 p2 = new TProfile2D(name,title,projY->GetNbins(),&ybins->fArray[iymin-1]
2529 ,projX->GetNbins(),projX->GetXmin(),projX->GetXmax());
2530 } else {
2531 p2 = new TProfile2D(name,title,projY->GetNbins(),&ybins->fArray[iymin-1],projX->GetNbins(),&xbins->fArray[ixmin-1]);
2532 }
2533 } else {
2534 if (xbins->fN == 0 && ybins->fN == 0) {
2535 p2 = new TProfile2D(name,title,ny,projY->GetBinLowEdge(iymin),projY->GetBinUpEdge(iymax)
2536 ,nx,projX->GetBinLowEdge(ixmin),projX->GetBinUpEdge(ixmax));
2537 } else if (ybins->fN == 0) {
2538 p2 = new TProfile2D(name,title,ny,projY->GetBinLowEdge(iymin),projY->GetBinUpEdge(iymax)
2539 ,nx,&xbins->fArray[ixmin-1]);
2540 } else if (xbins->fN == 0) {
2541 p2 = new TProfile2D(name,title,ny,&ybins->fArray[iymin-1]
2542 ,nx,projX->GetBinLowEdge(ixmin),projX->GetBinUpEdge(ixmax));
2543 } else {
2544 p2 = new TProfile2D(name,title,ny,&ybins->fArray[iymin-1],nx,&xbins->fArray[ixmin-1]);
2545 }
2546 }
2547 }
2548
2549 // Set references to the axis, so that the loop has no branches.
2550 const TAxis* outAxis = 0;
2551 if ( projX != GetXaxis() && projY != GetXaxis() ) {
2552 outAxis = GetXaxis();
2553 } else if ( projX != GetYaxis() && projY != GetYaxis() ) {
2554 outAxis = GetYaxis();
2555 } else {
2556 outAxis = GetZaxis();
2557 }
2558
2559 // Weights management
2560 bool useWeights = (GetSumw2N() > 0);
2561 // store sum of w2 in profile if histo is weighted
2562 if (useWeights && (p2->GetBinSumw2()->fN != p2->GetNcells() ) ) p2->Sumw2();
2563
2564 // Set references to the bins, so that the loop has no branches.
2565 Int_t *refX = 0, *refY = 0, *refZ = 0;
2566 Int_t ixbin, iybin, outbin;
2567 if ( projX == GetXaxis() && projY == GetYaxis() ) { refX = &ixbin; refY = &iybin; refZ = &outbin; }
2568 if ( projX == GetYaxis() && projY == GetXaxis() ) { refX = &iybin; refY = &ixbin; refZ = &outbin; }
2569 if ( projX == GetXaxis() && projY == GetZaxis() ) { refX = &ixbin; refY = &outbin; refZ = &iybin; }
2570 if ( projX == GetZaxis() && projY == GetXaxis() ) { refX = &iybin; refY = &outbin; refZ = &ixbin; }
2571 if ( projX == GetYaxis() && projY == GetZaxis() ) { refX = &outbin; refY = &ixbin; refZ = &iybin; }
2572 if ( projX == GetZaxis() && projY == GetYaxis() ) { refX = &outbin; refY = &iybin; refZ = &ixbin; }
2573 R__ASSERT (refX != 0 && refY != 0 && refZ != 0);
2574
2575 Int_t outmin = outAxis->GetFirst();
2576 Int_t outmax = outAxis->GetLast();
2577 // GetFirst, GetLast can return underflow or overflow bins
2578 // correct for underflow/overflows
2579 if (useUF && !outAxis->TestBit(TAxis::kAxisRange) ) outmin -= 1;
2580 if (useOF && !outAxis->TestBit(TAxis::kAxisRange) ) outmax += 1;
2581
2582 TArrayD & binSumw2 = *(p2->GetBinSumw2());
2583 if (useWeights && binSumw2.fN <= 0) useWeights = false;
2584 if (!useWeights) p2->SetBit(TH1::kIsNotW);
2585
2586 // Call specific method for the projection
2587 for (ixbin=0;ixbin<=1+projX->GetNbins();ixbin++) {
2588 if ( (ixbin < ixmin || ixbin > ixmax) && projX->TestBit(TAxis::kAxisRange)) continue;
2589 for ( iybin=0;iybin<=1+projY->GetNbins();iybin++) {
2590 if ( (iybin < iymin || iybin > iymax) && projX->TestBit(TAxis::kAxisRange)) continue;
2591
2592 // profile output bin
2593 Int_t poutBin = p2->FindBin(projY->GetBinCenter(iybin), projX->GetBinCenter(ixbin));
2594 if (poutBin <0) continue;
2595 // loop on the bins to be integrated (outbin should be called inbin)
2596 for (outbin = outmin; outbin <= outmax; outbin++) {
2597
2598 Int_t bin = GetBin(*refX,*refY,*refZ);
2599
2600 //DoFillProfileProjection(p2, *projY, *projX, *outAxis, iybin, ixbin, outbin, bin, useWeights);
2601
2602 Double_t cont = RetrieveBinContent(bin);
2603 if (!cont) continue;
2604
2605 Double_t tmp = 0;
2606 // the following fill update wrongly the fBinSumw2- need to save it before
2607 if ( useWeights ) tmp = binSumw2.fArray[poutBin];
2608 p2->Fill( projY->GetBinCenter(iybin) , projX->GetBinCenter(ixbin), outAxis->GetBinCenter(outbin), cont);
2609 if (useWeights ) binSumw2.fArray[poutBin] = tmp + fSumw2.fArray[bin];
2610
2611 }
2612 }
2613 }
2614
2615 // recompute statistics for the projected profiles
2616 // forget about preserving old statistics
2617 bool resetStats = true;
2618 Double_t stats[kNstat];
2619 // reset statistics
2620 if (resetStats)
2621 for (Int_t i=0;i<kNstat;i++) stats[i] = 0;
2622
2623 p2->PutStats(stats);
2624 Double_t entries = fEntries;
2625 // recalculate the statistics
2626 if (resetStats) {
2627 entries = p2->GetEffectiveEntries();
2628 if (!useWeights) entries = TMath::Floor( entries + 0.5); // to avoid numerical rounding
2629 p2->SetEntries( entries );
2630 }
2631
2632 p2->SetEntries(entries);
2633
2634 return p2;
2635}
2636
2637
2638////////////////////////////////////////////////////////////////////////////////
2639/// Project a 3-d histogram into a 2-d profile histograms depending
2640/// on the option parameter
2641/// option may contain a combination of the characters x,y,z
2642/// option = "xy" return the x versus y projection into a TProfile2D histogram
2643/// option = "yx" return the y versus x projection into a TProfile2D histogram
2644/// option = "xz" return the x versus z projection into a TProfile2D histogram
2645/// option = "zx" return the z versus x projection into a TProfile2D histogram
2646/// option = "yz" return the y versus z projection into a TProfile2D histogram
2647/// option = "zy" return the z versus y projection into a TProfile2D histogram
2648/// NB: the notation "a vs b" means "a" vertical and "b" horizontal
2649///
2650/// option = "o" original axis range of the target axes will be
2651/// kept, but only bins inside the selected range will be filled.
2652///
2653/// The projection is made for the selected bins only.
2654/// To select a bin range along an axis, use TAxis::SetRange, eg
2655/// h3.GetYaxis()->SetRange(23,56);
2656///
2657/// NOTE 1: The generated histogram is named th3name + "_p" + option
2658/// eg if the TH3* h histogram is named "myhist", then
2659/// h->Project3D("xy"); produces a TProfile2D histogram named "myhist_pxy".
2660/// The following sequence
2661/// h->Project3DProfile("xy");
2662/// h->Project3DProfile("xy2");
2663/// will generate two TProfile2D histograms named "myhist_pxy" and "myhist_pxy2"
2664/// So, passing additional characters in the option string one can customize the name.
2665///
2666/// NOTE 2: If a profile of the same type already exists with compatible axes,
2667/// the profile is reset and filled again with the projected contents of the TH3.
2668/// In the case of axes incompatibility, an error is reported and a NULL pointer is returned.
2669///
2670/// NOTE 3: The number of entries in the projected profile is estimated from the number of
2671/// effective entries for all the cells included in the projection.
2672///
2673/// NOTE 4: underflow/overflow are by default excluded from the projection
2674/// (Note that this is a different default behavior compared to the projection to an histogram)
2675/// To include the underflow and/or overflow use option "UF" and/or "OF"
2676
2678{
2679 TString opt = option; opt.ToLower();
2680 Int_t pcase = 0;
2681 TString ptype;
2682 if (opt.Contains("xy")) { pcase = 4; ptype = "xy"; }
2683 if (opt.Contains("yx")) { pcase = 5; ptype = "yx"; }
2684 if (opt.Contains("xz")) { pcase = 6; ptype = "xz"; }
2685 if (opt.Contains("zx")) { pcase = 7; ptype = "zx"; }
2686 if (opt.Contains("yz")) { pcase = 8; ptype = "yz"; }
2687 if (opt.Contains("zy")) { pcase = 9; ptype = "zy"; }
2688
2689 if (pcase == 0) {
2690 Error("Project3D","No projection axis specified - return a NULL pointer");
2691 return 0;
2692 }
2693 // do not remove ptype from opt to use later in the projected histo name
2694
2695 Bool_t useUF = kFALSE;
2696 if (opt.Contains("uf") ) {
2697 useUF = kTRUE;
2698 opt.Remove(opt.Index("uf"),2);
2699 }
2700 Bool_t useOF = kFALSE;
2701 if (opt.Contains("of") ) {
2702 useOF = kTRUE;
2703 opt.Remove(opt.Index("of"),2);
2704 }
2705
2706 Bool_t originalRange = kFALSE;
2707 if (opt.Contains('o') ) {
2708 originalRange = kTRUE;
2709 opt.Remove(opt.First("o"),1);
2710 }
2711
2712 // Create the projected profile
2713 TProfile2D *p2 = 0;
2714 TString name = GetName();
2715 TString title = GetTitle();
2716 name += "_p"; name += opt; // opt may include a user defined name
2717 title += " profile "; title += ptype; title += " projection";
2718
2719 // Call the method with the specific projected axes.
2720 switch (pcase) {
2721 case 4:
2722 // "xy"
2723 p2 = DoProjectProfile2D(name, title, GetXaxis(), GetYaxis(), originalRange, useUF, useOF);
2724 break;
2725
2726 case 5:
2727 // "yx"
2728 p2 = DoProjectProfile2D(name, title, GetYaxis(), GetXaxis(), originalRange, useUF, useOF);
2729 break;
2730
2731 case 6:
2732 // "xz"
2733 p2 = DoProjectProfile2D(name, title, GetXaxis(), GetZaxis(), originalRange, useUF, useOF);
2734 break;
2735
2736 case 7:
2737 // "zx"
2738 p2 = DoProjectProfile2D(name, title, GetZaxis(), GetXaxis(), originalRange, useUF, useOF);
2739 break;
2740
2741 case 8:
2742 // "yz"
2743 p2 = DoProjectProfile2D(name, title, GetYaxis(), GetZaxis(), originalRange, useUF, useOF);
2744 break;
2745
2746 case 9:
2747 // "zy"
2748 p2 = DoProjectProfile2D(name, title, GetZaxis(), GetYaxis(), originalRange, useUF, useOF);
2749 break;
2750
2751 }
2752
2753 return p2;
2754}
2755
2756
2757////////////////////////////////////////////////////////////////////////////////
2758/// Replace current statistics with the values in array stats
2759
2761{
2762 TH1::PutStats(stats);
2763 fTsumwy = stats[4];
2764 fTsumwy2 = stats[5];
2765 fTsumwxy = stats[6];
2766 fTsumwz = stats[7];
2767 fTsumwz2 = stats[8];
2768 fTsumwxz = stats[9];
2769 fTsumwyz = stats[10];
2770}
2771
2772
2773////////////////////////////////////////////////////////////////////////////////
2774/// Rebin only the X axis
2775/// see Rebin3D
2776
2777TH3 *TH3::RebinX(Int_t ngroup, const char *newname)
2778{
2779 return Rebin3D(ngroup, 1, 1, newname);
2780}
2781
2782
2783////////////////////////////////////////////////////////////////////////////////
2784/// Rebin only the Y axis
2785/// see Rebin3D
2786
2787TH3 *TH3::RebinY(Int_t ngroup, const char *newname)
2788{
2789 return Rebin3D(1, ngroup, 1, newname);
2790}
2791
2792
2793////////////////////////////////////////////////////////////////////////////////
2794/// Rebin only the Z axis
2795/// see Rebin3D
2796
2797TH3 *TH3::RebinZ(Int_t ngroup, const char *newname)
2798{
2799 return Rebin3D(1, 1, ngroup, newname);
2800
2801}
2802
2803
2804////////////////////////////////////////////////////////////////////////////////
2805/// Rebin this histogram grouping nxgroup/nygroup/nzgroup bins along the xaxis/yaxis/zaxis together.
2806///
2807/// if newname is not blank a new temporary histogram hnew is created.
2808/// else the current histogram is modified (default)
2809/// The parameter nxgroup/nygroup indicate how many bins along the xaxis/yaxis of this
2810/// have to me merged into one bin of hnew
2811/// If the original histogram has errors stored (via Sumw2), the resulting
2812/// histograms has new errors correctly calculated.
2813///
2814/// examples: if hpxpy is an existing TH3 histogram with 40 x 40 x 40 bins
2815/// hpxpypz->Rebin3D(); // merges two bins along the xaxis and yaxis in one in hpxpypz
2816/// // Carefull: previous contents of hpxpy are lost
2817/// hpxpypz->RebinX(5); //merges five bins along the xaxis in one in hpxpypz
2818/// TH3 *hnew = hpxpypz->RebinY(5,"hnew"); // creates a new histogram hnew
2819/// // merging 5 bins of h1 along the yaxis in one bin
2820///
2821/// NOTE : If nxgroup/nygroup is not an exact divider of the number of bins,
2822/// along the xaxis/yaxis the top limit(s) of the rebinned histogram
2823/// is changed to the upper edge of the xbin=newxbins*nxgroup resp.
2824/// ybin=newybins*nygroup and the corresponding bins are added to
2825/// the overflow bin.
2826/// Statistics will be recomputed from the new bin contents.
2827
2828TH3 *TH3::Rebin3D(Int_t nxgroup, Int_t nygroup, Int_t nzgroup, const char *newname)
2829{
2830 Int_t i,j,k,xbin,ybin,zbin;
2831 Int_t nxbins = fXaxis.GetNbins();
2832 Int_t nybins = fYaxis.GetNbins();
2833 Int_t nzbins = fZaxis.GetNbins();
2838 Double_t zmin = fZaxis.GetXmin();
2839 Double_t zmax = fZaxis.GetXmax();
2840 if ((nxgroup <= 0) || (nxgroup > nxbins)) {
2841 Error("Rebin", "Illegal value of nxgroup=%d",nxgroup);
2842 return 0;
2843 }
2844 if ((nygroup <= 0) || (nygroup > nybins)) {
2845 Error("Rebin", "Illegal value of nygroup=%d",nygroup);
2846 return 0;
2847 }
2848 if ((nzgroup <= 0) || (nzgroup > nzbins)) {
2849 Error("Rebin", "Illegal value of nzgroup=%d",nzgroup);
2850 return 0;
2851 }
2852
2853 Int_t newxbins = nxbins/nxgroup;
2854 Int_t newybins = nybins/nygroup;
2855 Int_t newzbins = nzbins/nzgroup;
2856
2857 // Save old bin contents into a new array
2858 Double_t entries = fEntries;
2859 Double_t *oldBins = new Double_t[fNcells];
2860 for (Int_t ibin = 0; ibin < fNcells; ibin++) {
2861 oldBins[ibin] = RetrieveBinContent(ibin);
2862 }
2863 Double_t *oldSumw2 = 0;
2864 if (fSumw2.fN != 0) {
2865 oldSumw2 = new Double_t[fNcells];
2866 for (Int_t ibin = 0; ibin < fNcells; ibin++) {
2867 oldSumw2[ibin] = fSumw2.fArray[ibin];
2868 }
2869 }
2870
2871 // create a clone of the old histogram if newname is specified
2872 TH3 *hnew = this;
2873 if (newname && strlen(newname)) {
2874 hnew = (TH3*)Clone();
2875 hnew->SetName(newname);
2876 }
2877
2878 // save original statistics
2879 Double_t stat[kNstat];
2880 GetStats(stat);
2881 bool resetStat = false;
2882
2883
2884 // change axis specs and rebuild bin contents array
2885 if (newxbins*nxgroup != nxbins) {
2886 xmax = fXaxis.GetBinUpEdge(newxbins*nxgroup);
2887 resetStat = true; //stats must be reset because top bins will be moved to overflow bin
2888 }
2889 if (newybins*nygroup != nybins) {
2890 ymax = fYaxis.GetBinUpEdge(newybins*nygroup);
2891 resetStat = true; //stats must be reset because top bins will be moved to overflow bin
2892 }
2893 if (newzbins*nzgroup != nzbins) {
2894 zmax = fZaxis.GetBinUpEdge(newzbins*nzgroup);
2895 resetStat = true; //stats must be reset because top bins will be moved to overflow bin
2896 }
2897 // save the TAttAxis members (reset by SetBins) for x axis
2898 Int_t nXdivisions = fXaxis.GetNdivisions();
2899 Color_t xAxisColor = fXaxis.GetAxisColor();
2900 Color_t xLabelColor = fXaxis.GetLabelColor();
2901 Style_t xLabelFont = fXaxis.GetLabelFont();
2902 Float_t xLabelOffset = fXaxis.GetLabelOffset();
2903 Float_t xLabelSize = fXaxis.GetLabelSize();
2904 Float_t xTickLength = fXaxis.GetTickLength();
2905 Float_t xTitleOffset = fXaxis.GetTitleOffset();
2906 Float_t xTitleSize = fXaxis.GetTitleSize();
2907 Color_t xTitleColor = fXaxis.GetTitleColor();
2908 Style_t xTitleFont = fXaxis.GetTitleFont();
2909 // save the TAttAxis members (reset by SetBins) for y axis
2910 Int_t nYdivisions = fYaxis.GetNdivisions();
2911 Color_t yAxisColor = fYaxis.GetAxisColor();
2912 Color_t yLabelColor = fYaxis.GetLabelColor();
2913 Style_t yLabelFont = fYaxis.GetLabelFont();
2914 Float_t yLabelOffset = fYaxis.GetLabelOffset();
2915 Float_t yLabelSize = fYaxis.GetLabelSize();
2916 Float_t yTickLength = fYaxis.GetTickLength();
2917 Float_t yTitleOffset = fYaxis.GetTitleOffset();
2918 Float_t yTitleSize = fYaxis.GetTitleSize();
2919 Color_t yTitleColor = fYaxis.GetTitleColor();
2920 Style_t yTitleFont = fYaxis.GetTitleFont();
2921 // save the TAttAxis members (reset by SetBins) for z axis
2922 Int_t nZdivisions = fZaxis.GetNdivisions();
2923 Color_t zAxisColor = fZaxis.GetAxisColor();
2924 Color_t zLabelColor = fZaxis.GetLabelColor();
2925 Style_t zLabelFont = fZaxis.GetLabelFont();
2926 Float_t zLabelOffset = fZaxis.GetLabelOffset();
2927 Float_t zLabelSize = fZaxis.GetLabelSize();
2928 Float_t zTickLength = fZaxis.GetTickLength();
2929 Float_t zTitleOffset = fZaxis.GetTitleOffset();
2930 Float_t zTitleSize = fZaxis.GetTitleSize();
2931 Color_t zTitleColor = fZaxis.GetTitleColor();
2932 Style_t zTitleFont = fZaxis.GetTitleFont();
2933
2934 // copy merged bin contents (ignore under/overflows)
2935 if (nxgroup != 1 || nygroup != 1 || nzgroup != 1) {
2936 if (fXaxis.GetXbins()->GetSize() > 0 || fYaxis.GetXbins()->GetSize() > 0 || fZaxis.GetXbins()->GetSize() > 0) {
2937 // variable bin sizes in x or y, don't treat both cases separately
2938 Double_t *xbins = new Double_t[newxbins+1];
2939 for (i = 0; i <= newxbins; ++i) xbins[i] = fXaxis.GetBinLowEdge(1+i*nxgroup);
2940 Double_t *ybins = new Double_t[newybins+1];
2941 for (i = 0; i <= newybins; ++i) ybins[i] = fYaxis.GetBinLowEdge(1+i*nygroup);
2942 Double_t *zbins = new Double_t[newzbins+1];
2943 for (i = 0; i <= newzbins; ++i) zbins[i] = fZaxis.GetBinLowEdge(1+i*nzgroup);
2944 hnew->SetBins(newxbins,xbins, newybins, ybins, newzbins, zbins);//changes also errors array (if any)
2945 delete [] xbins;
2946 delete [] ybins;
2947 delete [] zbins;
2948 } else {
2949 hnew->SetBins(newxbins, xmin, xmax, newybins, ymin, ymax, newzbins, zmin, zmax);//changes also errors array
2950 }
2951
2952 Double_t binContent, binSumw2;
2953 Int_t oldxbin = 1;
2954 Int_t oldybin = 1;
2955 Int_t oldzbin = 1;
2956 Int_t bin;
2957 for (xbin = 1; xbin <= newxbins; xbin++) {
2958 oldybin=1;
2959 oldzbin=1;
2960 for (ybin = 1; ybin <= newybins; ybin++) {
2961 oldzbin=1;
2962 for (zbin = 1; zbin <= newzbins; zbin++) {
2963 binContent = 0;
2964 binSumw2 = 0;
2965 for (i = 0; i < nxgroup; i++) {
2966 if (oldxbin+i > nxbins) break;
2967 for (j =0; j < nygroup; j++) {
2968 if (oldybin+j > nybins) break;
2969 for (k =0; k < nzgroup; k++) {
2970 if (oldzbin+k > nzbins) break;
2971 //get global bin (same conventions as in TH1::GetBin(xbin,ybin)
2972 bin = oldxbin + i + (oldybin + j)*(nxbins + 2) + (oldzbin + k)*(nxbins + 2)*(nybins + 2);
2973 binContent += oldBins[bin];
2974 if (oldSumw2) binSumw2 += oldSumw2[bin];
2975 }
2976 }
2977 }
2978 Int_t ibin = hnew->GetBin(xbin,ybin,zbin); // new bin number
2979 hnew->SetBinContent(ibin, binContent);
2980 if (oldSumw2) hnew->fSumw2.fArray[ibin] = binSumw2;
2981 oldzbin += nzgroup;
2982 }
2983 oldybin += nygroup;
2984 }
2985 oldxbin += nxgroup;
2986 }
2987
2988 // compute new underflow/overflows for the 8 vertices
2989 for (Int_t xover = 0; xover <= 1; xover++) {
2990 for (Int_t yover = 0; yover <= 1; yover++) {
2991 for (Int_t zover = 0; zover <= 1; zover++) {
2992 binContent = 0;
2993 binSumw2 = 0;
2994 // make loop in case of only underflow/overflow
2995 for (xbin = xover*oldxbin; xbin <= xover*(nxbins+1); xbin++) {
2996 for (ybin = yover*oldybin; ybin <= yover*(nybins+1); ybin++) {
2997 for (zbin = zover*oldzbin; zbin <= zover*(nzbins+1); zbin++) {
2998 bin = GetBin(xbin,ybin,zbin);
2999 binContent += oldBins[bin];
3000 if (oldSumw2) binSumw2 += oldSumw2[bin];
3001 }
3002 }
3003 }
3004 Int_t binNew = hnew->GetBin( xover *(newxbins+1),
3005 yover*(newybins+1), zover*(newzbins+1) );
3006 hnew->SetBinContent(binNew,binContent);
3007 if (oldSumw2) hnew->fSumw2.fArray[binNew] = binSumw2;
3008 }
3009 }
3010 }
3011
3012 Double_t binContent0, binContent2, binContent3, binContent4;
3013 Double_t binError0, binError2, binError3, binError4;
3014 Int_t oldxbin2, oldybin2, oldzbin2;
3015 Int_t ufbin, ofbin, ofbin2, ofbin3, ofbin4;
3016
3017 // recompute under/overflow contents in y for the new x and z bins
3018 oldxbin2 = 1;
3019 oldybin2 = 1;
3020 oldzbin2 = 1;
3021 for (xbin = 1; xbin<=newxbins; xbin++) {
3022 oldzbin2 = 1;
3023 for (zbin = 1; zbin<=newzbins; zbin++) {
3024 binContent0 = binContent2 = 0;
3025 binError0 = binError2 = 0;
3026 for (i=0; i<nxgroup; i++) {
3027 if (oldxbin2+i > nxbins) break;
3028 for (k=0; k<nzgroup; k++) {
3029 if (oldzbin2+k > nzbins) break;
3030 //old underflow bin (in y)
3031 ufbin = oldxbin2 + i + (nxbins+2)*(nybins+2)*(oldzbin2+k);
3032 binContent0 += oldBins[ufbin];
3033 if (oldSumw2) binError0 += oldSumw2[ufbin];
3034 for (ybin = oldybin; ybin <= nybins + 1; ybin++) {
3035 //old overflow bin (in y)
3036 ofbin = ufbin + ybin*(nxbins+2);
3037 binContent2 += oldBins[ofbin];
3038 if (oldSumw2) binError2 += oldSumw2[ofbin];
3039 }
3040 }
3041 }
3042 hnew->SetBinContent(xbin,0,zbin,binContent0);
3043 hnew->SetBinContent(xbin,newybins+1,zbin,binContent2);
3044 if (oldSumw2) {
3045 hnew->SetBinError(xbin,0,zbin,TMath::Sqrt(binError0));
3046 hnew->SetBinError(xbin,newybins+1,zbin,TMath::Sqrt(binError2) );
3047 }
3048 oldzbin2 += nzgroup;
3049 }
3050 oldxbin2 += nxgroup;
3051 }
3052
3053 // recompute under/overflow contents in x for the new y and z bins
3054 oldxbin2 = 1;
3055 oldybin2 = 1;
3056 oldzbin2 = 1;
3057 for (ybin = 1; ybin<=newybins; ybin++) {
3058 oldzbin2 = 1;
3059 for (zbin = 1; zbin<=newzbins; zbin++) {
3060 binContent0 = binContent2 = 0;
3061 binError0 = binError2 = 0;
3062 for (j=0; j<nygroup; j++) {
3063 if (oldybin2+j > nybins) break;
3064 for (k=0; k<nzgroup; k++) {
3065 if (oldzbin2+k > nzbins) break;
3066 //old underflow bin (in y)
3067 ufbin = (oldybin2 + j)*(nxbins+2) + (nxbins+2)*(nybins+2)*(oldzbin2+k);
3068 binContent0 += oldBins[ufbin];
3069 if (oldSumw2) binError0 += oldSumw2[ufbin];
3070 for (xbin = oldxbin; xbin <= nxbins + 1; xbin++) {
3071 //old overflow bin (in x)
3072 ofbin = ufbin + xbin;
3073 binContent2 += oldBins[ofbin];
3074 if (oldSumw2) binError2 += oldSumw2[ofbin];
3075 }
3076 }
3077 }
3078 hnew->SetBinContent(0,ybin,zbin,binContent0);
3079 hnew->SetBinContent(newxbins+1,ybin,zbin,binContent2);
3080 if (oldSumw2) {
3081 hnew->SetBinError(0,ybin,zbin,TMath::Sqrt(binError0));
3082 hnew->SetBinError(newxbins+1,ybin,zbin,TMath::Sqrt(binError2) );
3083 }
3084 oldzbin2 += nzgroup;
3085 }
3086 oldybin2 += nygroup;
3087 }
3088
3089 // recompute under/overflow contents in z for the new x and y bins
3090 oldxbin2 = 1;
3091 oldybin2 = 1;
3092 oldzbin2 = 1;
3093 for (xbin = 1; xbin<=newxbins; xbin++) {
3094 oldybin2 = 1;
3095 for (ybin = 1; ybin<=newybins; ybin++) {
3096 binContent0 = binContent2 = 0;
3097 binError0 = binError2 = 0;
3098 for (i=0; i<nxgroup; i++) {
3099 if (oldxbin2+i > nxbins) break;
3100 for (j=0; j<nygroup; j++) {
3101 if (oldybin2+j > nybins) break;
3102 //old underflow bin (in z)
3103 ufbin = oldxbin2 + i + (nxbins+2)*(oldybin2+j);
3104 binContent0 += oldBins[ufbin];
3105 if (oldSumw2) binError0 += oldSumw2[ufbin];
3106 for (zbin = oldzbin; zbin <= nzbins + 1; zbin++) {
3107 //old overflow bin (in z)
3108 ofbin = ufbin + (nxbins+2)*(nybins+2)*zbin;
3109 binContent2 += oldBins[ofbin];
3110 if (oldSumw2) binError2 += oldSumw2[ofbin];
3111 }
3112 }
3113 }
3114 hnew->SetBinContent(xbin,ybin,0,binContent0);
3115 hnew->SetBinContent(xbin,ybin,newzbins+1,binContent2);
3116 if (oldSumw2) {
3117 hnew->SetBinError(xbin,ybin,0,TMath::Sqrt(binError0));
3118 hnew->SetBinError(xbin,ybin,newzbins+1,TMath::Sqrt(binError2) );
3119 }
3120 oldybin2 += nygroup;
3121 }
3122 oldxbin2 += nxgroup;
3123 }
3124
3125 // recompute under/overflow contents in y, z for the new x
3126 oldxbin2 = 1;
3127 oldybin2 = 1;
3128 oldzbin2 = 1;
3129 for (xbin = 1; xbin<=newxbins; xbin++) {
3130 binContent0 = 0;
3131 binContent2 = 0;
3132 binContent3 = 0;
3133 binContent4 = 0;
3134 binError0 = 0;
3135 binError2 = 0;
3136 binError3 = 0;
3137 binError4 = 0;
3138 for (i=0; i<nxgroup; i++) {
3139 if (oldxbin2+i > nxbins) break;
3140 ufbin = oldxbin2 + i; //
3141 binContent0 += oldBins[ufbin];
3142 if (oldSumw2) binError0 += oldSumw2[ufbin];
3143 for (ybin = oldybin; ybin <= nybins + 1; ybin++) {
3144 ofbin3 = ufbin+ybin*(nxbins+2);
3145 binContent3 += oldBins[ ofbin3 ];
3146 if (oldSumw2) binError3 += oldSumw2[ofbin3];
3147 for (zbin = oldzbin; zbin <= nzbins + 1; zbin++) {
3148 //old overflow bin (in z)
3149 ofbin4 = oldxbin2 + i + ybin*(nxbins+2) + (nxbins+2)*(nybins+2)*zbin;
3150 binContent4 += oldBins[ofbin4];
3151 if (oldSumw2) binError4 += oldSumw2[ofbin4];
3152 }
3153 }
3154 for (zbin = oldzbin; zbin <= nzbins + 1; zbin++) {
3155 ofbin2 = ufbin+zbin*(nxbins+2)*(nybins+2);
3156 binContent2 += oldBins[ ofbin2 ];
3157 if (oldSumw2) binError2 += oldSumw2[ofbin2];
3158 }
3159 }
3160 hnew->SetBinContent(xbin,0,0,binContent0);
3161 hnew->SetBinContent(xbin,0,newzbins+1,binContent2);
3162 hnew->SetBinContent(xbin,newybins+1,0,binContent3);
3163 hnew->SetBinContent(xbin,newybins+1,newzbins+1,binContent4);
3164 if (oldSumw2) {
3165 hnew->SetBinError(xbin,0,0,TMath::Sqrt(binError0));
3166 hnew->SetBinError(xbin,0,newzbins+1,TMath::Sqrt(binError2) );
3167 hnew->SetBinError(xbin,newybins+1,0,TMath::Sqrt(binError3) );
3168 hnew->SetBinError(xbin,newybins+1,newzbins+1,TMath::Sqrt(binError4) );
3169 }
3170 oldxbin2 += nxgroup;
3171 }
3172
3173 // recompute under/overflow contents in x, y for the new z
3174 oldxbin2 = 1;
3175 oldybin2 = 1;
3176 oldzbin2 = 1;
3177 for (zbin = 1; zbin<=newzbins; zbin++) {
3178 binContent0 = 0;
3179 binContent2 = 0;
3180 binContent3 = 0;
3181 binContent4 = 0;
3182 binError0 = 0;
3183 binError2 = 0;
3184 binError3 = 0;
3185 binError4 = 0;
3186 for (i=0; i<nzgroup; i++) {
3187 if (oldzbin2+i > nzbins) break;
3188 ufbin = (oldzbin2 + i)*(nxbins+2)*(nybins+2); //
3189 binContent0 += oldBins[ufbin];
3190 if (oldSumw2) binError0 += oldSumw2[ufbin];
3191 for (ybin = oldybin; ybin <= nybins + 1; ybin++) {
3192 ofbin3 = ufbin+ybin*(nxbins+2);
3193 binContent3 += oldBins[ ofbin3 ];
3194 if (oldSumw2) binError3 += oldSumw2[ofbin3];
3195 for (xbin = oldxbin; xbin <= nxbins + 1; xbin++) {
3196 //old overflow bin (in z)
3197 ofbin4 = ufbin + xbin + ybin*(nxbins+2);
3198 binContent4 += oldBins[ofbin4];
3199 if (oldSumw2) binError4 += oldSumw2[ofbin4];
3200 }
3201 }
3202 for (xbin = oldxbin; xbin <= nxbins + 1; xbin++) {
3203 ofbin2 = xbin +(oldzbin2+i)*(nxbins+2)*(nybins+2);
3204 binContent2 += oldBins[ ofbin2 ];
3205 if (oldSumw2) binError2 += oldSumw2[ofbin2];
3206 }
3207 }
3208 hnew->SetBinContent(0,0,zbin,binContent0);
3209 hnew->SetBinContent(0,newybins+1,zbin,binContent3);
3210 hnew->SetBinContent(newxbins+1,0,zbin,binContent2);
3211 hnew->SetBinContent(newxbins+1,newybins+1,zbin,binContent4);
3212 if (oldSumw2) {
3213 hnew->SetBinError(0,0,zbin,TMath::Sqrt(binError0));
3214 hnew->SetBinError(0,newybins+1,zbin,TMath::Sqrt(binError3) );
3215 hnew->SetBinError(newxbins+1,0,zbin,TMath::Sqrt(binError2) );
3216 hnew->SetBinError(newxbins+1,newybins+1,zbin,TMath::Sqrt(binError4) );
3217 }
3218 oldzbin2 += nzgroup;
3219 }
3220
3221 // recompute under/overflow contents in x, z for the new y
3222 oldxbin2 = 1;
3223 oldybin2 = 1;
3224 oldzbin2 = 1;
3225 for (ybin = 1; ybin<=newybins; ybin++) {
3226 binContent0 = 0;
3227 binContent2 = 0;
3228 binContent3 = 0;
3229 binContent4 = 0;
3230 binError0 = 0;
3231 binError2 = 0;
3232 binError3 = 0;
3233 binError4 = 0;
3234 for (i=0; i<nygroup; i++) {
3235 if (oldybin2+i > nybins) break;
3236 ufbin = (oldybin2 + i)*(nxbins+2); //
3237 binContent0 += oldBins[ufbin];
3238 if (oldSumw2) binError0 += oldSumw2[ufbin];
3239 for (xbin = oldxbin; xbin <= nxbins + 1; xbin++) {
3240 ofbin3 = ufbin+xbin;
3241 binContent3 += oldBins[ ofbin3 ];
3242 if (oldSumw2) binError3 += oldSumw2[ofbin3];
3243 for (zbin = oldzbin; zbin <= nzbins + 1; zbin++) {
3244 //old overflow bin (in z)
3245 ofbin4 = xbin + (nxbins+2)*(nybins+2)*zbin+(oldybin2+i)*(nxbins+2);
3246 binContent4 += oldBins[ofbin4];
3247 if (oldSumw2) binError4 += oldSumw2[ofbin4];
3248 }
3249 }
3250 for (zbin = oldzbin; zbin <= nzbins + 1; zbin++) {
3251 ofbin2 = (oldybin2+i)*(nxbins+2)+zbin*(nxbins+2)*(nybins+2);
3252 binContent2 += oldBins[ ofbin2 ];
3253 if (oldSumw2) binError2 += oldSumw2[ofbin2];
3254 }
3255 }
3256 hnew->SetBinContent(0,ybin,0,binContent0);
3257 hnew->SetBinContent(0,ybin,newzbins+1,binContent2);
3258 hnew->SetBinContent(newxbins+1,ybin,0,binContent3);
3259 hnew->SetBinContent(newxbins+1,ybin,newzbins+1,binContent4);
3260 if (oldSumw2) {
3261 hnew->SetBinError(0,ybin,0,TMath::Sqrt(binError0));
3262 hnew->SetBinError(0,ybin,newzbins+1,TMath::Sqrt(binError2) );
3263 hnew->SetBinError(newxbins+1,ybin,0,TMath::Sqrt(binError3) );
3264 hnew->SetBinError(newxbins+1,ybin,newzbins+1,TMath::Sqrt(binError4) );
3265 }
3266 oldybin2 += nygroup;
3267 }
3268 }
3269
3270 // Restore x axis attributes
3271 fXaxis.SetNdivisions(nXdivisions);
3272 fXaxis.SetAxisColor(xAxisColor);
3273 fXaxis.SetLabelColor(xLabelColor);
3274 fXaxis.SetLabelFont(xLabelFont);
3275 fXaxis.SetLabelOffset(xLabelOffset);
3276 fXaxis.SetLabelSize(xLabelSize);
3277 fXaxis.SetTickLength(xTickLength);
3278 fXaxis.SetTitleOffset(xTitleOffset);
3279 fXaxis.SetTitleSize(xTitleSize);
3280 fXaxis.SetTitleColor(xTitleColor);
3281 fXaxis.SetTitleFont(xTitleFont);
3282 // Restore y axis attributes
3283 fYaxis.SetNdivisions(nYdivisions);
3284 fYaxis.SetAxisColor(yAxisColor);
3285 fYaxis.SetLabelColor(yLabelColor);
3286 fYaxis.SetLabelFont(yLabelFont);
3287 fYaxis.SetLabelOffset(yLabelOffset);
3288 fYaxis.SetLabelSize(yLabelSize);
3289 fYaxis.SetTickLength(yTickLength);
3290 fYaxis.SetTitleOffset(yTitleOffset);
3291 fYaxis.SetTitleSize(yTitleSize);
3292 fYaxis.SetTitleColor(yTitleColor);
3293 fYaxis.SetTitleFont(yTitleFont);
3294 // Restore z axis attributes
3295 fZaxis.SetNdivisions(nZdivisions);
3296 fZaxis.SetAxisColor(zAxisColor);
3297 fZaxis.SetLabelColor(zLabelColor);
3298 fZaxis.SetLabelFont(zLabelFont);
3299 fZaxis.SetLabelOffset(zLabelOffset);
3300 fZaxis.SetLabelSize(zLabelSize);
3301 fZaxis.SetTickLength(zTickLength);
3302 fZaxis.SetTitleOffset(zTitleOffset);
3303 fZaxis.SetTitleSize(zTitleSize);
3304 fZaxis.SetTitleColor(zTitleColor);
3305 fZaxis.SetTitleFont(zTitleFont);
3306
3307 //restore statistics and entries modified by SetBinContent
3308 hnew->SetEntries(entries);
3309 if (!resetStat) hnew->PutStats(stat);
3310
3311 delete [] oldBins;
3312 if (oldSumw2) delete [] oldSumw2;
3313 return hnew;
3314}
3315
3316
3317////////////////////////////////////////////////////////////////////////////////
3318/// Reset this histogram: contents, errors, etc.
3319
3321{
3322 TH1::Reset(option);
3323 TString opt = option;
3324 opt.ToUpper();
3325 if (opt.Contains("ICE") && !opt.Contains("S")) return;
3326 fTsumwy = 0;
3327 fTsumwy2 = 0;
3328 fTsumwxy = 0;
3329 fTsumwz = 0;
3330 fTsumwz2 = 0;
3331 fTsumwxz = 0;
3332 fTsumwyz = 0;
3333}
3334
3335
3336////////////////////////////////////////////////////////////////////////////////
3337/// Set bin content.
3338
3340{
3341 fEntries++;
3342 fTsumw = 0;
3343 if (bin < 0) return;
3344 if (bin >= fNcells) return;
3345 UpdateBinContent(bin, content);
3346}
3347
3348
3349////////////////////////////////////////////////////////////////////////////////
3350/// Stream an object of class TH3.
3351
3352void TH3::Streamer(TBuffer &R__b)
3353{
3354 if (R__b.IsReading()) {
3355 UInt_t R__s, R__c;
3356 Version_t R__v = R__b.ReadVersion(&R__s, &R__c);
3357 if (R__v > 2) {
3358 R__b.ReadClassBuffer(TH3::Class(), this, R__v, R__s, R__c);
3359 return;
3360 }
3361 //====process old versions before automatic schema evolution
3362 TH1::Streamer(R__b);
3363 TAtt3D::Streamer(R__b);
3364 R__b.CheckByteCount(R__s, R__c, TH3::IsA());
3365 //====end of old versions
3366
3367 } else {
3368 R__b.WriteClassBuffer(TH3::Class(),this);
3369 }
3370}
3371
3372
3373//______________________________________________________________________________
3374// TH3C methods
3375// TH3C a 3-D histogram with one byte per cell (char)
3376//______________________________________________________________________________
3377
3378ClassImp(TH3C);
3379
3380
3381////////////////////////////////////////////////////////////////////////////////
3382/// Constructor.
3383
3385{
3386 SetBinsLength(27);
3387 if (fgDefaultSumw2) Sumw2();
3388}
3389
3390
3391////////////////////////////////////////////////////////////////////////////////
3392/// Destructor.
3393
3395{
3396}
3397
3398
3399////////////////////////////////////////////////////////////////////////////////
3400/// Normal constructor for fix bin size 3-D histograms.
3401
3402TH3C::TH3C(const char *name,const char *title,Int_t nbinsx,Double_t xlow,Double_t xup
3403 ,Int_t nbinsy,Double_t ylow,Double_t yup
3404 ,Int_t nbinsz,Double_t zlow,Double_t zup)
3405 :TH3(name,title,nbinsx,xlow,xup,nbinsy,ylow,yup,nbinsz,zlow,zup)
3406{
3408 if (fgDefaultSumw2) Sumw2();
3409
3410 if (xlow >= xup || ylow >= yup || zlow >= zup) SetBuffer(fgBufferSize);
3411}
3412
3413
3414////////////////////////////////////////////////////////////////////////////////
3415/// Normal constructor for variable bin size 3-D histograms.
3416
3417TH3C::TH3C(const char *name,const char *title,Int_t nbinsx,const Float_t *xbins
3418 ,Int_t nbinsy,const Float_t *ybins
3419 ,Int_t nbinsz,const Float_t *zbins)
3420 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
3421{
3423 if (fgDefaultSumw2) Sumw2();
3424}
3425
3426
3427////////////////////////////////////////////////////////////////////////////////
3428/// Normal constructor for variable bin size 3-D histograms.
3429
3430TH3C::TH3C(const char *name,const char *title,Int_t nbinsx,const Double_t *xbins
3431 ,Int_t nbinsy,const Double_t *ybins
3432 ,Int_t nbinsz,const Double_t *zbins)
3433 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
3434{
3436 if (fgDefaultSumw2) Sumw2();
3437}
3438
3439
3440////////////////////////////////////////////////////////////////////////////////
3441/// Copy constructor.
3442
3443TH3C::TH3C(const TH3C &h3c) : TH3(), TArrayC()
3444{
3445 ((TH3C&)h3c).Copy(*this);
3446}
3447
3448
3449////////////////////////////////////////////////////////////////////////////////
3450/// Increment bin content by 1.
3451
3453{
3454 if (fArray[bin] < 127) fArray[bin]++;
3455}
3456
3457
3458////////////////////////////////////////////////////////////////////////////////
3459/// Increment bin content by w.
3460
3462{
3463 Int_t newval = fArray[bin] + Int_t(w);
3464 if (newval > -128 && newval < 128) {fArray[bin] = Char_t(newval); return;}
3465 if (newval < -127) fArray[bin] = -127;
3466 if (newval > 127) fArray[bin] = 127;
3467}
3468
3469
3470////////////////////////////////////////////////////////////////////////////////
3471/// Copy this 3-D histogram structure to newth3.
3472
3473void TH3C::Copy(TObject &newth3) const
3474{
3475 TH3::Copy((TH3C&)newth3);
3476}
3477
3478
3479////////////////////////////////////////////////////////////////////////////////
3480/// Reset this histogram: contents, errors, etc.
3481
3483{
3484 TH3::Reset(option);
3486 // should also reset statistics once statistics are implemented for TH3
3487}
3488
3489
3490////////////////////////////////////////////////////////////////////////////////
3491/// Set total number of bins including under/overflow
3492/// Reallocate bin contents array
3493
3495{
3496 if (n < 0) n = (fXaxis.GetNbins()+2)*(fYaxis.GetNbins()+2)*(fZaxis.GetNbins()+2);
3497 fNcells = n;
3498 TArrayC::Set(n);
3499}
3500
3501
3502////////////////////////////////////////////////////////////////////////////////
3503/// When the mouse is moved in a pad containing a 3-d view of this histogram
3504/// a second canvas shows a projection type given as option.
3505/// To stop the generation of the projections, delete the canvas
3506/// containing the projection.
3507/// option may contain a combination of the characters x,y,z,e
3508/// option = "x" return the x projection into a TH1D histogram
3509/// option = "y" return the y projection into a TH1D histogram
3510/// option = "z" return the z projection into a TH1D histogram
3511/// option = "xy" return the x versus y projection into a TH2D histogram
3512/// option = "yx" return the y versus x projection into a TH2D histogram
3513/// option = "xz" return the x versus z projection into a TH2D histogram
3514/// option = "zx" return the z versus x projection into a TH2D histogram
3515/// option = "yz" return the y versus z projection into a TH2D histogram
3516/// option = "zy" return the z versus y projection into a TH2D histogram
3517/// option can also include the drawing option for the projection, eg to draw
3518/// the xy projection using the draw option "box" do
3519/// myhist.SetShowProjection("xy box");
3520/// This function is typically called from the context menu.
3521/// NB: the notation "a vs b" means "a" vertical and "b" horizontal
3522
3523void TH3::SetShowProjection(const char *option,Int_t nbins)
3524{
3525 GetPainter();
3526
3527 if (fPainter) fPainter->SetShowProjection(option,nbins);
3528}
3529
3530
3531////////////////////////////////////////////////////////////////////////////////
3532/// Stream an object of class TH3C.
3533
3534void TH3C::Streamer(TBuffer &R__b)
3535{
3536 if (R__b.IsReading()) {
3537 UInt_t R__s, R__c;
3538 if (R__b.GetParent() && R__b.GetVersionOwner() < 22300) return;
3539 Version_t R__v = R__b.ReadVersion(&R__s, &R__c);
3540 if (R__v > 2) {
3541 R__b.ReadClassBuffer(TH3C::Class(), this, R__v, R__s, R__c);
3542 return;
3543 }
3544 //====process old versions before automatic schema evolution
3545 if (R__v < 2) {
3546 R__b.ReadVersion();
3547 TH1::Streamer(R__b);
3548 TArrayC::Streamer(R__b);
3549 R__b.ReadVersion(&R__s, &R__c);
3550 TAtt3D::Streamer(R__b);
3551 } else {
3552 TH3::Streamer(R__b);
3553 TArrayC::Streamer(R__b);
3554 R__b.CheckByteCount(R__s, R__c, TH3C::IsA());
3555 }
3556 //====end of old versions
3557
3558 } else {
3559 R__b.WriteClassBuffer(TH3C::Class(),this);
3560 }
3561}
3562
3563
3564////////////////////////////////////////////////////////////////////////////////
3565/// Operator =
3566
3568{
3569 if (this != &h1) ((TH3C&)h1).Copy(*this);
3570 return *this;
3571}
3572
3573
3574////////////////////////////////////////////////////////////////////////////////
3575/// Operator *
3576
3578{
3579 TH3C hnew = h1;
3580 hnew.Scale(c1);
3581 hnew.SetDirectory(0);
3582 return hnew;
3583}
3584
3585
3586////////////////////////////////////////////////////////////////////////////////
3587/// Operator +
3588
3590{
3591 TH3C hnew = h1;
3592 hnew.Add(&h2,1);
3593 hnew.SetDirectory(0);
3594 return hnew;
3595}
3596
3597
3598////////////////////////////////////////////////////////////////////////////////
3599/// Operator -
3600
3602{
3603 TH3C hnew = h1;
3604 hnew.Add(&h2,-1);
3605 hnew.SetDirectory(0);
3606 return hnew;
3607}
3608
3609
3610////////////////////////////////////////////////////////////////////////////////
3611/// Operator *
3612
3614{
3615 TH3C hnew = h1;
3616 hnew.Multiply(&h2);
3617 hnew.SetDirectory(0);
3618 return hnew;
3619}
3620
3621
3622////////////////////////////////////////////////////////////////////////////////
3623/// Operator /
3624
3626{
3627 TH3C hnew = h1;
3628 hnew.Divide(&h2);
3629 hnew.SetDirectory(0);
3630 return hnew;
3631}
3632
3633
3634//______________________________________________________________________________
3635// TH3S methods
3636// TH3S a 3-D histogram with two bytes per cell (short integer)
3637//______________________________________________________________________________
3638
3639ClassImp(TH3S);
3640
3641
3642////////////////////////////////////////////////////////////////////////////////
3643/// Constructor.
3644
3646{
3647 SetBinsLength(27);
3648 if (fgDefaultSumw2) Sumw2();
3649}
3650
3651
3652////////////////////////////////////////////////////////////////////////////////
3653/// Destructor.
3654
3656{
3657}
3658
3659
3660////////////////////////////////////////////////////////////////////////////////
3661/// Normal constructor for fix bin size 3-D histograms.
3662
3663TH3S::TH3S(const char *name,const char *title,Int_t nbinsx,Double_t xlow,Double_t xup
3664 ,Int_t nbinsy,Double_t ylow,Double_t yup
3665 ,Int_t nbinsz,Double_t zlow,Double_t zup)
3666 :TH3(name,title,nbinsx,xlow,xup,nbinsy,ylow,yup,nbinsz,zlow,zup)
3667{
3669 if (fgDefaultSumw2) Sumw2();
3670
3671 if (xlow >= xup || ylow >= yup || zlow >= zup) SetBuffer(fgBufferSize);
3672}
3673
3674
3675////////////////////////////////////////////////////////////////////////////////
3676/// Normal constructor for variable bin size 3-D histograms.
3677
3678TH3S::TH3S(const char *name,const char *title,Int_t nbinsx,const Float_t *xbins
3679 ,Int_t nbinsy,const Float_t *ybins
3680 ,Int_t nbinsz,const Float_t *zbins)
3681 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
3682{
3684 if (fgDefaultSumw2) Sumw2();
3685}
3686
3687
3688////////////////////////////////////////////////////////////////////////////////
3689/// Normal constructor for variable bin size 3-D histograms.
3690
3691TH3S::TH3S(const char *name,const char *title,Int_t nbinsx,const Double_t *xbins
3692 ,Int_t nbinsy,const Double_t *ybins
3693 ,Int_t nbinsz,const Double_t *zbins)
3694 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
3695{
3697 if (fgDefaultSumw2) Sumw2();
3698}
3699
3700
3701////////////////////////////////////////////////////////////////////////////////
3702/// Copy Constructor.
3703
3704TH3S::TH3S(const TH3S &h3s) : TH3(), TArrayS()
3705{
3706 ((TH3S&)h3s).Copy(*this);
3707}
3708
3709
3710////////////////////////////////////////////////////////////////////////////////
3711/// Increment bin content by 1.
3712
3714{
3715 if (fArray[bin] < 32767) fArray[bin]++;
3716}
3717
3718
3719////////////////////////////////////////////////////////////////////////////////
3720/// Increment bin content by w.
3721
3723{
3724 Int_t newval = fArray[bin] + Int_t(w);
3725 if (newval > -32768 && newval < 32768) {fArray[bin] = Short_t(newval); return;}
3726 if (newval < -32767) fArray[bin] = -32767;
3727 if (newval > 32767) fArray[bin] = 32767;
3728}
3729
3730
3731////////////////////////////////////////////////////////////////////////////////
3732/// Copy this 3-D histogram structure to newth3.
3733
3734void TH3S::Copy(TObject &newth3) const
3735{
3736 TH3::Copy((TH3S&)newth3);
3737}
3738
3739
3740////////////////////////////////////////////////////////////////////////////////
3741/// Reset this histogram: contents, errors, etc.
3742
3744{
3745 TH3::Reset(option);
3747 // should also reset statistics once statistics are implemented for TH3
3748}
3749
3750
3751////////////////////////////////////////////////////////////////////////////////
3752/// Set total number of bins including under/overflow
3753/// Reallocate bin contents array
3754
3756{
3757 if (n < 0) n = (fXaxis.GetNbins()+2)*(fYaxis.GetNbins()+2)*(fZaxis.GetNbins()+2);
3758 fNcells = n;
3759 TArrayS::Set(n);
3760}
3761
3762
3763////////////////////////////////////////////////////////////////////////////////
3764/// Stream an object of class TH3S.
3765
3766void TH3S::Streamer(TBuffer &R__b)
3767{
3768 if (R__b.IsReading()) {
3769 UInt_t R__s, R__c;
3770 if (R__b.GetParent() && R__b.GetVersionOwner() < 22300) return;
3771 Version_t R__v = R__b.ReadVersion(&R__s, &R__c);
3772 if (R__v > 2) {
3773 R__b.ReadClassBuffer(TH3S::Class(), this, R__v, R__s, R__c);
3774 return;
3775 }
3776 //====process old versions before automatic schema evolution
3777 if (R__v < 2) {
3778 R__b.ReadVersion();
3779 TH1::Streamer(R__b);
3780 TArrayS::Streamer(R__b);
3781 R__b.ReadVersion(&R__s, &R__c);
3782 TAtt3D::Streamer(R__b);
3783 } else {
3784 TH3::Streamer(R__b);
3785 TArrayS::Streamer(R__b);
3786 R__b.CheckByteCount(R__s, R__c, TH3S::IsA());
3787 }
3788 //====end of old versions
3789
3790 } else {
3791 R__b.WriteClassBuffer(TH3S::Class(),this);
3792 }
3793}
3794
3795
3796////////////////////////////////////////////////////////////////////////////////
3797/// Operator =
3798
3800{
3801 if (this != &h1) ((TH3S&)h1).Copy(*this);
3802 return *this;
3803}
3804
3805
3806////////////////////////////////////////////////////////////////////////////////
3807/// Operator *
3808
3810{
3811 TH3S hnew = h1;
3812 hnew.Scale(c1);
3813 hnew.SetDirectory(0);
3814 return hnew;
3815}
3816
3817
3818////////////////////////////////////////////////////////////////////////////////
3819/// Operator +
3820
3822{
3823 TH3S hnew = h1;
3824 hnew.Add(&h2,1);
3825 hnew.SetDirectory(0);
3826 return hnew;
3827}
3828
3829
3830////////////////////////////////////////////////////////////////////////////////
3831/// Operator -
3832
3834{
3835 TH3S hnew = h1;
3836 hnew.Add(&h2,-1);
3837 hnew.SetDirectory(0);
3838 return hnew;
3839}
3840
3841
3842////////////////////////////////////////////////////////////////////////////////
3843/// Operator *
3844
3846{
3847 TH3S hnew = h1;
3848 hnew.Multiply(&h2);
3849 hnew.SetDirectory(0);
3850 return hnew;
3851}
3852
3853
3854////////////////////////////////////////////////////////////////////////////////
3855/// Operator /
3856
3858{
3859 TH3S hnew = h1;
3860 hnew.Divide(&h2);
3861 hnew.SetDirectory(0);
3862 return hnew;
3863}
3864
3865
3866//______________________________________________________________________________
3867// TH3I methods
3868// TH3I a 3-D histogram with four bytes per cell (32 bits integer)
3869//______________________________________________________________________________
3870
3871ClassImp(TH3I);
3872
3873
3874////////////////////////////////////////////////////////////////////////////////
3875/// Constructor.
3876
3878{
3879 SetBinsLength(27);
3880 if (fgDefaultSumw2) Sumw2();
3881}
3882
3883
3884////////////////////////////////////////////////////////////////////////////////
3885/// Destructor.
3886
3888{
3889}
3890
3891
3892////////////////////////////////////////////////////////////////////////////////
3893/// Normal constructor for fix bin size 3-D histograms.
3894
3895TH3I::TH3I(const char *name,const char *title,Int_t nbinsx,Double_t xlow,Double_t xup
3896 ,Int_t nbinsy,Double_t ylow,Double_t yup
3897 ,Int_t nbinsz,Double_t zlow,Double_t zup)
3898 :TH3(name,title,nbinsx,xlow,xup,nbinsy,ylow,yup,nbinsz,zlow,zup)
3899{
3901 if (fgDefaultSumw2) Sumw2();
3902
3903 if (xlow >= xup || ylow >= yup || zlow >= zup) SetBuffer(fgBufferSize);
3904}
3905
3906
3907////////////////////////////////////////////////////////////////////////////////
3908/// Normal constructor for variable bin size 3-D histograms.
3909
3910TH3I::TH3I(const char *name,const char *title,Int_t nbinsx,const Float_t *xbins
3911 ,Int_t nbinsy,const Float_t *ybins
3912 ,Int_t nbinsz,const Float_t *zbins)
3913 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
3914{
3916 if (fgDefaultSumw2) Sumw2();
3917}
3918
3919
3920////////////////////////////////////////////////////////////////////////////////
3921/// Normal constructor for variable bin size 3-D histograms.
3922
3923TH3I::TH3I(const char *name,const char *title,Int_t nbinsx,const Double_t *xbins
3924 ,Int_t nbinsy,const Double_t *ybins
3925 ,Int_t nbinsz,const Double_t *zbins)
3926 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
3927{
3929 if (fgDefaultSumw2) Sumw2();
3930}
3931
3932
3933////////////////////////////////////////////////////////////////////////////////
3934/// Copy constructor.
3935
3936TH3I::TH3I(const TH3I &h3i) : TH3(), TArrayI()
3937{
3938 ((TH3I&)h3i).Copy(*this);
3939}
3940
3941
3942////////////////////////////////////////////////////////////////////////////////
3943/// Increment bin content by 1.
3944
3946{
3947 if (fArray[bin] < INT_MAX) fArray[bin]++;
3948}
3949
3950
3951////////////////////////////////////////////////////////////////////////////////
3952/// Increment bin content by w.
3953
3955{
3956 Long64_t newval = fArray[bin] + Long64_t(w);
3957 if (newval > -INT_MAX && newval < INT_MAX) {fArray[bin] = Int_t(newval); return;}
3958 if (newval < -INT_MAX) fArray[bin] = -INT_MAX;
3959 if (newval > INT_MAX) fArray[bin] = INT_MAX;
3960}
3961
3962
3963////////////////////////////////////////////////////////////////////////////////
3964/// Copy this 3-D histogram structure to newth3.
3965
3966void TH3I::Copy(TObject &newth3) const
3967{
3968 TH3::Copy((TH3I&)newth3);
3969}
3970
3971
3972////////////////////////////////////////////////////////////////////////////////
3973/// Reset this histogram: contents, errors, etc.
3974
3976{
3977 TH3::Reset(option);
3979 // should also reset statistics once statistics are implemented for TH3
3980}
3981
3982
3983////////////////////////////////////////////////////////////////////////////////
3984/// Set total number of bins including under/overflow
3985/// Reallocate bin contents array
3986
3988{
3989 if (n < 0) n = (fXaxis.GetNbins()+2)*(fYaxis.GetNbins()+2)*(fZaxis.GetNbins()+2);
3990 fNcells = n;
3991 TArrayI::Set(n);
3992}
3993
3994
3995////////////////////////////////////////////////////////////////////////////////
3996/// Operator =
3997
3999{
4000 if (this != &h1) ((TH3I&)h1).Copy(*this);
4001 return *this;
4002}
4003
4004
4005////////////////////////////////////////////////////////////////////////////////
4006/// Operator *
4007
4009{
4010 TH3I hnew = h1;
4011 hnew.Scale(c1);
4012 hnew.SetDirectory(0);
4013 return hnew;
4014}
4015
4016
4017////////////////////////////////////////////////////////////////////////////////
4018/// Operator +
4019
4021{
4022 TH3I hnew = h1;
4023 hnew.Add(&h2,1);
4024 hnew.SetDirectory(0);
4025 return hnew;
4026}
4027
4028
4029////////////////////////////////////////////////////////////////////////////////
4030/// Operator _
4031
4033{
4034 TH3I hnew = h1;
4035 hnew.Add(&h2,-1);
4036 hnew.SetDirectory(0);
4037 return hnew;
4038}
4039
4040
4041////////////////////////////////////////////////////////////////////////////////
4042/// Operator *
4043
4045{
4046 TH3I hnew = h1;
4047 hnew.Multiply(&h2);
4048 hnew.SetDirectory(0);
4049 return hnew;
4050}
4051
4052
4053////////////////////////////////////////////////////////////////////////////////
4054/// Operator /
4055
4057{
4058 TH3I hnew = h1;
4059 hnew.Divide(&h2);
4060 hnew.SetDirectory(0);
4061 return hnew;
4062}
4063
4064
4065//______________________________________________________________________________
4066// TH3F methods
4067// TH3F a 3-D histogram with four bytes per cell (float)
4068//______________________________________________________________________________
4069
4070ClassImp(TH3F);
4071
4072
4073////////////////////////////////////////////////////////////////////////////////
4074/// Constructor.
4075
4077{
4078 SetBinsLength(27);
4079 if (fgDefaultSumw2) Sumw2();
4080}
4081
4082
4083////////////////////////////////////////////////////////////////////////////////
4084/// Destructor.
4085
4087{
4088}
4089
4090
4091////////////////////////////////////////////////////////////////////////////////
4092/// Normal constructor for fix bin size 3-D histograms.
4093
4094TH3F::TH3F(const char *name,const char *title,Int_t nbinsx,Double_t xlow,Double_t xup
4095 ,Int_t nbinsy,Double_t ylow,Double_t yup
4096 ,Int_t nbinsz,Double_t zlow,Double_t zup)
4097 :TH3(name,title,nbinsx,xlow,xup,nbinsy,ylow,yup,nbinsz,zlow,zup)
4098{
4100 if (fgDefaultSumw2) Sumw2();
4101
4102 if (xlow >= xup || ylow >= yup || zlow >= zup) SetBuffer(fgBufferSize);
4103}
4104
4105
4106////////////////////////////////////////////////////////////////////////////////
4107/// Normal constructor for variable bin size 3-D histograms.
4108
4109TH3F::TH3F(const char *name,const char *title,Int_t nbinsx,const Float_t *xbins
4110 ,Int_t nbinsy,const Float_t *ybins
4111 ,Int_t nbinsz,const Float_t *zbins)
4112 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
4113{
4115 if (fgDefaultSumw2) Sumw2();
4116}
4117
4118
4119////////////////////////////////////////////////////////////////////////////////
4120/// Normal constructor for variable bin size 3-D histograms.
4121
4122TH3F::TH3F(const char *name,const char *title,Int_t nbinsx,const Double_t *xbins
4123 ,Int_t nbinsy,const Double_t *ybins
4124 ,Int_t nbinsz,const Double_t *zbins)
4125 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
4126{
4128 if (fgDefaultSumw2) Sumw2();
4129}
4130
4131
4132////////////////////////////////////////////////////////////////////////////////
4133/// Copy constructor.
4134
4135TH3F::TH3F(const TH3F &h3f) : TH3(), TArrayF()
4136{
4137 ((TH3F&)h3f).Copy(*this);
4138}
4139
4140
4141////////////////////////////////////////////////////////////////////////////////
4142/// Copy this 3-D histogram structure to newth3.
4143
4144void TH3F::Copy(TObject &newth3) const
4145{
4146 TH3::Copy((TH3F&)newth3);
4147}
4148
4149
4150////////////////////////////////////////////////////////////////////////////////
4151/// Reset this histogram: contents, errors, etc.
4152
4154{
4155 TH3::Reset(option);
4157 // should also reset statistics once statistics are implemented for TH3
4158}
4159
4160
4161////////////////////////////////////////////////////////////////////////////////
4162/// Set total number of bins including under/overflow
4163/// Reallocate bin contents array
4164
4166{
4167 if (n < 0) n = (fXaxis.GetNbins()+2)*(fYaxis.GetNbins()+2)*(fZaxis.GetNbins()+2);
4168 fNcells = n;
4169 TArrayF::Set(n);
4170}
4171
4172
4173////////////////////////////////////////////////////////////////////////////////
4174/// Stream an object of class TH3F.
4175
4176void TH3F::Streamer(TBuffer &R__b)
4177{
4178 if (R__b.IsReading()) {
4179 UInt_t R__s, R__c;
4180 if (R__b.GetParent() && R__b.GetVersionOwner() < 22300) return;
4181 Version_t R__v = R__b.ReadVersion(&R__s, &R__c);
4182 if (R__v > 2) {
4183 R__b.ReadClassBuffer(TH3F::Class(), this, R__v, R__s, R__c);
4184 return;
4185 }
4186 //====process old versions before automatic schema evolution
4187 if (R__v < 2) {
4188 R__b.ReadVersion();
4189 TH1::Streamer(R__b);
4190 TArrayF::Streamer(R__b);
4191 R__b.ReadVersion(&R__s, &R__c);
4192 TAtt3D::Streamer(R__b);
4193 } else {
4194 TH3::Streamer(R__b);
4195 TArrayF::Streamer(R__b);
4196 R__b.CheckByteCount(R__s, R__c, TH3F::IsA());
4197 }
4198 //====end of old versions
4199
4200 } else {
4201 R__b.WriteClassBuffer(TH3F::Class(),this);
4202 }
4203}
4204
4205
4206////////////////////////////////////////////////////////////////////////////////
4207/// Operator =
4208
4210{
4211 if (this != &h1) ((TH3F&)h1).Copy(*this);
4212 return *this;
4213}
4214
4215
4216////////////////////////////////////////////////////////////////////////////////
4217/// Operator *
4218
4220{
4221 TH3F hnew = h1;
4222 hnew.Scale(c1);
4223 hnew.SetDirectory(0);
4224 return hnew;
4225}
4226
4227
4228////////////////////////////////////////////////////////////////////////////////
4229/// Operator +
4230
4232{
4233 TH3F hnew = h1;
4234 hnew.Add(&h2,1);
4235 hnew.SetDirectory(0);
4236 return hnew;
4237}
4238
4239
4240////////////////////////////////////////////////////////////////////////////////
4241/// Operator -
4242
4244{
4245 TH3F hnew = h1;
4246 hnew.Add(&h2,-1);
4247 hnew.SetDirectory(0);
4248 return hnew;
4249}
4250
4251
4252////////////////////////////////////////////////////////////////////////////////
4253/// Operator *
4254
4256{
4257 TH3F hnew = h1;
4258 hnew.Multiply(&h2);
4259 hnew.SetDirectory(0);
4260 return hnew;
4261}
4262
4263
4264////////////////////////////////////////////////////////////////////////////////
4265/// Operator /
4266
4268{
4269 TH3F hnew = h1;
4270 hnew.Divide(&h2);
4271 hnew.SetDirectory(0);
4272 return hnew;
4273}
4274
4275
4276//______________________________________________________________________________
4277// TH3D methods
4278// TH3D a 3-D histogram with eight bytes per cell (double)
4279//______________________________________________________________________________
4280
4281ClassImp(TH3D);
4282
4283
4284////////////////////////////////////////////////////////////////////////////////
4285/// Constructor.
4286
4288{
4289 SetBinsLength(27);
4290 if (fgDefaultSumw2) Sumw2();
4291}
4292
4293
4294////////////////////////////////////////////////////////////////////////////////
4295/// Destructor.
4296
4298{
4299}
4300
4301
4302////////////////////////////////////////////////////////////////////////////////
4303/// Normal constructor for fix bin size 3-D histograms.
4304
4305TH3D::TH3D(const char *name,const char *title,Int_t nbinsx,Double_t xlow,Double_t xup
4306 ,Int_t nbinsy,Double_t ylow,Double_t yup
4307 ,Int_t nbinsz,Double_t zlow,Double_t zup)
4308 :TH3(name,title,nbinsx,xlow,xup,nbinsy,ylow,yup,nbinsz,zlow,zup)
4309{
4311 if (fgDefaultSumw2) Sumw2();
4312
4313 if (xlow >= xup || ylow >= yup || zlow >= zup) SetBuffer(fgBufferSize);
4314}
4315
4316
4317////////////////////////////////////////////////////////////////////////////////
4318/// Normal constructor for variable bin size 3-D histograms.
4319
4320TH3D::TH3D(const char *name,const char *title,Int_t nbinsx,const Float_t *xbins
4321 ,Int_t nbinsy,const Float_t *ybins
4322 ,Int_t nbinsz,const Float_t *zbins)
4323 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
4324{
4326 if (fgDefaultSumw2) Sumw2();
4327}
4328
4329
4330////////////////////////////////////////////////////////////////////////////////
4331/// Normal constructor for variable bin size 3-D histograms.
4332
4333TH3D::TH3D(const char *name,const char *title,Int_t nbinsx,const Double_t *xbins
4334 ,Int_t nbinsy,const Double_t *ybins
4335 ,Int_t nbinsz,const Double_t *zbins)
4336 :TH3(name,title,nbinsx,xbins,nbinsy,ybins,nbinsz,zbins)
4337{
4339 if (fgDefaultSumw2) Sumw2();
4340}
4341
4342
4343////////////////////////////////////////////////////////////////////////////////
4344/// Copy constructor.
4345
4346TH3D::TH3D(const TH3D &h3d) : TH3(), TArrayD()
4347{
4348 ((TH3D&)h3d).Copy(*this);
4349}
4350
4351
4352////////////////////////////////////////////////////////////////////////////////
4353/// Copy this 3-D histogram structure to newth3.
4354
4355void TH3D::Copy(TObject &newth3) const
4356{
4357 TH3::Copy((TH3D&)newth3);
4358}
4359
4360
4361////////////////////////////////////////////////////////////////////////////////
4362/// Reset this histogram: contents, errors, etc.
4363
4365{
4366 TH3::Reset(option);
4368 // should also reset statistics once statistics are implemented for TH3
4369}
4370
4371
4372////////////////////////////////////////////////////////////////////////////////
4373/// Set total number of bins including under/overflow
4374/// Reallocate bin contents array
4375
4377{
4378 if (n < 0) n = (fXaxis.GetNbins()+2)*(fYaxis.GetNbins()+2)*(fZaxis.GetNbins()+2);
4379 fNcells = n;
4380 TArrayD::Set(n);
4381}
4382
4383
4384////////////////////////////////////////////////////////////////////////////////
4385/// Stream an object of class TH3D.
4386
4387void TH3D::Streamer(TBuffer &R__b)
4388{
4389 if (R__b.IsReading()) {
4390 UInt_t R__s, R__c;
4391 if (R__b.GetParent() && R__b.GetVersionOwner() < 22300) return;
4392 Version_t R__v = R__b.ReadVersion(&R__s, &R__c);
4393 if (R__v > 2) {
4394 R__b.ReadClassBuffer(TH3D::Class(), this, R__v, R__s, R__c);
4395 return;
4396 }
4397 //====process old versions before automatic schema evolution
4398 if (R__v < 2) {
4399 R__b.ReadVersion();
4400 TH1::Streamer(R__b);
4401 TArrayD::Streamer(R__b);
4402 R__b.ReadVersion(&R__s, &R__c);
4403 TAtt3D::Streamer(R__b);
4404 } else {
4405 TH3::Streamer(R__b);
4406 TArrayD::Streamer(R__b);
4407 R__b.CheckByteCount(R__s, R__c, TH3D::IsA());
4408 }
4409 //====end of old versions
4410
4411 } else {
4412 R__b.WriteClassBuffer(TH3D::Class(),this);
4413 }
4414}
4415
4416
4417////////////////////////////////////////////////////////////////////////////////
4418/// Operator =
4419
4421{
4422 if (this != &h1) ((TH3D&)h1).Copy(*this);
4423 return *this;
4424}
4425
4426
4427////////////////////////////////////////////////////////////////////////////////
4428/// Operator *
4429
4431{
4432 TH3D hnew = h1;
4433 hnew.Scale(c1);
4434 hnew.SetDirectory(0);
4435 return hnew;
4436}
4437
4438
4439////////////////////////////////////////////////////////////////////////////////
4440/// Operator +
4441
4443{
4444 TH3D hnew = h1;
4445 hnew.Add(&h2,1);
4446 hnew.SetDirectory(0);
4447 return hnew;
4448}
4449
4450
4451////////////////////////////////////////////////////////////////////////////////
4452/// Operator -
4453
4455{
4456 TH3D hnew = h1;
4457 hnew.Add(&h2,-1);
4458 hnew.SetDirectory(0);
4459 return hnew;
4460}
4461
4462
4463////////////////////////////////////////////////////////////////////////////////
4464/// Operator *
4465
4467{
4468 TH3D hnew = h1;
4469 hnew.Multiply(&h2);
4470 hnew.SetDirectory(0);
4471 return hnew;
4472}
4473
4474
4475////////////////////////////////////////////////////////////////////////////////
4476/// Operator /
4477
4479{
4480 TH3D hnew = h1;
4481 hnew.Divide(&h2);
4482 hnew.SetDirectory(0);
4483 return hnew;
4484}
#define c(i)
Definition RSha256.hxx:101
#define s1(x)
Definition RSha256.hxx:91
#define h(i)
Definition RSha256.hxx:106
#define e(i)
Definition RSha256.hxx:103
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:92
short Short_t
Definition RtypesCore.h:39
double Double_t
Definition RtypesCore.h:59
short Color_t
Definition RtypesCore.h:83
long long Long64_t
Definition RtypesCore.h:73
short Style_t
Definition RtypesCore.h:80
float Float_t
Definition RtypesCore.h:57
const Bool_t kTRUE
Definition RtypesCore.h:91
const char Option_t
Definition RtypesCore.h:66
#define ClassImp(name)
Definition Rtypes.h:364
#define R__ASSERT(e)
Definition TError.h:120
void Warning(const char *location, const char *msgfmt,...)
Use this function in warning situations.
Definition TError.cxx:231
char name[80]
Definition TGX11.cxx:110
TH3C operator/(TH3C &h1, TH3C &h2)
Operator /.
Definition TH3.cxx:3625
TH3C operator*(Float_t c1, TH3C &h1)
Operator *.
Definition TH3.cxx:3577
TH3C operator-(TH3C &h1, TH3C &h2)
Operator -.
Definition TH3.cxx:3601
TH3C operator+(TH3C &h1, TH3C &h2)
Operator +.
Definition TH3.cxx:3589
float xmin
int nentries
float ymin
float xmax
float ymax
#define gROOT
Definition TROOT.h:406
R__EXTERN TRandom * gRandom
Definition TRandom.h:62
#define gPad
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 * 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
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
Int_t fN
Definition TArray.h:38
virtual void Set(Int_t n)=0
Int_t GetSize() const
Definition TArray.h:47
Use this attribute class when an object should have 3D capabilities.
Definition TAtt3D.h:19
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:293
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:162
virtual void SetLabelSize(Float_t size=0.04)
Set size of axis labels.
Definition TAttAxis.cxx:203
virtual Style_t GetLabelFont() const
Definition TAttAxis.h:39
virtual void SetTitleFont(Style_t font=62)
Set the title font.
Definition TAttAxis.cxx:321
virtual void SetLabelOffset(Float_t offset=0.005)
Set distance between the axis and the labels.
Definition TAttAxis.cxx:192
virtual void SetLabelFont(Style_t font=62)
Set labels' font.
Definition TAttAxis.cxx:182
virtual void SetTitleSize(Float_t size=0.04)
Set size of axis title.
Definition TAttAxis.cxx:303
virtual void SetTitleColor(Color_t color=1)
Set color of axis title.
Definition TAttAxis.cxx:312
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 Float_t GetTitleOffset() const
Definition TAttAxis.h:43
virtual void SetTickLength(Float_t length=0.03)
Set tick mark length.
Definition TAttAxis.cxx:279
virtual void SetNdivisions(Int_t n=510, Bool_t optim=kTRUE)
Set the number of divisions for this axis.
Definition TAttAxis.cxx:228
virtual void SetLabelColor(Color_t color=1, Float_t alpha=1.)
Set color of labels.
Definition TAttAxis.cxx:172
virtual Color_t GetFillColor() const
Return the fill area color.
Definition TAttFill.h:30
virtual void SetFillColor(Color_t fcolor)
Set the fill area color.
Definition TAttFill.h:37
virtual Color_t GetLineColor() const
Return the line color.
Definition TAttLine.h:33
virtual void SetLineColor(Color_t lcolor)
Set the line color.
Definition TAttLine.h:40
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 void SetMarkerStyle(Style_t mstyle=1)
Set the marker style.
Definition TAttMarker.h:40
Class to manage histogram axis.
Definition TAxis.h:30
virtual void SetBinLabel(Int_t bin, const char *label)
Set label for bin.
Definition TAxis.cxx:823
virtual Double_t GetBinCenter(Int_t bin) const
Return center of bin.
Definition TAxis.cxx:478
Bool_t CanExtend() const
Definition TAxis.h:82
const TArrayD * GetXbins() const
Definition TAxis.h:130
Double_t GetXmax() const
Definition TAxis.h:134
@ kAxisRange
Definition TAxis.h:61
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 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
Int_t GetLast() const
Return last bin on the axis i.e.
Definition TAxis.cxx:469
virtual void ImportAttributes(const TAxis *axis)
Copy axis attributes to this.
Definition TAxis.cxx:631
Double_t GetXmin() const
Definition TAxis.h:133
Int_t GetNbins() const
Definition TAxis.h:121
const char * GetTitle() const
Returns title of object.
Definition TAxis.h:129
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
Buffer base class used for serializing objects.
Definition TBuffer.h:43
virtual Int_t ReadClassBuffer(const TClass *cl, void *pointer, const TClass *onfile_class=0)=0
TObject * GetParent() const
Return pointer to parent of this buffer.
Definition TBuffer.cxx:262
virtual Version_t ReadVersion(UInt_t *start=0, UInt_t *bcnt=0, const TClass *cl=0)=0
virtual Int_t CheckByteCount(UInt_t startpos, UInt_t bcnt, const TClass *clss)=0
virtual Int_t GetVersionOwner() const =0
Bool_t IsReading() const
Definition TBuffer.h:86
virtual Int_t WriteClassBuffer(const TClass *cl, void *pointer)=0
1-Dim function class
Definition TF1.h:213
virtual TH1 * GetHistogram() const
Return a pointer to the histogram used to visualise the function Note that this histogram is managed ...
Definition TF1.cxx:1574
virtual Double_t GetParError(Int_t ipar) const
Return value of parameter number ipar.
Definition TF1.cxx:1920
Double_t GetChisquare() const
Definition TF1.h:444
virtual void SetRange(Double_t xmin, Double_t xmax)
Initialize the upper and lower bounds to draw the function.
Definition TF1.cxx:3532
virtual Int_t GetNpar() const
Definition TF1.h:481
virtual Int_t GetNumberFitPoints() const
Definition TF1.h:503
virtual Double_t * GetParameters() const
Definition TF1.h:520
virtual Double_t EvalPar(const Double_t *x, const Double_t *params=0)
Evaluate function with given coordinates and parameters.
Definition TF1.cxx:1463
virtual void GetRange(Double_t *xmin, Double_t *xmax) const
Return range of a generic N-D function.
Definition TF1.cxx:2269
virtual const char * GetParName(Int_t ipar) const
Definition TF1.h:529
virtual void SetParameters(const Double_t *params)
Definition TF1.h:644
virtual Double_t GetParameter(Int_t ipar) const
Definition TF1.h:512
A 3-Dim function with parameters.
Definition TF3.h:28
1-D histogram with a double per channel (see TH1 documentation)}
Definition TH1.h:618
virtual void Reset(Option_t *option="")
Reset.
Definition TH1.cxx:9947
TH1 is the base class of all histogram classes in ROOT.
Definition TH1.h:58
virtual void SetDirectory(TDirectory *dir)
By default when an histogram is created, it is added to the list of histogram objects in the current ...
Definition TH1.cxx:8777
Double_t * fBuffer
[fBufferSize] entry buffer
Definition TH1.h:107
virtual Double_t GetEffectiveEntries() const
Number of effective entries of the histogram.
Definition TH1.cxx:4411
TAxis * GetZaxis()
Definition TH1.h:322
virtual Bool_t Multiply(TF1 *f1, Double_t c1=1)
Performs the operation:
Definition TH1.cxx:5980
Int_t fNcells
number of bins(1D), cells (2D) +U/Overflows
Definition TH1.h:88
Double_t fTsumw
Total Sum of weights.
Definition TH1.h:95
Double_t fTsumw2
Total Sum of squares of weights.
Definition TH1.h:96
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:7870
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:7500
virtual Int_t GetNbinsY() const
Definition TH1.h:297
virtual void AddBinContent(Int_t bin)
Increment bin content by 1.
Definition TH1.cxx:1257
virtual Double_t GetBinError(Int_t bin) const
Return value of error associated to bin number bin.
Definition TH1.cxx:8903
virtual Int_t GetNbinsZ() const
Definition TH1.h:298
virtual Int_t GetDimension() const
Definition TH1.h:282
@ kIsNotW
Histogram is forced to be not weighted even when the histogram is filled with weighted different than...
Definition TH1.h:171
virtual Bool_t CanExtendAllAxes() const
Returns true if all axes are extendable.
Definition TH1.cxx:6596
virtual void Reset(Option_t *option="")
Reset this histogram: contents, errors, etc.
Definition TH1.cxx:7069
TAxis * GetXaxis()
Get the behaviour adopted by the object about the statoverflows. See EStatOverflows for more informat...
Definition TH1.h:320
virtual Int_t GetNcells() const
Definition TH1.h:299
virtual void PutStats(Double_t *stats)
Replace current statistics with the values in array stats.
Definition TH1.cxx:7777
TVirtualHistPainter * GetPainter(Option_t *option="")
Return pointer to painter.
Definition TH1.cxx:4452
TObject * Clone(const char *newname=0) const
Make a complete copy of the underlying object.
Definition TH1.cxx:2740
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:3892
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:4893
virtual Int_t GetNbinsX() const
Definition TH1.h:296
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:822
Int_t fBufferSize
fBuffer size
Definition TH1.h:106
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:9280
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:9046
static Int_t fgBufferSize
!default buffer size for automatic histograms
Definition TH1.h:114
TAxis * GetYaxis()
Definition TH1.h:321
UInt_t GetAxisLabelStatus() const
Internal function used in TH1::Fill to see which axis is full alphanumeric i.e.
Definition TH1.cxx:6635
Double_t * fIntegral
!Integral of bins used by GetRandom
Definition TH1.h:110
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:9062
@ kNstat
Definition TH1.h:183
virtual Double_t GetBinLowEdge(Int_t bin) const
Return bin lower edge for 1D histogram.
Definition TH1.cxx:8992
virtual Double_t GetEntries() const
Return the current number of entries.
Definition TH1.cxx:4386
virtual void Copy(TObject &hnew) const
Copy this histogram structure to newth1.
Definition TH1.cxx:2663
virtual void Draw(Option_t *option="")
Draw this histogram with options.
Definition TH1.cxx:3073
virtual void ResetStats()
Reset the statistics including the number of entries and replace with values calculated from bin cont...
Definition TH1.cxx:7795
virtual void SetBuffer(Int_t buffersize, Option_t *option="")
Set the maximum number of entries to be kept in the buffer.
Definition TH1.cxx:8306
@ kXaxis
Definition TH1.h:72
@ kAllAxes
Definition TH1.h:75
@ kZaxis
Definition TH1.h:74
@ kYaxis
Definition TH1.h:73
Double_t fEntries
Number of entries.
Definition TH1.h:94
virtual void SetName(const char *name)
Change the name of this histogram.
Definition TH1.cxx:8800
TAxis fZaxis
Z axis descriptor.
Definition TH1.h:91
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:9290
virtual Double_t GetBinContent(Int_t bin) const
Return content of bin number bin.
Definition TH1.cxx:4993
TAxis fXaxis
X axis descriptor.
Definition TH1.h:89
virtual void ExtendAxis(Double_t x, TAxis *axis)
Histogram is resized along axis such that x is in the axis range.
Definition TH1.cxx:6464
TArrayD fSumw2
Array of sum of squares of weights.
Definition TH1.h:103
virtual void Scale(Double_t c1=1, Option_t *option="")
Multiply this histogram by a constant c1.
Definition TH1.cxx:6564
virtual void Paint(Option_t *option="")
Control routine to paint any kind of histograms.
Definition TH1.cxx:6155
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:3680
Bool_t GetStatOverflowsBehaviour() const
Definition TH1.h:152
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:2828
TAxis fYaxis
Y axis descriptor.
Definition TH1.h:90
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:8607
virtual void Sumw2(Bool_t flag=kTRUE)
Create structure to store sum of squares of weights.
Definition TH1.cxx:8860
virtual void SetEntries(Double_t n)
Definition TH1.h:385
static Bool_t fgDefaultSumw2
!flag to call TH1::Sumw2 automatically at histogram creation time
Definition TH1.h:117
Double_t fTsumwx
Total Sum of weight*X.
Definition TH1.h:97
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:2530
2-D histogram with a double per channel (see TH1 documentation)}
Definition TH2.h:292
virtual void Reset(Option_t *option="")
Reset this histogram: contents, errors, etc.
Definition TH2.cxx:3846
virtual void PutStats(Double_t *stats)
Replace current statistics with the values in array stats.
Definition TH2.cxx:2376
virtual void SetBinContent(Int_t bin, Double_t content)
Set bin content.
Definition TH2.cxx:2507
3-D histogram with a byte per channel (see TH1 documentation)
Definition TH3.h:159
virtual void Copy(TObject &hnew) const
Copy this 3-D histogram structure to newth3.
Definition TH3.cxx:3473
virtual void Reset(Option_t *option="")
Reset this histogram: contents, errors, etc.
Definition TH3.cxx:3482
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH3.cxx:3494
TH3C & operator=(const TH3C &h1)
Operator =.
Definition TH3.cxx:3567
virtual void AddBinContent(Int_t bin)
Increment bin content by 1.
Definition TH3.cxx:3452
TH3C()
Constructor.
Definition TH3.cxx:3384
virtual ~TH3C()
Destructor.
Definition TH3.cxx:3394
3-D histogram with a double per channel (see TH1 documentation)}
Definition TH3.h:305
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH3.cxx:4376
TH3D()
Constructor.
Definition TH3.cxx:4287
virtual void Copy(TObject &hnew) const
Copy this 3-D histogram structure to newth3.
Definition TH3.cxx:4355
TH3D & operator=(const TH3D &h1)
Operator =.
Definition TH3.cxx:4420
virtual ~TH3D()
Destructor.
Definition TH3.cxx:4297
3-D histogram with a float per channel (see TH1 documentation)}
Definition TH3.h:268
TH3F & operator=(const TH3F &h1)
Operator =.
Definition TH3.cxx:4209
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH3.cxx:4165
TH3F()
Constructor.
Definition TH3.cxx:4076
virtual ~TH3F()
Destructor.
Definition TH3.cxx:4086
virtual void Copy(TObject &hnew) const
Copy this 3-D histogram structure to newth3.
Definition TH3.cxx:4144
3-D histogram with an int per channel (see TH1 documentation)}
Definition TH3.h:231
virtual void Copy(TObject &hnew) const
Copy this 3-D histogram structure to newth3.
Definition TH3.cxx:3966
TH3I & operator=(const TH3I &h1)
Operator =.
Definition TH3.cxx:3998
TH3I()
Constructor.
Definition TH3.cxx:3877
virtual void AddBinContent(Int_t bin)
Increment bin content by 1.
Definition TH3.cxx:3945
virtual ~TH3I()
Destructor.
Definition TH3.cxx:3887
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH3.cxx:3987
3-D histogram with a short per channel (see TH1 documentation)
Definition TH3.h:195
virtual void AddBinContent(Int_t bin)
Increment bin content by 1.
Definition TH3.cxx:3713
virtual void SetBinsLength(Int_t n=-1)
Set total number of bins including under/overflow Reallocate bin contents array.
Definition TH3.cxx:3755
virtual ~TH3S()
Destructor.
Definition TH3.cxx:3655
TH3S & operator=(const TH3S &h1)
Operator =.
Definition TH3.cxx:3799
TH3S()
Constructor.
Definition TH3.cxx:3645
virtual void Copy(TObject &hnew) const
Copy this 3-D histogram structure to newth3.
Definition TH3.cxx:3734
The 3-D histogram classes derived from the 1-D histogram classes.
Definition TH3.h:31
virtual TH3 * Rebin3D(Int_t nxgroup=2, Int_t nygroup=2, Int_t nzgroup=2, const char *newname="")
Rebin this histogram grouping nxgroup/nygroup/nzgroup bins along the xaxis/yaxis/zaxis together.
Definition TH3.cxx:2828
Int_t Fill(Double_t)
Invalid Fill method.
Definition TH3.cxx:287
Double_t fTsumwy
Definition TH3.h:34
virtual void FillRandom(const char *fname, Int_t ntimes=5000, TRandom *rng=nullptr)
Fill histogram following distribution in function fname.
Definition TH3.cxx:742
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 TH3.cxx:1216
Double_t fTsumwy2
Definition TH3.h:35
virtual Double_t GetCovariance(Int_t axis1=1, Int_t axis2=2) const
Return covariance between axis1 and axis2.
Definition TH3.cxx:1118
virtual Int_t BufferEmpty(Int_t action=0)
Fill histogram with all entries in the buffer.
Definition TH3.cxx:184
virtual TH2D * DoProject2D(const char *name, const char *title, const TAxis *projX, const TAxis *projY, bool computeErrors, bool originalRange, bool useUF, bool useOF) const
internal method performing the projection to a 2D histogram called from TH3::Project3D
Definition TH3.cxx:2011
Double_t fTsumwxz
Definition TH3.h:39
virtual TH1D * ProjectionY(const char *name="_py", Int_t ixmin=0, Int_t ixmax=-1, Int_t izmin=0, Int_t izmax=-1, Option_t *option="") const
Project a 3-D histogram into a 1-D histogram along Y.
Definition TH3.cxx:1689
virtual void GetRandom3(Double_t &x, Double_t &y, Double_t &, TRandom *rng=nullptr)
Return 3 random numbers along axis x , y and z distributed according to the cell-contents of this 3-d...
Definition TH3.cxx:1168
virtual Int_t GetBin(Int_t binx, Int_t biny, Int_t binz) const
See comments in TH1::GetBin.
Definition TH3.cxx:1026
virtual void Reset(Option_t *option="")
Reset this histogram: contents, errors, etc.
Definition TH3.cxx:3320
virtual Double_t Integral(Option_t *option="") const
Return integral of bin contents.
Definition TH3.cxx:1299
virtual void Copy(TObject &hnew) const
Copy.
Definition TH3.cxx:163
virtual ~TH3()
Destructor.
Definition TH3.cxx:155
virtual TH3 * RebinY(Int_t ngroup=2, const char *newname="")
Rebin only the Y axis see Rebin3D.
Definition TH3.cxx:2787
virtual Double_t IntegralAndError(Int_t binx1, Int_t binx2, Int_t biny1, Int_t biny2, Int_t binz1, Int_t binz2, Double_t &err, Option_t *option="") const
Return integral of bin contents in range [binx1,binx2],[biny1,biny2],[binz1,binz2] for a 3-D histogra...
Definition TH3.cxx:1330
virtual TH1D * ProjectionZ(const char *name="_pz", Int_t ixmin=0, Int_t ixmax=-1, Int_t iymin=0, Int_t iymax=-1, Option_t *option="") const
Project a 3-D histogram into a 1-D histogram along Z.
Definition TH3.cxx:1721
virtual TH1D * ProjectionX(const char *name="_px", Int_t iymin=0, Int_t iymax=-1, Int_t izmin=0, Int_t izmax=-1, Option_t *option="") const
Project a 3-D histogram into a 1-D histogram along X.
Definition TH3.cxx:1656
virtual TProfile2D * Project3DProfile(Option_t *option="xy") const
Project a 3-d histogram into a 2-d profile histograms depending on the option parameter option may co...
Definition TH3.cxx:2677
Double_t fTsumwz2
Definition TH3.h:38
virtual Double_t GetBinContent(Int_t bin) const
Return content of bin number bin.
Definition TH3.h:96
Double_t fTsumwxy
Definition TH3.h:36
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 TH3.cxx:1441
virtual void FitSlicesZ(TF1 *f1=0, Int_t binminx=1, Int_t binmaxx=0, Int_t binminy=1, Int_t binmaxy=0, Int_t cut=0, Option_t *option="QNR")
Project slices along Z in case of a 3-D histogram, then fit each slice with function f1 and make a 2-...
Definition TH3.cxx:887
virtual TH1 * Project3D(Option_t *option="x") const
Project a 3-d histogram into 1 or 2-d histograms depending on the option parameter,...
Definition TH3.cxx:2313
virtual void PutStats(Double_t *stats)
Replace current statistics with the values in array stats.
Definition TH3.cxx:2760
virtual Double_t GetBinWithContent3(Double_t c, Int_t &binx, Int_t &biny, Int_t &binz, Int_t firstx=0, Int_t lastx=0, Int_t firsty=0, Int_t lasty=0, Int_t firstz=0, Int_t lastz=0, Double_t maxdiff=0) const
Compute first cell (binx,biny,binz) in the range [firstx,lastx](firsty,lasty][firstz,...
Definition TH3.cxx:1060
virtual TH3 * RebinX(Int_t ngroup=2, const char *newname="")
Rebin only the X axis see Rebin3D.
Definition TH3.cxx:2777
void DoFillProfileProjection(TProfile2D *p2, const TAxis &a1, const TAxis &a2, const TAxis &a3, Int_t bin1, Int_t bin2, Int_t bin3, Int_t inBin, Bool_t useWeights) const
internal function to fill the bins of the projected profile 2D histogram called from DoProjectProfile...
Definition TH3.cxx:2445
virtual void SetBinContent(Int_t bin, Double_t content)
Set bin content.
Definition TH3.cxx:3339
virtual TH3 * RebinZ(Int_t ngroup=2, const char *newname="")
Rebin only the Z axis see Rebin3D.
Definition TH3.cxx:2797
virtual Int_t BufferFill(Double_t x, Double_t y, Double_t z, Double_t w)
accumulate arguments in buffer.
Definition TH3.cxx:258
virtual Double_t Interpolate(Double_t x, Double_t y) const
Not yet implemented.
Definition TH3.cxx:1350
virtual void SetShowProjection(const char *option="xy", Int_t nbins=1)
When the mouse is moved in a pad containing a 3-d view of this histogram a second canvas shows a proj...
Definition TH3.cxx:3523
virtual Double_t GetCorrelationFactor(Int_t axis1=1, Int_t axis2=2) const
Return correlation factor between axis1 and axis2.
Definition TH3.cxx:1100
virtual TH1D * DoProject1D(const char *name, const char *title, int imin1, int imax1, int imin2, int imax2, const TAxis *projAxis, const TAxis *axis1, const TAxis *axis2, Option_t *option) const
internal method performing the projection to 1D histogram called from TH3::Project3D
Definition TH3.cxx:1738
Double_t fTsumwz
Definition TH3.h:37
Double_t fTsumwyz
Definition TH3.h:40
TH3()
Default constructor.
Definition TH3.cxx:64
virtual TProfile2D * DoProjectProfile2D(const char *name, const char *title, const TAxis *projX, const TAxis *projY, bool originalRange, bool useUF, bool useOF) const
internal method to project to a 2D Profile called from TH3::Project3DProfile
Definition TH3.cxx:2471
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
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
Collectable string class.
Definition TObjString.h:28
TString & String()
Definition TObjString.h:48
Mother of all ROOT objects.
Definition TObject.h:37
virtual const char * GetName() const
Returns name of object.
Definition TObject.cxx:359
R__ALWAYS_INLINE Bool_t TestBit(UInt_t f) const
Definition TObject.h:187
virtual const char * ClassName() const
Returns name of class to which the object belongs.
Definition TObject.cxx:130
virtual void Warning(const char *method, const char *msgfmt,...) const
Issue warning message.
Definition TObject.cxx:879
virtual TObject * FindObject(const char *name) const
Must be redefined in derived classes.
Definition TObject.cxx:323
void SetBit(UInt_t f, Bool_t set)
Set or unset the user status bits as specified in f.
Definition TObject.cxx:696
virtual Bool_t InheritsFrom(const char *classname) const
Returns kTRUE if object inherits from class "classname".
Definition TObject.cxx:445
virtual void Error(const char *method, const char *msgfmt,...) const
Issue error message.
Definition TObject.cxx:893
virtual void Info(const char *method, const char *msgfmt,...) const
Issue info message.
Definition TObject.cxx:867
Profile2D histograms are used to display the mean value of Z and its error for each cell in X,...
Definition TProfile2D.h:27
Int_t Fill(const Double_t *v)
Definition TProfile2D.h:51
virtual void Reset(Option_t *option="")
Reset contents of a Profile2D histogram.
void SetBins(const Int_t *nbins, const Double_t *range)
Definition TProfile2D.h:49
virtual void Sumw2(Bool_t flag=kTRUE)
Create/Delete structure to store sum of squares of weights per bin.
virtual void PutStats(Double_t *stats)
Replace current statistics with the values in array stats.
virtual TArrayD * GetBinSumw2()
Definition TProfile2D.h:116
This is the base class for the ROOT Random number generators.
Definition TRandom.h:27
virtual Double_t Rndm()
Machine independent random number generator.
Definition TRandom.cxx:552
Basic string class.
Definition TString.h:136
void ToLower()
Change string to lower-case.
Definition TString.cxx:1145
Ssiz_t First(char c) const
Find first occurrence of a character c.
Definition TString.cxx:519
const char * Data() const
Definition TString.h:369
void ToUpper()
Change string to upper case.
Definition TString.cxx:1158
TString & Remove(Ssiz_t pos)
Definition TString.h:673
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:2331
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
virtual void SetShowProjection(const char *option, Int_t nbins)=0
TVirtualPad is an abstract base class for the Pad and Canvas classes.
Definition TVirtualPad.h:51
virtual TVirtualPad * GetSelectedPad() const =0
virtual TVirtualPad * cd(Int_t subpadnumber=0)=0
void Draw(Option_t *option="") override=0
Default Draw method for all objects.
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
Short_t Max(Short_t a, Short_t b)
Definition TMathBase.h:212
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
Bool_t Permute(Int_t n, Int_t *a)
Simple recursive algorithm to find the permutations of n natural numbers, not necessarily all distinc...
Definition TMath.cxx:2517
Double_t QuietNaN()
Returns a quiet NaN as defined by IEEE 754
Definition TMath.h:901
Double_t Floor(Double_t x)
Definition TMath.h:703
Double_t Log(Double_t x)
Definition TMath.h:760
Double_t Mean(Long64_t n, const T *a, const Double_t *w=0)
Return the weighted mean of an array a with length n.
Definition TMath.h:1073
Double_t Sqrt(Double_t x)
Definition TMath.h:691
Double_t KolmogorovProb(Double_t z)
Calculates the Kolmogorov distribution function,.
Definition TMath.cxx:656
Long64_t BinarySearch(Long64_t n, const T *array, T value)
Definition TMathBase.h:278
Short_t Abs(Short_t d)
Definition TMathBase.h:120