GRSISort "v4.0.0.5"
An extension of the ROOT analysis Framework
Loading...
Searching...
No Matches
TPeak.cxx
Go to the documentation of this file.
1#include "TPeak.h"
2#include "TGraph.h"
3#include "Math/MinimizerOptions.h"
4#include "TVirtualFitter.h"
5#include "TFitResult.h"
6#include "TList.h"
7
8#include "Globals.h"
9#include "TGRSIFunctions.h"
10
11Bool_t TPeak::fLogLikelihoodFlag = true;
12TPeak* TPeak::fLastFit = nullptr;
13
14TPeak::TPeak(Double_t cent, Double_t xlow, Double_t xhigh, TF1* background)
15 : TGRSIFit("photopeakbg", TGRSIFunctions::PhotoPeakBG, xlow, xhigh, 10), fResiduals(new TGraph)
16{
17 Clear();
18 Bool_t outOfRangeFlag = false;
19
20 if(cent > xhigh) {
21 std::cout << "centroid is higher than range" << std::endl;
22 outOfRangeFlag = true;
23 } else if(cent < xlow) {
24 std::cout << "centroid is lower than range" << std::endl;
25 outOfRangeFlag = true;
26 }
27
28 // This fixes things if your user is like me and screws up a lot.
29 if(outOfRangeFlag) {
30 if(xlow > cent) {
31 std::swap(xlow, cent);
32 }
33 if(xlow > xhigh) {
34 std::swap(xlow, xhigh);
35 }
36 if(cent > xhigh) {
37 std::swap(cent, xhigh);
38 }
39 std::cout << "Something about your range was wrong. Assuming:" << std::endl;
40 std::cout << "centroid: " << cent << " \t range: " << xlow << " to " << xhigh << std::endl;
41 }
42
43 SetRange(xlow, xhigh);
44 // We also need to make initial guesses at parameters
45 // We need nice ways to access parameters etc.
46 // Need to make a TMultipeak-like thing (does a helper class come into play then?)
47
48 // Set the fit function to be a radware style photo peak.
49 // This function might be unnecessary. Will revist this later. rd.
50 SetName(Form("Chan%d_%d_to_%d", static_cast<Int_t>(cent), static_cast<Int_t>(xlow),
51 static_cast<Int_t>(xhigh))); // Gives a default name to the peak
52
53 // We need to set parameter names now.
54 InitNames();
55 SetParameter("centroid", cent);
56
57 // Check to see if background is good.
58 if(background != nullptr) {
59 fBackground = background;
60 fOwnBgFlag = false;
61 } else {
62 fBackground = new TF1(
63 Form("background%d_%d_to_%d", static_cast<Int_t>(cent), static_cast<Int_t>(xlow), static_cast<Int_t>(xhigh)),
64 TGRSIFunctions::StepBG, xlow, xhigh, 10);
66 fOwnBgFlag = true;
67 }
68
69 fBackground->SetNpx(1000);
70 fBackground->SetLineStyle(2);
71 fBackground->SetLineColor(kBlack);
72}
73
74TPeak::TPeak() : TGRSIFit("photopeakbg", TGRSIFunctions::PhotoPeakBG, 0, 1000, 10),
75 fBackground(new TF1("background", TGRSIFunctions::StepBG, 0, 1000, 10)), fResiduals(new TGraph)
76{
77 InitNames();
78 fBackground->SetNpx(1000);
79 fBackground->SetLineStyle(2);
80 fBackground->SetLineColor(kBlack);
82}
83
85{
86 if(fOwnBgFlag) {
87 delete fBackground;
88 }
89 delete fResiduals;
90}
91
92TPeak::TPeak(const TPeak& copy) : TGRSIFit(copy)
93{
94 copy.Copy(*this);
95}
96
98{
99 SetParName(0, "Height");
100 SetParName(1, "centroid");
101 SetParName(2, "sigma");
102 SetParName(3, "beta");
103 SetParName(4, "R");
104 SetParName(5, "step");
105 SetParName(6, "A");
106 SetParName(7, "B");
107 SetParName(8, "C");
108 SetParName(9, "bg_offset");
109}
110
111void TPeak::Copy(TObject& obj) const
112{
113 TGRSIFit::Copy(obj);
114
115 if(static_cast<TPeak&>(obj).fBackground == nullptr) {
116 static_cast<TPeak&>(obj).fBackground = new TF1(*fBackground);
117 }
118 if(static_cast<TPeak&>(obj).fResiduals == nullptr) {
119 static_cast<TPeak&>(obj).fResiduals = new TGraph(*fResiduals);
120 }
121
122 static_cast<TPeak&>(obj).fArea = fArea;
123 static_cast<TPeak&>(obj).fDArea = fDArea;
124
125 static_cast<TPeak&>(obj).fChi2 = fChi2;
126 static_cast<TPeak&>(obj).fNdf = fNdf;
127
128 *(static_cast<TPeak&>(obj).fBackground) = *fBackground;
129 // We are making a direct copy of the background so the ownership is that of the copy
130 static_cast<TPeak&>(obj).fOwnBgFlag = true;
131 *(static_cast<TPeak&>(obj).fResiduals) = *fResiduals;
132
133 static_cast<TPeak&>(obj).SetHist(GetHist());
134}
135
136Bool_t TPeak::InitParams(TH1* fitHist)
137{
138 // Makes initial guesses at parameters for the fit. Uses the histogram to
139 if(fitHist == nullptr) {
140 return false;
141 }
142 Double_t xlow = 0.;
143 Double_t xhigh = 0.;
144 GetRange(xlow, xhigh);
145 Int_t bin = fitHist->FindBin(GetParameter("centroid"));
146 Int_t binlow = fitHist->GetXaxis()->FindBin(xlow);
147 Int_t binhigh = fitHist->GetXaxis()->FindBin(xhigh);
148 SetParLimits(0, 0, fitHist->GetMaximum());
149 Double_t low = 0.;
150 Double_t high = 0.;
151 GetParLimits(1, low, high);
152 if(low == high && low == 0.) {
153 SetParLimits(1, xlow, xhigh);
154 }
155 GetParLimits(2, low, high);
156 if(low == high && low == 0.) {
157 SetParLimits(2, 0.5, (xhigh - xlow)); // sigma should be less than the window width - JKS
158 }
159 SetParLimits(3, 0.000001, 10);
160 SetParLimits(4, 0.000001, 100); // this is a percentage. no reason for it to go to 500% - JKS
161 // Step size is allow to vary to anything. If it goes below 0, the code will fix it to 0
162 SetParLimits(5, 0.0, 1.0E2);
163 SetParLimits(6, 0.0, fitHist->GetBinContent(bin) * 100.);
164 SetParLimits(9, xlow, xhigh);
165
166 if((fitHist == nullptr) && (GetHist() != nullptr)) {
167 fitHist = GetHist();
168 }
169
170 if(fitHist == nullptr) {
171 std::cout << "No histogram is associated yet, no initial guesses made" << std::endl;
172 return false;
173 }
174 // Make initial guesses
175 // Actually set the parameters in the photopeak function
176 // Fixing has to come after setting
177 // Might have to include bin widths eventually
178 // The centroid should already be set by this point in the ctor
179 SetParameter("Height", fitHist->GetBinContent(bin));
180 SetParameter("centroid", GetParameter("centroid"));
181 SetParameter("sigma", TMath::Sqrt(9.0 + 4. * GetParameter("centroid") / 1000.) / 2.35);
182 SetParameter("beta", GetParameter("sigma") / 2.0);
183 SetParameter("R", 0.001);
184 SetParameter("step", 1.0);
185 SetParameter("A", fitHist->GetBinContent(binhigh));
186 SetParameter("B", (fitHist->GetBinContent(binlow) - fitHist->GetBinContent(binhigh)) / (xlow - xhigh));
187 SetParameter("C", 0.0000);
188 SetParameter("bg_offset", GetParameter("centroid"));
189 FixParameter(8, 0.00);
190 FixParameter(3, GetParameter("beta"));
191 FixParameter(4, 0.00);
193 return true;
194}
195
196Bool_t TPeak::Fit(TH1* fitHist, Option_t* opt)
197{
198 TString options = opt;
199 options.ToLower();
200 bool quiet = options.Contains("q");
201 bool verbose = options.Contains("v");
202 if(quiet && verbose) {
203 std::cout << "Don't know how to be quiet and verbose at once (" << opt << "), going to be verbose!" << std::endl;
204 quiet = false;
205 }
206 bool retryFit = options.Contains("retryfit");
207 options.ReplaceAll("retryfit", "");
208 if(!verbose && !quiet) { options.Append("q"); }
209
210 if(fitHist == nullptr && GetHist() == nullptr) {
211 std::cout << "No hist passed, trying something... ";
212 fitHist = fHistogram;
213 }
214 if(fitHist == nullptr) {
215 std::cout << "No histogram associated with Peak" << std::endl;
216 return false;
217 }
218 if(!IsInitialized()) {
219 InitParams(fitHist);
220 }
221 ROOT::Math::MinimizerOptions::SetDefaultMinimizer("Minuit2", "Combination");
222 TVirtualFitter::SetMaxIterations(100000);
223 TVirtualFitter::SetPrecision(1e-3);
224
225 SetHist(fitHist);
226
227 // Now that it is initialized, let's fit it.
228 // Just in case the range changed, we should reset the centroid and bg energy limits
229 // check first if the parameter has been fixed!
230 std::vector<double> lowerLimit(GetNpar());
231 std::vector<double> upperLimit(GetNpar());
232 for(int i = 0; i < GetNpar(); ++i) {
233 GetParLimits(i, lowerLimit[i], upperLimit[i]);
234 if(i < 2) { // height, and centroid
235 FixParameter(i, GetParameter(i));
236 }
237 }
238
239 TFitResultPtr fitres;
240 // Log likelihood is the proper fitting technique UNLESS the data is a result of an addition or subtraction.
242 fitres = fitHist->Fit(this, Form("%sRLSN", options.Data())); // The RS needs to always be there
243 } else {
244 fitres = fitHist->Fit(this, Form("%sRSN", options.Data())); // The RS needs to always be there
245 }
246
247 // Check fit exited successfully before continuing
248 if(static_cast<int>(fitres) == -1) { return false; }
249
250 for(int i = 0; i < GetNpar(); ++i) {
251 SetParLimits(i, lowerLimit[i], upperLimit[i]);
252 }
253
254 // Log likelihood is the proper fitting technique UNLESS the data is a result of an addition or subtraction.
256 fitres = fitHist->Fit(this, Form("%sRLS", options.Data())); // The RS needs to always be there
257 } else {
258 fitres = fitHist->Fit(this, Form("%sRS", options.Data())); // The RS needs to always be there
259 }
260
261 // Check fit exited successfully before continuing
262 if(static_cast<int>(fitres) == -1) { return false; }
263
264 // After performing this fit I want to put something here that takes the fit result (good,bad,etc)
265 // for printing out. RD
266
267 if(fitres->ParError(2) != fitres->ParError(2)) { // Check to see if nan
268 if(fitres->Parameter(3) < 1) {
269 InitParams(fitHist);
270 FixParameter(4, 0);
271 FixParameter(3, 1);
272 if(verbose) { std::cout << "Beta may have broken the fit, retrying with R=0" << std::endl; }
273 // Leaving the log-likelihood argument out so users are not constrained to just using that. - JKS
274 fitHist->GetListOfFunctions()->Last()->Delete();
276 fitres = fitHist->Fit(this, Form("%sRLS", options.Data())); // The RS needs to always be there
277 } else {
278 fitres = fitHist->Fit(this, Form("%sRS", options.Data()));
279 }
280 }
281 }
282
283 // check parameter errors
284 if(!TGRSIFunctions::CheckParameterErrors(fitres, options.Data())) {
285 if(retryFit) {
286 // fit again with all parameters released
287 if(!quiet) { std::cout << GREEN << "Re-fitting with released parameters (without any limits)" << RESET_COLOR << std::endl; }
288 for(int i = 0; i < GetNpar(); ++i) {
289 ReleaseParameter(i);
290 }
292 fitres = fitHist->Fit(this, Form("%sRLS", options.Data())); // The RS needs to always be there
293 } else {
294 fitres = fitHist->Fit(this, Form("%sRS", options.Data()));
295 }
296 } else {
297 // re-try using minos instead of minuit
298 if(!quiet) { std::cout << YELLOW << "Re-fitting with \"E\" option to get better error estimation using Minos technique." << RESET_COLOR << std::endl; }
300 fitres = fitHist->Fit(this, Form("%sERLS", options.Data())); // The RS needs to always be there
301 } else {
302 fitres = fitHist->Fit(this, Form("%sERS", options.Data()));
303 }
304 }
305 }
307
308 Double_t binWidth = fitHist->GetBinWidth(1);
309 Double_t width = GetParameter("sigma");
310 if(verbose) {
311 std::cout << "Chi^2/NDF = " << fitres->Chi2() / fitres->Ndf() << std::endl;
312 }
313 fChi2 = fitres->Chi2();
314 fNdf = fitres->Ndf();
315 Double_t xlow = 0.;
316 Double_t xhigh = 0.;
317 GetRange(xlow, xhigh);
318 Double_t int_low = xlow - 10. * width; // making the integration bounds a bit smaller, but still large enough. -JKS
319 Double_t int_high = xhigh + 10. * width;
320
321 // Make a function that does not include the background
322 // Integrate the background.
323 // TPeak* tmppeak = new TPeak(*this);
324 auto* tmppeak = new TPeak;
325 Copy(*tmppeak);
326 tmppeak->SetParameter("step", 0.0);
327 tmppeak->SetParameter("A", 0.0);
328 tmppeak->SetParameter("B", 0.0);
329 tmppeak->SetParameter("C", 0.0);
330 tmppeak->SetParameter("bg_offset", 0.0);
331 tmppeak->SetRange(int_low, int_high); // This will help get the true area of the gaussian 200 ~ infinity in a gaus
332 tmppeak->SetName("tmppeak");
333
334 // SOMETHING IS WRONG WITH THESE UNCERTAINTIES
335 // This is where we will do integrals and stuff.
336 fArea = (tmppeak->Integral(int_low, int_high)) / binWidth;
337 // Set the background values in the covariance matrix to 0, while keeping their covariance errors
338 TMatrixDSym CovMat = fitres->GetCovarianceMatrix();
339 CovMat(5, 5) = 0.0;
340 CovMat(6, 6) = 0.0;
341 CovMat(7, 7) = 0.0;
342 CovMat(8, 8) = 0.0;
343 CovMat(9, 9) = 0.0;
344 fDArea = (tmppeak->IntegralError(int_low, int_high, tmppeak->GetParameters(), CovMat.GetMatrixArray())) / binWidth;
345
346 if(verbose) {
347 std::cout << "Integral: " << fArea << " +/- " << fDArea << std::endl;
348 }
349 // Set the background for drawing later
350 fBackground->SetParameters(GetParameters());
351 // To DO: put a flag in signalling that the errors are not to be trusted if we have a bad cov matrix
352 Copy(*fitHist->GetListOfFunctions()->Last());
353
354 // always print result of the fit even if not verbose
355 if(!quiet) { Print("+"); }
356 delete tmppeak;
357 fLastFit = this;
358 return true;
359}
360
361void TPeak::Clear(Option_t*)
362{
363 // Clear the TPeak including functions and histogram, does not
364 // currently clear inherited members such as name.
365 // want to make a clear that doesn't clear everything
366 fArea = 0.0;
367 fDArea = 0.0;
368 fChi2 = 0.0;
369 fNdf = 0.0;
371 // Do deep clean stuff maybe? require an option?
372}
373
374void TPeak::Print(Option_t* opt) const
375{
376 // Prints TPeak properties. To see More properties use the option "+"
377 std::cout << "Name: " << GetName() << std::endl;
378 std::cout << "Centroid: " << GetParameter("centroid") << " +/- " << GetParError(GetParNumber("centroid")) << std::endl;
379 std::cout << "Area: " << fArea << " +/- " << fDArea << std::endl;
380 std::cout << "FWHM: " << GetParameter("sigma") * 2.3548 << " +/- " << GetParError(GetParNumber("sigma")) * 2.3548 << std::endl;
381 std::cout << "Chi^2/NDF: " << fChi2 / fNdf << std::endl;
382 if(strchr(opt, '+') != nullptr) {
383 TF1::Print();
384 TGRSIFit::Print(opt); // Polymorphise this a bit better
385 }
386}
387
388void TPeak::DrawBackground(Option_t* opt) const
389{
390 fBackground->Draw(opt);
391}
392
394{
395 if(GetHist() == nullptr) {
396 std::cout << "No hist set" << std::endl;
397 return;
398 }
399 if(fChi2 < 0.000000001) {
400 std::cout << "No fit performed" << std::endl;
401 return;
402 }
403
404 Double_t xlow = 0.;
405 Double_t xhigh = 0.;
406 GetRange(xlow, xhigh);
407 Int_t nbins = GetHist()->GetXaxis()->GetNbins();
408 auto* res = new Double_t[nbins];
409 auto* bin = new Double_t[nbins];
410 Int_t points = 0;
411 fResiduals->Clear();
412
413 for(int i = 1; i <= nbins; i++) {
414 if(GetHist()->GetBinCenter(i) <= xlow || GetHist()->GetBinCenter(i) >= xhigh) {
415 continue;
416 }
417 res[points] = (GetHist()->GetBinContent(i) - Eval(GetHist()->GetBinCenter(i))) +
418 GetParameter("Height") / 2; /// GetHist()->GetBinError(i));// + GetParameter("Height") + 10.;
419 bin[points] = GetHist()->GetBinCenter(i);
420 fResiduals->SetPoint(i, bin[i], res[i]);
421
422 points++;
423 }
424
425 fResiduals->Draw();
426
427 delete[] res;
428 delete[] bin;
429}
430
432{
433 if(GetHist() == nullptr) {
434 std::cout << "No hist set" << std::endl;
435 return false;
436 }
437 if(fChi2 < 0.000000001) {
438 std::cout << "No fit performed" << std::endl;
439 return false;
440 }
441 return true;
442}
443
445{
446 if(!GoodStatus()) { return 0.; }
447
448 Double_t width = GetParameter("sigma");
449 Double_t xlow = 0.;
450 Double_t xhigh = 0.;
451 GetRange(xlow, xhigh);
452 Double_t int_low = xlow - 10. * width; // making the integration bounds a bit smaller, but still large enough. -JKS
453 Double_t int_high = xhigh + 10. * width;
454 return GetIntegralArea(int_low, int_high);
455}
456
457Double_t TPeak::GetIntegralArea(Double_t int_low, Double_t int_high)
458{
459 if(!GoodStatus()) { return 0.; }
460
461 // pull appropriate properties from peak and histogram
462 TH1* hist = GetHist();
463
464 // use those properties to integrate the histogram
465 Int_t binlow = hist->FindBin(int_low);
466 Int_t binhigh = hist->FindBin(int_high);
467 Double_t binWidth = hist->GetBinWidth(binlow);
468 Double_t hist_integral = hist->Integral(binlow, binhigh);
469 Double_t xlow = hist->GetXaxis()->GetBinLowEdge(binlow);
470 Double_t xhigh = hist->GetXaxis()->GetBinUpEdge(binhigh);
471
472 // ... and then integrate the background
473 Double_t bg_area = (Background()->Integral(xlow, xhigh)) / binWidth;
474
475 // calculate the peak area and error
476 Double_t peakarea = hist_integral - bg_area;
477
478 return peakarea;
479}
480
481Double_t TPeak::GetIntegralAreaErr(Double_t int_low, Double_t int_high)
482{
483 if(!GoodStatus()) { return 0.; }
484
485 // pull appropriate properties from peak and histogram
486 TH1* hist = GetHist();
487
488 // use those properties to integrate the histogram
489 Int_t binlow = hist->FindBin(int_low);
490 Int_t binhigh = hist->FindBin(int_high);
491 Double_t binWidth = hist->GetBinWidth(binlow);
492 Double_t hist_integral = hist->Integral(binlow, binhigh);
493 Double_t xlow = hist->GetXaxis()->GetBinLowEdge(binlow);
494 Double_t xhigh = hist->GetXaxis()->GetBinUpEdge(binhigh);
495
496 // ... and then integrate the background
497 Double_t bg_area = (Background()->Integral(xlow, xhigh)) / binWidth;
498
499 // calculate the peak error
500 Double_t peakerr = sqrt(hist_integral + bg_area);
501
502 return peakerr;
503}
504
506{
507 if(!GoodStatus()) { return 0.; }
508
509 Double_t width = GetParameter("sigma");
510 Double_t xlow = 0.;
511 Double_t xhigh = 0.;
512 GetRange(xlow, xhigh);
513 Double_t int_low = xlow - 10. * width; // making the integration bounds a bit smaller, but still large enough. -JKS
514 Double_t int_high = xhigh + 10. * width;
515 return GetIntegralAreaErr(int_low, int_high);
516}
517
518void TPeak::CheckArea(Double_t int_low, Double_t int_high)
519{
520 if(!GoodStatus()) { return; }
521
522 // calculate the peak area and error
523 Double_t peakarea = GetIntegralArea(int_low, int_high);
524 Double_t peakerr = GetIntegralAreaErr(int_low, int_high);
525
526 // now print properties
527 std::cout << "TPeak integral: " << fArea << " +/- " << fDArea << std::endl;
528 std::cout << "Histogram - BG integral: " << peakarea << " +/- " << peakerr << std::endl;
529 if(std::abs(peakarea - fArea) < (fDArea + peakerr)) {
530 std::cout << DGREEN << "Areas are consistent." << RESET_COLOR << std::endl;
531 } else if(std::abs(peakarea - fArea) < 2 * (fDArea + peakerr)) {
532 std::cout << DYELLOW << "Areas are consistent within 2 sigma." << RESET_COLOR << std::endl;
533 } else {
534 std::cout << DRED << "Areas are inconsistent." << RESET_COLOR << std::endl;
535 }
536}
537
539{
540 if(!GoodStatus()) { return; }
541
542 // calculate the peak area and error
543 Double_t peakarea = GetIntegralArea();
544 Double_t peakerr = GetIntegralAreaErr();
545
546 // now print properties
547 std::cout << "TPeak integral: " << fArea << " +/- " << fDArea << std::endl;
548 std::cout << "Histogram - BG integral: " << peakarea << " +/- " << peakerr << std::endl;
549 if(std::abs(peakarea - fArea) < (fDArea + peakerr)) {
550 std::cout << DGREEN << "Areas are consistent." << RESET_COLOR << std::endl;
551 } else if(std::abs(peakarea - fArea) < 2 * (fDArea + peakerr)) {
552 std::cout << DYELLOW << "Areas are consistent within 2 sigma." << RESET_COLOR << std::endl;
553 } else {
554 std::cout << DRED << "Areas are inconsistent." << RESET_COLOR << std::endl;
555 }
556}
#define DYELLOW
Definition Globals.h:16
#define DRED
Definition Globals.h:18
#define DGREEN
Definition Globals.h:17
#define YELLOW
Definition Globals.h:7
#define GREEN
Definition Globals.h:8
#define RESET_COLOR
Definition Globals.h:5
TH1D * hist
Definition UserFillObj.h:3
Bool_t AddToGlobalList(Bool_t yes=kTRUE) override
Definition TGRSIFit.cxx:64
virtual void SetHist(TH1 *hist)
Definition TGRSIFit.h:42
void Clear(Option_t *opt="") override
Definition TGRSIFit.cxx:38
Bool_t IsInitialized() const
Definition TGRSIFit.h:56
void SetInitialized(Bool_t flag=true)
Definition TGRSIFit.h:57
void Copy(TObject &obj) const override
Definition TGRSIFit.cxx:22
virtual TH1 * GetHist() const
Definition TGRSIFit.h:46
void Print(Option_t *opt="") const override
Definition TGRSIFit.cxx:29
Definition TPeak.h:23
Bool_t Fit(TH1 *fitHist, Option_t *opt="")
Definition TPeak.cxx:196
Double_t GetIntegralArea()
Definition TPeak.cxx:444
~TPeak()
Definition TPeak.cxx:84
TF1 * Background() const
Definition TPeak.h:91
void InitNames()
Definition TPeak.cxx:97
Double_t GetIntegralAreaErr()
Definition TPeak.cxx:505
Double_t fDArea
Definition TPeak.h:114
void DrawResiduals()
Definition TPeak.cxx:393
void CheckArea()
Definition TPeak.cxx:538
Double_t fChi2
Definition TPeak.h:115
Bool_t fOwnBgFlag
Definition TPeak.h:117
TGraph * fResiduals
Definition TPeak.h:123
void Print(Option_t *opt="") const override
Definition TPeak.cxx:374
TF1 * fBackground
Definition TPeak.h:122
void DrawBackground(Option_t *opt="SAME") const
Definition TPeak.cxx:388
bool GoodStatus()
Definition TPeak.cxx:431
void Copy(TObject &obj) const override
Definition TPeak.cxx:111
Double_t fNdf
Definition TPeak.h:116
Double_t fArea
Definition TPeak.h:113
Bool_t InitParams(TH1 *fitHist=nullptr) override
Definition TPeak.cxx:136
static TPeak * fLastFit
!
Definition TPeak.h:120
void Clear(Option_t *opt="") override
Definition TPeak.cxx:361
static bool fLogLikelihoodFlag
!
Definition TPeak.h:119
static Bool_t GetLogLikelihoodFlag()
Definition TPeak.h:98
TPeak()
Definition TPeak.cxx:74
bool CheckParameterErrors(const TFitResultPtr &fitres, std::string opt="")
Double_t StepBG(Double_t *dim, Double_t *par)