data analysis scripts
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

273 lines
9.3 KiB

  1. //+ Combined (simultaneous) fit of two histogram with separate functions
  2. // and some common parameters
  3. //
  4. // See http://root.cern.ch/phpBB3//viewtopic.php?f=3&t=11740#p50908
  5. // for a modified version working with Fumili or GSLMultiFit
  6. //
  7. // N.B. this macro must be compiled with ACliC
  8. //
  9. //Author: L. Moneta - Dec 2010
  10. #include "Fit/Fitter.h"
  11. #include "Fit/BinData.h"
  12. #include "Fit/Chi2FCN.h"
  13. #include "TH1.h"
  14. #include "TList.h"
  15. #include "Math/WrappedMultiTF1.h"
  16. #include "HFitInterface.h"
  17. #include "TCanvas.h"
  18. #include "TStyle.h"
  19. #include "TGraphErrors.h"
  20. #include "TLegend.h"
  21. #include "TMultiGraph.h"
  22. // definition of shared parameter
  23. // background function
  24. int iparB[2] = { 0, //amplitude
  25. 1, // k_b
  26. };
  27. // signal + background function
  28. int iparSB2[2] = { 0, // amplitude
  29. 2, // k_b
  30. };
  31. int iparSB3[2] = { 0, // amplitude
  32. 3, // k_b
  33. };
  34. int iparSB4[2] = { 0, // amplitude
  35. 4, // k_b
  36. };
  37. struct GlobalChi2 {
  38. GlobalChi2( ROOT::Math::IMultiGenFunction & f1,
  39. ROOT::Math::IMultiGenFunction & f2,
  40. ROOT::Math::IMultiGenFunction & f3,
  41. ROOT::Math::IMultiGenFunction & f4) :
  42. fChi2_1(&f1), fChi2_2(&f2), fChi2_3(&f3), fChi2_4(&f4) {}
  43. // parameter vector is first background (in common 1 and 2)
  44. // and then is signal (only in 2)
  45. double operator() (const double *par) const {
  46. double p1[2];
  47. for (int i = 0; i < 2; ++i) p1[i] = par[iparB[i] ];
  48. double p2[2];
  49. for (int i = 0; i < 2; ++i) p2[i] = par[iparSB2[i] ];
  50. double p3[2];
  51. for (int i = 0; i < 2; ++i) p3[i] = par[iparSB3[i] ];
  52. double p4[2];
  53. for (int i = 0; i < 2; ++i) p4[i] = par[iparSB4[i] ];
  54. return (*fChi2_1)(p1) + (*fChi2_2)(p2) + (*fChi2_3)(p3) + (*fChi2_4)(p4);
  55. }
  56. const ROOT::Math::IMultiGenFunction * fChi2_1;
  57. const ROOT::Math::IMultiGenFunction * fChi2_2;
  58. const ROOT::Math::IMultiGenFunction * fChi2_3;
  59. const ROOT::Math::IMultiGenFunction * fChi2_4;
  60. };
  61. void combinedFit_hitbirk() {
  62. #if defined(__CINT__) && !defined(__MAKECINT__)
  63. cout << "ERROR: This tutorial can run only using ACliC, you must run it by doing: " << endl;
  64. cout << "\t .x $ROOTSYS/tutorials/fit/combinedFit_hit.C+" << endl;
  65. return;
  66. #endif
  67. TF1 * fB = new TF1("fB","[0]*(1/(1+[1]*1.65901*TMath::Power(x,-1.7218)))",0.3,0.59);
  68. TF1 * fSB2 = new TF1("fSB2","[0]*(1/(1+[1]*4*1.65901*TMath::Power(x,-1.7218)))",0.34,0.59);
  69. TF1 * fSB3 = new TF1("fSB3","[0]*(1/(1+[1]*36*1.65901*TMath::Power(x,-1.7218)))",0.4,0.73);
  70. TF1 * fSB4 = new TF1("fSB4","[0]*(1/(1+[1]*64*1.65901*TMath::Power(x,-1.7218)))",0.43,0.73);
  71. TGraphErrors * hB = new TGraphErrors("energylist_p_bpmbeta1.txt","%lg %lg %lg");
  72. TGraphErrors * hSB2 = new TGraphErrors("energylist_he_bpmbeta1.txt","%lg %lg %lg");
  73. TGraphErrors * hSB3 = new TGraphErrors("energylist_c_bpmbeta1.txt","%lg %lg %lg");
  74. TGraphErrors * hSB4 = new TGraphErrors("energylist_o_bpmbeta1.txt","%lg %lg %lg");
  75. TGraphErrors * hB_2 = new TGraphErrors("energylist_p_bpmbeta1.txt","%lg %lg %lg");
  76. TGraphErrors * hSB2_2 = new TGraphErrors("energylist_he_bpmbeta1.txt","%lg %lg %lg");
  77. TGraphErrors * hSB3_2 = new TGraphErrors("energylist_c_bpmbeta1.txt","%lg %lg %lg");
  78. TGraphErrors * hSB4_2 = new TGraphErrors("energylist_o_bpmbeta1.txt","%lg %lg %lg");
  79. // perform now global fit
  80. // TF1 * fSB2 = new TF1("fSB2","expo + gaus(2)",0,100);
  81. ROOT::Math::WrappedMultiTF1 wfB(*fB,1);
  82. ROOT::Math::WrappedMultiTF1 wfSB2(*fSB2,1);
  83. ROOT::Math::WrappedMultiTF1 wfSB3(*fSB3,1);
  84. ROOT::Math::WrappedMultiTF1 wfSB4(*fSB4,1);
  85. ROOT::Fit::DataOptions opt;
  86. ROOT::Fit::DataRange rangeB;
  87. // set the data range
  88. rangeB.SetRange(0.3,0.59);
  89. ROOT::Fit::BinData dataB(opt,rangeB);
  90. ROOT::Fit::FillData(dataB, hB);
  91. ROOT::Fit::DataRange rangeSB2;
  92. rangeSB2.SetRange(0.34,0.59);
  93. ROOT::Fit::BinData dataSB2(opt,rangeSB2);
  94. ROOT::Fit::FillData(dataSB2, hSB2);
  95. ROOT::Fit::DataRange rangeSB3;
  96. rangeSB3.SetRange(0.4,0.73);
  97. ROOT::Fit::BinData dataSB3(opt,rangeSB3);
  98. ROOT::Fit::FillData(dataSB3, hSB3);
  99. ROOT::Fit::DataRange rangeSB4;
  100. rangeSB4.SetRange(0.43,0.73);
  101. ROOT::Fit::BinData dataSB4(opt,rangeSB4);
  102. ROOT::Fit::FillData(dataSB4, hSB4);
  103. ROOT::Fit::Chi2Function chi2_B(dataB, wfB);
  104. ROOT::Fit::Chi2Function chi2_SB2(dataSB2, wfSB2);
  105. ROOT::Fit::Chi2Function chi2_SB3(dataSB3, wfSB3);
  106. ROOT::Fit::Chi2Function chi2_SB4(dataSB4, wfSB4);
  107. GlobalChi2 globalChi2(chi2_B, chi2_SB2, chi2_SB3, chi2_SB4);
  108. ROOT::Fit::Fitter fitter;
  109. const int Npar = 5;
  110. double par0[Npar] = {1.4,0.1,0.1,0.1,0.1};
  111. // double par0[Npar] = {1.4,0.000007,0.15,1.4, 0.00250,2, 0.005,2, 0.007};
  112. // create before the parameter settings in order to fix or set range on them
  113. fitter.Config().SetParamsSettings(Npar,par0);
  114. // fix 5-th parameter
  115. // fitter.Config().ParSettings(1).Fix();
  116. // set limits on the third and 4-th parameter
  117. fitter.Config().ParSettings(0).SetLimits(0,5);
  118. fitter.Config().ParSettings(1).SetLimits(0,1.0);
  119. fitter.Config().ParSettings(2).SetLimits(0,1.0);
  120. fitter.Config().ParSettings(3).SetLimits(0,1.0);//1
  121. fitter.Config().ParSettings(4).SetLimits(0,1.0);//10
  122. // fitter.Config().ParSettings(4).SetStepSize(2);
  123. // fitter.Config().ParSettings(1).SetStepSize(0.1);
  124. // fitter.Config().ParSettings(6).SetStepSize(10);
  125. // fitter.Config().ParSettings(8).SetStepSize(10);
  126. fitter.Config().MinimizerOptions().SetPrintLevel(0);
  127. fitter.Config().SetMinimizer("Minuit2","Migrad"); //Minuit2
  128. //fitter.Config().SetNormErrors(true);
  129. // fit FCN function directly
  130. // (specify optionally data size and flag to indicate that is a chi2 fit)
  131. fitter.FitFCN(Npar,globalChi2,0,dataB.Size()+dataSB2.Size()+dataSB3.Size()+dataSB4.Size(),true);
  132. ROOT::Fit::FitResult result = fitter.Result();
  133. result.Print(std::cout, true);
  134. //result.PrintCovMatrix(std::cout);
  135. cout << "FitResult.Status() = " << result.Status() << endl;
  136. TCanvas * c1 = new TCanvas("Simfit","Simultaneous fit");
  137. // c1->Divide(2,2);
  138. // c1->cd(1);
  139. // gStyle->SetOptFit(1111);
  140. fB->SetFitResult( result, iparB);
  141. fB->SetRange(rangeB().first, rangeB().second);
  142. fB->SetLineColor(kRed);
  143. hB->GetListOfFunctions()->Add(fB);
  144. //hB->Draw("AP");
  145. // c1->cd(2);
  146. fSB2->SetFitResult( result, iparSB2);
  147. fSB2->SetRange(rangeSB2().first, rangeSB2().second);
  148. fSB2->SetLineColor(kRed);
  149. hSB2->GetListOfFunctions()->Add(fSB2);
  150. // hSB2->Draw("AP");
  151. // c1->cd(3);
  152. fSB3->SetFitResult( result, iparSB3);
  153. fSB3->SetRange(rangeSB3().first, rangeSB3().second);
  154. fSB3->SetLineColor(kRed);
  155. hSB3->GetListOfFunctions()->Add(fSB3);
  156. // hSB3->Draw("AP");
  157. // c1->cd(4);
  158. fSB4->SetFitResult( result, iparSB4);
  159. fSB4->SetRange(rangeSB4().first, rangeSB4().second);
  160. fSB4->SetLineColor(kRed);
  161. hSB4->GetListOfFunctions()->Add(fSB4);
  162. // hSB4->Draw("AP");
  163. TMultiGraph * mg_e9 = new TMultiGraph();
  164. mg_e9->Add(hB,"p"); hB->SetMarkerStyle(20);
  165. mg_e9->Add(hSB2,"p"); hSB2->SetMarkerStyle(21);
  166. mg_e9->Add(hSB3,"p"); hSB3->SetMarkerStyle(22);
  167. mg_e9->Add(hSB4,"p"); hSB4->SetMarkerStyle(23);
  168. mg_e9->Draw("a"); //must draw first before labeling axes
  169. mg_e9->SetTitle(" ");
  170. mg_e9->GetXaxis()->SetTitle("Lorentz #beta");
  171. mg_e9->GetYaxis()->SetTitle("dA/dE / (10^{-6} a.u./(Mev#upointion#upoints^{-1})");
  172. mg_e9->SetMinimum(0.5);
  173. mg_e9->SetMaximum(1.4);
  174. TF1 * tf1_birk1 = new TF1("tf1_birk1","[0]*(1/(1+[1]*1.65901*TMath::Power(x,-1.7218)))",0.3,0.59);
  175. TF1 * tf1_birk2 = new TF1("tf1_birk2","[0]*(1/(1+[1]*4*1.65901*TMath::Power(x,-1.7218)))",0.34,0.59);
  176. TF1 * tf1_birk3 = new TF1("tf1_birk3","[0]*(1/(1+[1]*36*1.65901*TMath::Power(x,-1.7218)))",0.4,0.73);
  177. TF1 * tf1_birk4 = new TF1("tf1_birk4","[0]*(1/(1+[1]*64*1.65901*TMath::Power(x,-1.7218)))",0.43,0.73);
  178. tf1_birk1->SetParameters(1,0.01);tf1_birk1->SetLineStyle(2);tf1_birk1->SetLineColor(kBlack);
  179. tf1_birk2->SetParameters(1,0.01);tf1_birk2->SetLineStyle(2);tf1_birk2->SetLineColor(kBlack);
  180. tf1_birk3->SetParameters(1,0.01);tf1_birk3->SetLineStyle(2);tf1_birk3->SetLineColor(kBlack);
  181. tf1_birk4->SetParameters(1,0.01);tf1_birk4->SetLineStyle(2);tf1_birk4->SetLineColor(kBlack);
  182. hB_2->Fit(tf1_birk1);
  183. hSB2_2->Fit(tf1_birk2);
  184. hSB3_2->Fit(tf1_birk3);
  185. hSB4_2->Fit(tf1_birk4);
  186. tf1_birk1->Draw("same");
  187. tf1_birk2->Draw("same");
  188. tf1_birk3->Draw("same");
  189. tf1_birk4->Draw("same");
  190. TLegend * mylegende9 = new TLegend(0.65,0.65,0.9,0.9);
  191. mylegende9->SetFillColor(0); // white background
  192. mylegende9->SetTextFont(22);
  193. mylegende9->SetBorderSize(0); // get rid of the box
  194. mylegende9->SetTextSize(0.035); // set text size
  195. mylegende9->AddEntry(hB,"Protons","p"); // options: p,l,f
  196. mylegende9->AddEntry(hSB2,"Helium","p"); // options: p,l,f
  197. mylegende9->AddEntry(hSB3,"Carbon","p"); // options: p,l,f
  198. mylegende9->AddEntry(hSB4,"Oxygen","p"); // options: p,l,f
  199. mylegende9->AddEntry(fB,"Birks Fit 1","l"); // options: p,l,f
  200. mylegende9->AddEntry(tf1_birk1,"Birks Fit 2","l"); // options: p,l,f
  201. // mylegende9->AddEntry(tf1_pow1,"[1]#upointpow(#beta,[2])}","l"); // options: p,l,f
  202. mylegende9->Draw();
  203. gPad->Modified();
  204. c1->SaveAs("figs/bvt_beta_combinedfitbirks2.pdf");
  205. c1->SaveAs("figs/bvt_beta_combinedfitbirks2.png");
  206. c1->SaveAs("figs/bvt_beta_combinedfitbirks2.C");
  207. }