1 | #include "MFit.h"
|
---|
2 |
|
---|
3 | #include <iomanip.h>
|
---|
4 |
|
---|
5 | #include <TF1.h>
|
---|
6 | #include <TH1.h>
|
---|
7 |
|
---|
8 | #include <TMinuit.h>
|
---|
9 |
|
---|
10 | ClassImp(MFit);
|
---|
11 |
|
---|
12 | TF1 *MFit::fgFunc=NULL;
|
---|
13 | TH1 *MFit::fgHist=NULL;
|
---|
14 |
|
---|
15 | Int_t MFit::fgBinMin;
|
---|
16 | Int_t MFit::fgBinMax;
|
---|
17 |
|
---|
18 | void MFit::Func(Int_t &npar, Double_t *gin, Double_t &f, Double_t *par, Int_t flag)
|
---|
19 | {
|
---|
20 | Double_t chisq = 0;
|
---|
21 |
|
---|
22 | for (int i=fgBinMin+1; i<fgBinMax; i++)
|
---|
23 | {
|
---|
24 | Double_t x = fgHist->GetBinCenter(i);
|
---|
25 |
|
---|
26 | Double_t y = fgFunc->EvalPar(&x, par);
|
---|
27 | Double_t d = (y - fgHist->GetBinContent(i))/fgHist->GetBinError(i);
|
---|
28 |
|
---|
29 | chisq += d*d;
|
---|
30 | }
|
---|
31 |
|
---|
32 | f = chisq / fgFunc->GetNDF();
|
---|
33 | fgFunc->SetChisquare(f);
|
---|
34 | }
|
---|
35 |
|
---|
36 | void MFit::FuncLog(Int_t &npar, Double_t *gin, Double_t &f, Double_t *par, Int_t flag)
|
---|
37 | {
|
---|
38 | Double_t chisq = 0;
|
---|
39 |
|
---|
40 | for (int i=fgBinMin+1; i<fgBinMax; i++)
|
---|
41 | {
|
---|
42 | Double_t x1 = fgHist->GetBinLowEdge(i+1);
|
---|
43 | Double_t x0 = fgHist->GetBinLowEdge(i);
|
---|
44 |
|
---|
45 | Double_t x = sqrt(x1*x0);
|
---|
46 |
|
---|
47 | Double_t y = fgFunc->EvalPar(&x, par);
|
---|
48 | Double_t d = (y - fgHist->GetBinContent(i))/fgHist->GetBinError(i);
|
---|
49 |
|
---|
50 | chisq += d*d;
|
---|
51 | }
|
---|
52 |
|
---|
53 | f = chisq / fgFunc->GetNDF();
|
---|
54 | fgFunc->SetChisquare(f);
|
---|
55 | }
|
---|
56 |
|
---|
57 | void MFit::DeleteF()
|
---|
58 | {
|
---|
59 | if (fFunc)
|
---|
60 | if (fFunc->TestBit(kIsOwner))
|
---|
61 | delete fFunc;
|
---|
62 |
|
---|
63 | if (fMinuit)
|
---|
64 | delete fMinuit;
|
---|
65 | }
|
---|
66 |
|
---|
67 | void MFit::DeleteH()
|
---|
68 | {
|
---|
69 | if (fHist)
|
---|
70 | if (fHist->TestBit(kIsOwner))
|
---|
71 | delete fHist;
|
---|
72 | }
|
---|
73 |
|
---|
74 | void MFit::SetFunc(TF1 *f)
|
---|
75 | {
|
---|
76 | DeleteF();
|
---|
77 |
|
---|
78 | fFunc = f;
|
---|
79 |
|
---|
80 | fMinuit = new TMinuit(fFunc->GetNpar());
|
---|
81 | fMinuit->SetPrintLevel(-1);
|
---|
82 | }
|
---|
83 |
|
---|
84 | void MFit::SetFunc(TString formula, Axis_t min, Axis_t max)
|
---|
85 | {
|
---|
86 | TF1 *f = new TF1("", formula, min, max);
|
---|
87 | f->SetBit(kIsOwner);
|
---|
88 |
|
---|
89 | SetFunc(f);
|
---|
90 | }
|
---|
91 |
|
---|
92 | void MFit::SetRange(Axis_t min, Axis_t max)
|
---|
93 | {
|
---|
94 | if (fFunc)
|
---|
95 | fFunc->SetRange(min, max);
|
---|
96 | }
|
---|
97 |
|
---|
98 | void MFit::SetHist(TH1 *h, Bool_t candelete)
|
---|
99 | {
|
---|
100 | DeleteH();
|
---|
101 |
|
---|
102 | fHist = h;
|
---|
103 |
|
---|
104 | if (candelete)
|
---|
105 | fHist->SetBit(kIsOwner);
|
---|
106 | }
|
---|
107 |
|
---|
108 | void MFit::Fit(Bool_t log)
|
---|
109 | {
|
---|
110 | fgBinMin = fHist->FindBin(fFunc->GetXmin()); // excluded
|
---|
111 | fgBinMax = fHist->FindBin(fFunc->GetXmax()); // excluded
|
---|
112 |
|
---|
113 | fFunc->SetNDF(fgBinMax-fgBinMin-1);
|
---|
114 |
|
---|
115 | fgHist = fHist;
|
---|
116 | fgFunc = fFunc;
|
---|
117 |
|
---|
118 | fMinuit->SetFCN(log ? FuncLog : Func);
|
---|
119 | fMinuit->Migrad();
|
---|
120 |
|
---|
121 | for (int i=0; i<fFunc->GetNpar(); i++)
|
---|
122 | {
|
---|
123 | Double_t par, err;
|
---|
124 | fMinuit->GetParameter(i, par, err);
|
---|
125 | fFunc->SetParameter(i, par);
|
---|
126 | fFunc->SetParError(i, err);
|
---|
127 | }
|
---|
128 | }
|
---|
129 |
|
---|
130 | void MFit::Print(Option_t *opt) const
|
---|
131 | {
|
---|
132 | for (int i=0; i<fFunc->GetNpar(); i++)
|
---|
133 | cout << "Par["<<i<<"]: " << GetParameter(i) << " +- " << GetParError(i) << endl;
|
---|
134 | cout << "ChiSq: " << fFunc->GetChisquare() << endl;
|
---|
135 | cout << "NDF: " << fFunc->GetNDF() << endl;
|
---|
136 | }
|
---|
137 |
|
---|
138 | void MFit::SetParameter(Int_t n, TString name, Axis_t start, Axis_t min, Axis_t max)
|
---|
139 | {
|
---|
140 | if (n>=fFunc->GetNpar())
|
---|
141 | return;
|
---|
142 |
|
---|
143 | fMinuit->DefineParameter(n, name, start, min/10, min, max);
|
---|
144 | }
|
---|
145 |
|
---|
146 | Double_t MFit::GetParameter(Int_t n) const
|
---|
147 | {
|
---|
148 | return fFunc->GetParameter(n);
|
---|
149 | }
|
---|
150 |
|
---|
151 | Double_t MFit::GetParError(Int_t n) const
|
---|
152 | {
|
---|
153 | return fFunc->GetParError(n);
|
---|
154 | }
|
---|
155 |
|
---|
156 | Double_t MFit::operator[](Int_t n) const
|
---|
157 | {
|
---|
158 | return fFunc->GetParameter(n);
|
---|
159 | }
|
---|
160 |
|
---|
161 | TF1 *MFit::DrawCopy(Option_t *o) const
|
---|
162 | {
|
---|
163 | return fFunc->DrawCopy(o);
|
---|
164 | }
|
---|
165 |
|
---|