Logo ROOT   6.12/07
Reference Guide
TBackCompFitter.cxx
Go to the documentation of this file.
1 // @(#)root/hist:$Id$
2 // Author: Lorenzo Moneta
3 
4 /*************************************************************************
5  * Copyright (C) 1995-2012, 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 ////////////////////////////////////////////////////////////////////////////////
13 /** \class TBackCompFitter
14  \ingroup Hist
15  \brief Backward compatible implementation of TVirtualFitter
16 
17 Backward compatible implementation of TVirtualFitter using the
18 class ROOT::Fit::Fitter. This class is created after fitting an
19 histogram (TH1), TGraph or TTree and provides in addition to the
20 methods of the TVirtualFitter hooks to access the fit result class
21 (ROOT::Fit::FitResult), the fit configuration
22 (ROOT::Fit::FitConfig) or the fit data (ROOT::Fit::FitData) using
23 
24 ~~~~~~~~{.cpp}
25  TBackCompFitter * fitter = (TBackCompFitter *) TVirtualFitter::GetFitter();
26  ROOT::Fit::FitResult & result = fitter->GetFitResult();
27  result.Print(std::cout);
28 ~~~~~~~~
29 
30 Methods for getting the confidence level or contours are also
31 provided. Note that after a new calls to TH1::Fit (or similar) the
32 class will be deleted and all reference to the FitResult, FitConfig
33 or minimizer will be invalid. One could eventually copying the
34 class before issuing a new fit to avoid deleting this information.
35 *///////////////////////////////////////////////////////////////////////////////
36 
37 #include "TROOT.h"
38 #include "TBackCompFitter.h"
39 
40 
41 #include "TMethodCall.h"
42 
43 #include "Math/Util.h"
44 
45 #include <iostream>
46 #include <cassert>
47 
48 //needed by GetCondifenceLevel
49 #include "Math/IParamFunction.h"
50 #include "TH1.h"
51 #include "TH2.h"
52 #include "TH3.h"
53 #include "TMath.h"
54 #include "TGraph.h"
55 #include "TGraphErrors.h"
56 #include "TGraph2DErrors.h"
57 #include "TMultiGraph.h"
58 #include "HFitInterface.h"
59 #include "Math/Minimizer.h"
60 #include "Fit/BinData.h"
61 #include "Fit/FitConfig.h"
62 #include "Fit/UnBinData.h"
64 #include "Fit/LogLikelihoodFCN.h"
65 #include "Fit/Chi2FCN.h"
66 #include "Fit/FcnAdapter.h"
67 #include "TFitResult.h"
68 
69 //#define DEBUG 1
70 
71 
73 
74 
75 
76 ////////////////////////////////////////////////////////////////////////////////
77 /// Constructor needed by TVirtualFitter interface. Same behavior as default constructor.
78 /// initialize setting name and the global pointer
79 
81  fMinimizer(0),
82  fObjFunc(0),
83  fModelFunc(0)
84 {
85  SetName("BCFitter");
86 }
87 
88 ////////////////////////////////////////////////////////////////////////////////
89 /// Constructor used after having fit using directly ROOT::Fit::Fitter
90 /// will create a dummy fitter copying configuration and parameter settings
91 
92 TBackCompFitter::TBackCompFitter(const std::shared_ptr<ROOT::Fit::Fitter> & fitter, const std::shared_ptr<ROOT::Fit::FitData> & data) :
93  fFitData(data),
94  fFitter(fitter),
95  fMinimizer(0),
96  fObjFunc(0),
97  fModelFunc(0)
98 {
99  SetName("LastFitter");
100 }
101 
102 ////////////////////////////////////////////////////////////////////////////////
103 /// Destructor - delete the managed objects
104 
106  if (fMinimizer) delete fMinimizer;
107  if (fObjFunc) delete fObjFunc;
108  if (fModelFunc) delete fModelFunc;
109 }
110 
111 ////////////////////////////////////////////////////////////////////////////////
112 /// Do chisquare calculations in case of likelihood fits
113 /// Do evaluation a the minimum only
114 
116  const std::vector<double> & minpar = fFitter->Result().Parameters();
117  assert (npar == (int) minpar.size() );
118  double diff = 0;
119  double s = 0;
120  for (int i =0; i < npar; ++i) {
121  diff += std::abs( params[i] - minpar[i] );
122  s += minpar[i];
123  }
124 
125  if (diff > s * 1.E-12 ) Warning("Chisquare","given parameter values are not at minimum - chi2 at minimum is returned");
126  return fFitter->Result().Chi2();
127 }
128 
129 ////////////////////////////////////////////////////////////////////////////////
130 /// Clear resources for consecutive fits
131 
133  // need to do something here ??? to be seen
134 }
135 
136 ////////////////////////////////////////////////////////////////////////////////
137 /// Execute the command (Fortran Minuit compatible interface)
138 
139 Int_t TBackCompFitter::ExecuteCommand(const char *command, Double_t *args, Int_t nargs) {
140 #ifdef DEBUG
141  std::cout<<"Execute command= "<<command<<std::endl;
142 #endif
143 
144  // set also number of parameters in obj function
145  DoSetDimension();
146 
147  TString scommand(command);
148  scommand.ToUpper();
149 
150  // MIGRAD
151  if (scommand.Contains("MIG")) {
152  if (!fObjFunc) {
153  Error("ExecuteCommand","FCN must set before executing this command");
154  return -1;
155  }
156 
157  fFitter->Config().SetMinimizer(GetDefaultFitter(), "Migrad");
158  bool ret = fFitter->FitFCN(*fObjFunc);
159  return (ret) ? 0 : -1;
160  }
161 
162  //Minimize
163  if (scommand.Contains("MINI")) {
164 
165  fFitter->Config().SetMinimizer(GetDefaultFitter(), "Minimize");
166  if (!fObjFunc) {
167  Error("ExecuteCommand","FCN must set before executing this command");
168  return -1;
169  }
170  bool ret = fFitter->FitFCN(*fObjFunc);
171  return (ret) ? 0 : -1;
172  }
173  //Simplex
174  if (scommand.Contains("SIM")) {
175 
176  if (!fObjFunc) {
177  Error("ExecuteCommand","FCN must set before executing this command");
178  return -1;
179  }
180 
181  fFitter->Config().SetMinimizer(GetDefaultFitter(), "Simplex");
182  bool ret = fFitter->FitFCN(*fObjFunc);
183  return (ret) ? 0 : -1;
184  }
185  //SCan
186  if (scommand.Contains("SCA")) {
187 
188  if (!fObjFunc) {
189  Error("ExecuteCommand","FCN must set before executing this command");
190  return -1;
191  }
192 
193  fFitter->Config().SetMinimizer(GetDefaultFitter(), "Scan");
194  bool ret = fFitter->FitFCN(*fObjFunc);
195  return (ret) ? 0 : -1;
196  }
197  // MINOS
198  else if (scommand.Contains("MINO")) {
199 
200  if (fFitter->Config().MinosErrors() ) return 0;
201 
202  if (!fObjFunc) {
203  Error("ExecuteCommand","FCN must set before executing this command");
204  return -1;
205  }
206  // do only MINOS. need access to minimizer. For the moment re-run fitting with minos options
207  fFitter->Config().SetMinosErrors(true);
208  // set new parameter values
209 
210  fFitter->Config().SetMinimizer(GetDefaultFitter(), "Migrad"); // redo -minimization with Minos
211  bool ret = fFitter->FitFCN(*fObjFunc);
212  return (ret) ? 0 : -1;
213 
214  }
215  //HESSE
216  else if (scommand.Contains("HES")) {
217 
218  if (fFitter->Config().ParabErrors() ) return 0;
219 
220  if (!fObjFunc) {
221  Error("ExecuteCommand","FCN must set before executing this command");
222  return -1;
223  }
224 
225  // do only HESSE. need access to minimizer. For the moment re-run fitting with hesse options
226  fFitter->Config().SetParabErrors(true);
227  fFitter->Config().SetMinimizer(GetDefaultFitter(), "Migrad"); // redo -minimization with Minos
228  bool ret = fFitter->FitFCN(*fObjFunc);
229  return (ret) ? 0 : -1;
230  }
231 
232  // FIX
233  else if (scommand.Contains("FIX")) {
234  for(int i = 0; i < nargs; i++) {
235  FixParameter(int(args[i])-1);
236  }
237  return 0;
238  }
239  // SET LIMIT (upper and lower)
240  else if (scommand.Contains("SET LIM")) {
241  if (nargs < 3) {
242  Error("ExecuteCommand","Invalid parameters given in SET LIMIT");
243  return -1;
244  }
245  int ipar = int(args[0]);
246  if (!ValidParameterIndex(ipar) ) return -1;
247  double low = args[1];
248  double up = args[2];
249  fFitter->Config().ParSettings(ipar).SetLimits(low,up);
250  return 0;
251  }
252  // SET PRINT
253  else if (scommand.Contains("SET PRIN")) {
254  if (nargs < 1) return -1;
255  fFitter->Config().MinimizerOptions().SetPrintLevel(int(args[0]) );
256  return 0;
257  }
258  // SET ERR
259  else if (scommand.Contains("SET ERR")) {
260  if (nargs < 1) return -1;
261  fFitter->Config().MinimizerOptions().SetPrintLevel(int( args[0]) );
262  return 0;
263  }
264  // SET STRATEGY
265  else if (scommand.Contains("SET STR")) {
266  if (nargs < 1) return -1;
267  fFitter->Config().MinimizerOptions().SetStrategy(int(args[0]) );
268  return 0;
269  }
270  //SET GRAD (not impl.)
271  else if (scommand.Contains("SET GRA")) {
272  // not yet available
273  // fGradient = true;
274  return -1;
275  }
276  //SET NOW (not impl.)
277  else if (scommand.Contains("SET NOW")) {
278  // no warning (works only for TMinuit)
279  // fGradient = true;
280  return -1;
281  }
282  // CALL FCN
283  else if (scommand.Contains("CALL FCN")) {
284  // call fcn function (global pointer to free function)
285 
286  if (nargs < 1 || fFCN == 0 ) return -1;
287  int npar = fObjFunc->NDim();
288  // use values in fit result if existing otherwise in ParameterSettings
289  std::vector<double> params(npar);
290  for (int i = 0; i < npar; ++i)
291  params[i] = GetParameter(i);
292 
293  double fval = 0;
294  (*fFCN)(npar, 0, fval, &params[0],int(args[0]) ) ;
295  return 0;
296  }
297  else {
298  // other commands passed
299  Error("ExecuteCommand","Invalid or not supported command given %s",command);
300  return -1;
301  }
302 }
303 
304 ////////////////////////////////////////////////////////////////////////////////
305 /// Check if ipar is a valid parameter index
306 
308  int nps = fFitter->Config().ParamsSettings().size();
309  if (ipar < 0 || ipar >= nps ) {
310  std::string msg = ROOT::Math::Util::ToString(ipar) + " is an invalid Parameter index";
311  Error("ValidParameterIndex","%s",msg.c_str());
312  return false;
313  }
314  return true;
315 }
316 
317 ////////////////////////////////////////////////////////////////////////////////
318 /// Fix the parameter
319 
321  if (ValidParameterIndex(ipar) )
322  fFitter->Config().ParSettings(ipar).Fix();
323 }
324 
325 ////////////////////////////////////////////////////////////////////////////////
326 /// Computes point-by-point confidence intervals for the fitted function.
327 /// \param n number of points
328 /// \param ndim dimensions of points
329 /// \param x points, at which to compute the intervals, for ndim > 1
330 /// should be in order: (x0,y0, x1, y1, ... xn, yn)
331 /// \param ci computed intervals are returned in this array
332 /// \param cl confidence level, default=0.95
333 ///
334 /// NOTE, that the intervals are approximate for nonlinear(in parameters) models
335 
337 {
338  if (!fFitter->Result().IsValid()) {
339  Error("GetConfidenceIntervals","Cannot compute confidence intervals with an invalide fit result");
340  return;
341  }
342 
343  fFitter->Result().GetConfidenceIntervals(n,ndim,1,x,ci,cl);
344 }
345 
346 ////////////////////////////////////////////////////////////////////////////////
347 /// Computes confidence intervals at level cl. Default is 0.95
348 /// The TObject parameter can be a TGraphErrors, a TGraph2DErrors or a TH1,2,3.
349 /// For Graphs, confidence intervals are computed for each point,
350 /// the value of the graph at that point is set to the function value at that
351 /// point, and the graph y-errors (or z-errors) are set to the value of
352 /// the confidence interval at that point.
353 /// For Histograms, confidence intervals are computed for each bin center
354 /// The bin content of this bin is then set to the function value at the bin
355 /// center, and the bin error is set to the confidence interval value.
356 //
357 /// NOTE: confidence intervals are approximate for nonlinear models!
358 ///
359 /// Allowed combinations:
360 ///
361 /// Fitted object | Passed object
362 /// --------------------------|------------------
363 /// TGraph | TGraphErrors, TH1
364 /// TGraphErrors, AsymmErrors | TGraphErrors, TH1
365 /// TH1 | TGraphErrors, TH1
366 /// TGraph2D | TGraph2DErrors, TH2
367 /// TGraph2DErrors | TGraph2DErrors, TH2
368 /// TH2 | TGraph2DErrors, TH2
369 /// TH3 | TH3
370 
372 {
373  if (!fFitter->Result().IsValid() ) {
374  Error("GetConfidenceIntervals","Cannot compute confidence intervals with an invalide fit result");
375  return;
376  }
377 
378  // get data dimension from fit object
379  int datadim = 1;
380  TObject * fitobj = GetObjectFit();
381  if (!fitobj) {
382  Error("GetConfidenceIntervals","Cannot compute confidence intervals without a fitting object");
383  return;
384  }
385 
386  if (fitobj->InheritsFrom(TGraph2D::Class())) datadim = 2;
387  if (fitobj->InheritsFrom(TH1::Class())) {
388  TH1 * h1 = dynamic_cast<TH1*>(fitobj);
389  assert(h1 != 0);
390  datadim = h1->GetDimension();
391  }
392 
393  if (datadim == 1) {
394  if (!obj->InheritsFrom(TGraphErrors::Class()) && !obj->InheritsFrom(TH1::Class() ) ) {
395  Error("GetConfidenceIntervals", "Invalid object passed for storing confidence level data, must be a TGraphErrors or a TH1");
396  return;
397  }
398  }
399  if (datadim == 2) {
400  if (!obj->InheritsFrom(TGraph2DErrors::Class()) && !obj->InheritsFrom(TH2::Class() ) ) {
401  Error("GetConfidenceIntervals", "Invalid object passed for storing confidence level data, must be a TGraph2DErrors or a TH2");
402  return;
403  }
404  }
405  if (datadim == 3) {
406  if (!obj->InheritsFrom(TH3::Class() ) ) {
407  Error("GetConfidenceIntervals", "Invalid object passed for storing confidence level data, must be a TH3");
408  return;
409  }
410  }
411 
412  // fill bin data (for the moment use all ranges) according to object passed
414  data.Opt().fUseEmpty = true; // need to use all bins of given histograms
415  // call appropriate function according to type of object
416  if (obj->InheritsFrom(TGraph::Class()) )
417  ROOT::Fit::FillData(data, dynamic_cast<TGraph *>(obj) );
418  else if (obj->InheritsFrom(TGraph2D::Class()) )
419  ROOT::Fit::FillData(data, dynamic_cast<TGraph2D *>(obj) );
420 // else if (obj->InheritsFrom(TMultiGraph::Class()) )
421 // ROOT::Fit::FillData(data, dynamic_cast<TMultiGraph *>(obj) );
422  else if (obj->InheritsFrom(TH1::Class()) )
423  ROOT::Fit::FillData(data, dynamic_cast<TH1 *>(obj) );
424 
425 
426  unsigned int n = data.Size();
427 
428  std::vector<double> ci( n );
429 
430  fFitter->Result().GetConfidenceIntervals(data,&ci[0],cl);
431 
432  const ROOT::Math::IParamMultiFunction * func = fFitter->Result().FittedFunction();
433  assert(func != 0);
434 
435  // fill now the object with cl data
436  for (unsigned int i = 0; i < n; ++i) {
437  const double * x = data.Coords(i);
438  double y = (*func)( x ); // function is evaluated using its parameters
439 
440  if (obj->InheritsFrom(TGraphErrors::Class()) ) {
441  TGraphErrors * gr = dynamic_cast<TGraphErrors *> (obj);
442  assert(gr != 0);
443  gr->SetPoint(i, *x, y);
444  gr->SetPointError(i, 0, ci[i]);
445  }
446  if (obj->InheritsFrom(TGraph2DErrors::Class()) ) {
447  TGraph2DErrors * gr = dynamic_cast<TGraph2DErrors *> (obj);
448  assert(gr != 0);
449  gr->SetPoint(i, x[0], x[1], y);
450  gr->SetPointError(i, 0, 0, ci[i]);
451  }
452  if (obj->InheritsFrom(TH1::Class()) ) {
453  TH1 * h1 = dynamic_cast<TH1 *> (obj);
454  assert(h1 != 0);
455  int ibin = 0;
456  if (datadim == 1) ibin = h1->FindBin(*x);
457  if (datadim == 2) ibin = h1->FindBin(x[0],x[1]);
458  if (datadim == 3) ibin = h1->FindBin(x[0],x[1],x[2]);
459  h1->SetBinContent(ibin, y);
460  h1->SetBinError(ibin, ci[i]);
461  }
462  }
463 
464 }
465 
466 ////////////////////////////////////////////////////////////////////////////////
467 /// Get the error matrix in a pointer to a NxN array.
468 /// excluding the fixed parameters
469 
471  unsigned int nfreepar = GetNumberFreeParameters();
472  unsigned int ntotpar = GetNumberTotalParameters();
473 
474  if (fCovar.size() != nfreepar*nfreepar )
475  fCovar.resize(nfreepar*nfreepar);
476 
477  if (!fFitter->Result().IsValid() ) {
478  Warning("GetCovarianceMatrix","Invalid fit result");
479  return 0;
480  }
481 
482  unsigned int l = 0;
483  for (unsigned int i = 0; i < ntotpar; ++i) {
484  if (fFitter->Config().ParSettings(i).IsFixed() ) continue;
485  unsigned int m = 0;
486  for (unsigned int j = 0; j < ntotpar; ++j) {
487  if (fFitter->Config().ParSettings(j).IsFixed() ) continue;
488  unsigned int index = nfreepar*l + m;
489  assert(index < fCovar.size() );
490  fCovar[index] = fFitter->Result().CovMatrix(i,j);
491  m++;
492  }
493  l++;
494  }
495  return &(fCovar.front());
496 }
497 
498 ////////////////////////////////////////////////////////////////////////////////
499 /// Get error matrix element (return all zero if matrix is not available)
500 
502  unsigned int np2 = fCovar.size();
503  unsigned int npar = GetNumberFreeParameters();
504  if ( np2 == 0 || np2 != npar *npar ) {
505  double * c = GetCovarianceMatrix();
506  if (c == 0) return 0;
507  }
508  return fCovar[i*npar + j];
509 }
510 
511 ////////////////////////////////////////////////////////////////////////////////
512 /// Get fit errors
513 
515  if (!ValidParameterIndex(ipar) ) return -1;
516 
517  const ROOT::Fit::FitResult & result = fFitter->Result();
518  if (!result.IsValid() ) {
519  Warning("GetErrors","Invalid fit result");
520  return -1;
521  }
522 
523  eparab = result.Error(ipar);
524  eplus = result.UpperError(ipar);
525  eminus = result.LowerError(ipar);
526  globcc = result.GlobalCC(ipar);
527  return 0;
528 }
529 
530 ////////////////////////////////////////////////////////////////////////////////
531 /// Number of total parameters
532 
534  return fFitter->Result().NTotalParameters();
535 }
537  // number of variable parameters
538  return fFitter->Result().NFreeParameters();
539 }
540 
541 ////////////////////////////////////////////////////////////////////////////////
542 /// Parameter error
543 
545  if (fFitter->Result().IsEmpty() ) {
546  if (ValidParameterIndex(ipar) ) return fFitter->Config().ParSettings(ipar).StepSize();
547  else return 0;
548  }
549  return fFitter->Result().Error(ipar);
550 }
551 
552 ////////////////////////////////////////////////////////////////////////////////
553 /// Parameter value
554 
556  if (fFitter->Result().IsEmpty() ) {
557  if (ValidParameterIndex(ipar) ) return fFitter->Config().ParSettings(ipar).Value();
558  else return 0;
559  }
560  return fFitter->Result().Value(ipar);
561 }
562 
563 ////////////////////////////////////////////////////////////////////////////////
564 /// Get all parameter info (name, value, errors)
565 
566 Int_t TBackCompFitter::GetParameter(Int_t ipar,char *name,Double_t &value,Double_t &verr,Double_t &vlow, Double_t &vhigh) const {
567  if (!ValidParameterIndex(ipar) ) {
568  return -1;
569  }
570  const std::string & pname = fFitter->Config().ParSettings(ipar).Name();
571  const char * c = pname.c_str();
572  std::copy(c,c + pname.size(),name);
573 
574  if (fFitter->Result().IsEmpty() ) {
575  value = fFitter->Config().ParSettings(ipar).Value();
576  verr = fFitter->Config().ParSettings(ipar).Value(); // error is step size in this case
577  vlow = fFitter->Config().ParSettings(ipar).LowerLimit(); // vlow is lower limit in this case
578  vhigh = fFitter->Config().ParSettings(ipar).UpperLimit(); // vlow is lower limit in this case
579  return 1;
580  }
581  else {
582  value = fFitter->Result().Value(ipar);
583  verr = fFitter->Result().Error(ipar);
584  vlow = fFitter->Result().LowerError(ipar);
585  vhigh = fFitter->Result().UpperError(ipar);
586  }
587  return 0;
588 }
589 
590 ////////////////////////////////////////////////////////////////////////////////
591 /// Return name of parameter ipar
592 
593 const char *TBackCompFitter::GetParName(Int_t ipar) const {
594  if (!ValidParameterIndex(ipar) ) {
595  return 0;
596  }
597  return fFitter->Config().ParSettings(ipar).Name().c_str();
598 }
599 
600 ////////////////////////////////////////////////////////////////////////////////
601 /// Get fit statistical information
602 
603 Int_t TBackCompFitter::GetStats(Double_t &amin, Double_t &edm, Double_t &errdef, Int_t &nvpar, Int_t &nparx) const {
604  const ROOT::Fit::FitResult & result = fFitter->Result();
605  amin = result.MinFcnValue();
606  edm = result.Edm();
607  errdef = fFitter->Config().MinimizerOptions().ErrorDef();
608  nvpar = result.NFreeParameters();
609  nparx = result.NTotalParameters();
610  return 0;
611 }
612 
613 ////////////////////////////////////////////////////////////////////////////////
614 /// Sum of log (un-needed)
615 
617  Warning("GetSumLog","Dummy method - returned 0");
618  return 0.;
619 }
620 
621 ////////////////////////////////////////////////////////////////////////////////
622 /// Query if parameter ipar is fixed
623 
625  if (!ValidParameterIndex(ipar) ) {
626  return false;
627  }
628  return fFitter->Config().ParSettings(ipar).IsFixed();
629 }
630 
631 ////////////////////////////////////////////////////////////////////////////////
632 /// Print the fit result.
633 /// Use PrintResults function in case of Minuit for old -style printing
634 
636  if (fFitter->GetMinimizer() && fFitter->Config().MinimizerType() == "Minuit")
637  fFitter->GetMinimizer()->PrintResults();
638  else {
639  if (level > 0) fFitter->Result().Print(std::cout);
640  if (level > 1) fFitter->Result().PrintCovMatrix(std::cout);
641  }
642  // need to print minos errors and globalCC + other info
643 }
644 
645 ////////////////////////////////////////////////////////////////////////////////
646 /// Release a fit parameter
647 
649  if (ValidParameterIndex(ipar) )
650  fFitter->Config().ParSettings(ipar).Release();
651 }
652 
653 ////////////////////////////////////////////////////////////////////////////////
654 /// Set fit method (chi2 or likelihood).
655 /// According to the method the appropriate FCN function will be created
656 
657 void TBackCompFitter::SetFitMethod(const char *) {
658  Info("SetFitMethod","non supported method");
659 }
660 
661 ////////////////////////////////////////////////////////////////////////////////
662 /// Set (add) a new fit parameter passing initial value, step size (verr) and parameter limits
663 /// if vlow > vhigh the parameter is unbounded
664 /// if the stepsize (verr) == 0 the parameter is treated as fixed
665 
666 Int_t TBackCompFitter::SetParameter(Int_t ipar,const char *parname,Double_t value,Double_t verr,Double_t vlow, Double_t vhigh) {
667  std::vector<ROOT::Fit::ParameterSettings> & parlist = fFitter->Config().ParamsSettings();
668  if ( ipar >= (int) parlist.size() ) parlist.resize(ipar+1);
669  ROOT::Fit::ParameterSettings ps(parname, value, verr);
670  if (verr == 0) ps.Fix();
671  if (vlow < vhigh) ps.SetLimits(vlow, vhigh);
672  parlist[ipar] = ps;
673  return 0;
674 }
675 
676 //______________________________________________________________________________
677 // static method evaluating FCN
678 // void TBackCompFitter::FCN( int &, double * , double & f, double * x , int /* iflag */) {
679 // // get static instance of fitter
680 // TBackCompFitter * fitter = dynamic_cast<TBackCompFitter *>(TVirtualFitter::GetFitter());
681 // assert(fitter);
682 // if (fitter->fObjFunc == 0) fitter->RecreateFCN();
683 // assert(fitter->fObjFunc);
684 // f = (*(fitter.fObjFunc) )(x);
685 // }
686 
687 ////////////////////////////////////////////////////////////////////////////////
688 /// Recreate a minimizer instance using the function and data
689 /// set objective function in minimizers function to re-create FCN from stored data object and fit options
690 
692  assert(fFitData.get());
693 
694  // case of standard fits (not made fia Fitter::FitFCN)
695  if (fFitter->Result().FittedFunction() != 0) {
696 
697  if (fModelFunc) delete fModelFunc;
698  fModelFunc = dynamic_cast<ROOT::Math::IParamMultiFunction *>((fFitter->Result().FittedFunction())->Clone());
699  assert(fModelFunc);
700 
701  // create fcn functions, should consider also gradient case
702  const ROOT::Fit::BinData * bindata = dynamic_cast<const ROOT::Fit::BinData *>(fFitData.get());
703  if (bindata) {
704  if (GetFitOption().Like )
706  else
708  }
709  else {
710  const ROOT::Fit::UnBinData * unbindata = dynamic_cast<const ROOT::Fit::UnBinData *>(fFitData.get());
711  assert(unbindata);
713  }
714  }
715 
716  // recreate the minimizer
717  fMinimizer = fFitter->Config().CreateMinimizer();
718  if (fMinimizer == 0) {
719  Error("SetMinimizerFunction","cannot create minimizer %s",fFitter->Config().MinimizerType().c_str() );
720  }
721  else {
722  if (!fObjFunc) {
723  Error("SetMinimizerFunction","Object Function pointer is NULL");
724  }
725  else
726  fMinimizer->SetFunction(*fObjFunc);
727  }
728 
729 }
730 
731 ////////////////////////////////////////////////////////////////////////////////
732 /// Override setFCN to use the Adapter to Minuit2 FCN interface
733 /// To set the address of the minimization function
734 
736 {
737  fFCN = fcn;
738  if (fObjFunc) delete fObjFunc;
740  DoSetDimension();
741 }
742 
743 
744 ////////////////////////////////////////////////////////////////////////////////
745 /// Set the objective function for fitting
746 /// Needed if fitting directly using TBackCompFitter class
747 /// The class clones a copy of the function and manages it
748 
750  if (fObjFunc) delete fObjFunc;
751  fObjFunc = fcn->Clone();
752 }
753 
754 ////////////////////////////////////////////////////////////////////////////////
755 /// Private method to set dimension in objective function
756 
758  if (!fObjFunc) return;
759  ROOT::Fit::FcnAdapter * fobj = dynamic_cast<ROOT::Fit::FcnAdapter*>(fObjFunc);
760  assert(fobj != 0);
761  int ndim = fFitter->Config().ParamsSettings().size();
762  if (ndim != 0) fobj->SetDimension(ndim);
763 }
764 
765 ////////////////////////////////////////////////////////////////////////////////
766 /// Return a pointer to the objective function (FCN)
767 /// If fitting directly using TBackCompFitter the pointer is managed by the class,
768 /// which has been set previously when calling SetObjFunction or SetFCN
769 /// Otherwise if the class is used in the backward compatible mode (e.g. after having fitted a TH1)
770 /// the return pointer will be valid after fitting and as long a new fit will not be done.
771 
773  if (fObjFunc) return fObjFunc;
774  return fFitter->GetFCN();
775 }
776 
777 ////////////////////////////////////////////////////////////////////////////////
778 /// Return a pointer to the minimizer.
779 /// the return pointer will be valid after fitting and as long a new fit will not be done.
780 /// For keeping a minimizer pointer the method ReCreateMinimizer() could eventually be used
781 
783  if (fMinimizer) return fMinimizer;
784  return fFitter->GetMinimizer();
785 }
786 
787 ////////////////////////////////////////////////////////////////////////////////
788 /// Return a new copy of the TFitResult object which needs to be deleted later by the user
789 
791  if (!fFitter.get() ) return 0;
792  return new TFitResult( fFitter->Result() );
793 }
794 
795 ////////////////////////////////////////////////////////////////////////////////
796 /// Scan parameter ipar between value of xmin and xmax
797 /// A graph must be given which will be on return filled with the scan resul
798 /// If the graph size is zero, a default size n = 40 will be used
799 
800 bool TBackCompFitter::Scan(unsigned int ipar, TGraph * gr, double xmin, double xmax )
801 {
802 
803  if (!gr) return false;
804  ROOT::Math::Minimizer * minimizer = fFitter->GetMinimizer();
805  if (!minimizer) {
806  Error("Scan","Minimizer is not available - cannot scan before fitting");
807  return false;
808  }
809 
810  unsigned int npoints = gr->GetN();
811  if (npoints == 0) {
812  npoints = 40;
813  gr->Set(npoints);
814  }
815  bool ret = minimizer->Scan( ipar, npoints, gr->GetX(), gr->GetY(), xmin, xmax);
816  if ((int) npoints < gr->GetN() ) gr->Set(npoints);
817  return ret;
818 }
819 
820 //______________________________________________________________________________
821 // bool TBackCompFitter::Scan2D(unsigned int ipar, unsigned int jpar, TGraph2D * gr,
822 // double xmin = 0, double xmax = 0, double ymin = 0, double ymax = 0) {
823 // // scan the parameters ipar between values of [xmin,xmax] and
824 // // jpar between values of [ymin,ymax] and
825 // // a graph2D must be given which will be on return filled with the scan resul
826 // // If the graph size is zero, a default size n = 20x20 will be used
827 // //*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*
828 
829 // if (!gr) return false;
830 // if (!fMinimizer) {
831 // Error("Scan","Minimizer is not available - cannot scan before fitting");
832 // return false;
833 // }
834 // unsigned int npoints = gr->GetN();
835 // if (npoints == 0) {
836 // npoints = 40;
837 // gr->Set(npoints);
838 // }
839 // // to be implemented
840 // for (unsigned int ix = 0; ix < npoints; ++ix) {
841 // return fMinimizer->Scan( ipar, npoints, gr->GetX(), gr->GetY(), xmin, xmax);
842 
843 // }
844 
845 ////////////////////////////////////////////////////////////////////////////////
846 /// Create a 2D contour around the minimum for the parameter ipar and jpar
847 /// if a minimum does not exist or is invalid it will return false
848 /// on exit a TGraph is filled with the contour points
849 /// the number of contour points is determined by the size of the TGraph.
850 /// if the size is zero a default number of points = 20 is used
851 /// pass optionally the confidence level, default is 0.683
852 /// it is assumed that ErrorDef() defines the right error definition
853 /// (i.e 1 sigma error for one parameter). If not the confidence level are scaled to new level
854 
855 bool TBackCompFitter::Contour(unsigned int ipar, unsigned int jpar, TGraph * gr, double confLevel) {
856  if (!gr) return false;
857  ROOT::Math::Minimizer * minimizer = fFitter->GetMinimizer();
858  if (!minimizer) {
859  Error("Scan","Minimizer is not available - cannot scan before fitting");
860  return false;
861  }
862 
863  // get error level used for fitting
864  double upScale = fFitter->Config().MinimizerOptions().ErrorDef();
865 
866  double upVal = TMath::ChisquareQuantile( confLevel, 2); // 2 is number of parameter we do the contour
867 
868  // set required error definition in minimizer
869  minimizer->SetErrorDef (upScale * upVal);
870 
871  unsigned int npoints = gr->GetN();
872  if (npoints == 0) {
873  npoints = 40;
874  gr->Set(npoints);
875  }
876  bool ret = minimizer->Contour( ipar, jpar, npoints, gr->GetX(), gr->GetY());
877  if ((int) npoints < gr->GetN() ) gr->Set(npoints);
878 
879  // restore the error level used for fitting
880  minimizer->SetErrorDef ( upScale);
881 
882  return ret;
883 }
884 
885 
void DoSetDimension()
Private method to set dimension in objective function.
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:3565
virtual Double_t * GetCovarianceMatrix() const
Get the error matrix in a pointer to a NxN array.
virtual Double_t GetCovarianceMatrixElement(Int_t i, Int_t j) const
Get error matrix element (return all zero if matrix is not available)
float xmin
Definition: THbookFile.cxx:93
virtual void PrintResults(Int_t level, Double_t amin) const
Print the fit result.
virtual void Info(const char *method, const char *msgfmt,...) const
Issue info message.
Definition: TObject.cxx:854
void SetErrorDef(double up)
set scale for calculating the errors
Definition: Minimizer.h:464
auto * m
Definition: textangle.C:8
virtual Int_t GetStats(Double_t &amin, Double_t &edm, Double_t &errdef, Int_t &nvpar, Int_t &nparx) const
Get fit statistical information.
virtual void Clear(Option_t *option="")
Clear resources for consecutive fits.
ROOT::Math::Minimizer * GetMinimizer() const
Return a pointer to the minimizer.
bool Contour(unsigned int ipar, unsigned int jpar, TGraph *gr, double confLevel=0.683)
Create a 2D contour around the minimum for the parameter ipar and jpar if a minimum does not exist or...
ROOT::Math::IMultiGenFunction * GetObjFunction() const
Return a pointer to the objective function (FCN) If fitting directly using TBackCompFitter the pointe...
double Error(unsigned int i) const
parameter error by index
Definition: FitResult.h:187
virtual Int_t ExecuteCommand(const char *command, Double_t *args, Int_t nargs)
Execute the command (Fortran Minuit compatible interface)
const char Option_t
Definition: RtypesCore.h:62
double Edm() const
Expected distance from minimum.
Definition: FitResult.h:127
virtual Int_t GetNumberFreeParameters() const
Class, describing value, limits and step size of the parameters Provides functionality also to set/re...
bool Scan(unsigned int ipar, TGraph *gr, double xmin=0, double xmax=0)
Scan parameter ipar between value of xmin and xmax A graph must be given which will be on return fill...
virtual void SetName(const char *name)
Set the name of the TNamed.
Definition: TNamed.cxx:140
ROOT::Math::Minimizer * fMinimizer
pointer to fitter object
void ToUpper()
Change string to upper case.
Definition: TString.cxx:1112
LogLikelihoodFCN class for likelihood fits.
void ReCreateMinimizer()
Recreate a minimizer instance using the function and data set objective function in minimizers functi...
static constexpr double ps
Basic string class.
Definition: TString.h:125
virtual IBaseFunctionMultiDimTempl< T > * Clone() const =0
Clone a function.
virtual void SetFCN(void(*fcn)(Int_t &, Double_t *, Double_t &f, Double_t *, Int_t))
Override setFCN to use the Adapter to Minuit2 FCN interface To set the address of the minimization fu...
Class describing the unbinned data sets (just x coordinates values) of any dimensions.
Definition: UnBinData.h:42
Backward compatible implementation of TVirtualFitter.
int Int_t
Definition: RtypesCore.h:41
bool Bool_t
Definition: RtypesCore.h:59
TFitResult * GetTFitResult() const
Return a new copy of the TFitResult object which needs to be deleted later by the user...
double MinFcnValue() const
Return value of the objective function (chi2 or likelihood) used in the fit.
Definition: FitResult.h:121
unsigned int NTotalParameters() const
get total number of parameters
Definition: FitResult.h:130
static const char * GetDefaultFitter()
static: return the name of the default fitter
const double * Coords(unsigned int ipoint) const
return a pointer to the coordinates data for the given fit point
Definition: FitData.h:246
virtual Double_t GetParError(Int_t ipar) const
Parameter error.
virtual Int_t GetDimension() const
Definition: TH1.h:277
Double_t ChisquareQuantile(Double_t p, Double_t ndf)
Evaluate the quantiles of the chi-squared probability distribution function.
Definition: TMath.cxx:2148
Double_t x[n]
Definition: legend1.C:17
TBackCompFitter()
Constructor needed by TVirtualFitter interface.
void Class()
Definition: Class.C:29
Extends the ROOT::Fit::Result class with a TNamed inheritance providing easy possibility for I/O...
Definition: TFitResult.h:30
class evaluating the log likelihood for binned Poisson likelihood fits it is template to distinguish ...
virtual ~TBackCompFitter()
Destructor - delete the managed objects.
virtual void SetPointError(Int_t i, Double_t ex, Double_t ey, Double_t ez)
Set ex, ey and ez values for point number i.
Abstract Minimizer class, defining the interface for the various minimizer (like Minuit2, Minuit, GSL, etc..) Plug-in&#39;s exist in ROOT to be able to instantiate the derived classes like ROOT::Math::GSLMinimizer or ROOT::Math::Minuit2Minimizer via the plug-in manager.
Definition: Minimizer.h:78
static constexpr double eplus
virtual Int_t GetNumberTotalParameters() const
Number of total parameters.
virtual bool Contour(unsigned int ivar, unsigned int jvar, unsigned int &npoints, double *xi, double *xj)
find the contour points (xi, xj) of the function for parameter ivar and jvar around the minimum The c...
Definition: Minimizer.h:379
void Fix()
fix the parameter
double LowerError(unsigned int i) const
lower Minos error. If Minos has not run for parameter i return the parabolic error ...
Definition: FitResult.cxx:389
TH1F * h1
Definition: legend1.C:5
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:8461
unsigned int Size() const
return number of fit points
Definition: FitData.h:303
virtual Bool_t IsFixed(Int_t ipar) const
Query if parameter ipar is fixed.
virtual void FixParameter(Int_t ipar)
Fix the parameter.
virtual Int_t GetErrors(Int_t ipar, Double_t &eplus, Double_t &eminus, Double_t &eparab, Double_t &globcc) const
Get fit errors.
virtual void SetObjFunction(ROOT::Math::IMultiGenFunction *f)
Set the objective function for fitting Needed if fitting directly using TBackCompFitter class The cla...
virtual Foption_t GetFitOption() const
Documentation for the abstract class IBaseFunctionMultiDim.
Definition: IFunction.h:62
Chi2FCN class for binnned fits using the least square methods.
Definition: Chi2FCN.h:49
ROOT::Math::IMultiGenFunction * fObjFunc
void FillData(BinData &dv, const TH1 *hist, TF1 *func=0)
fill the data vector from a TH1.
unsigned int NFreeParameters() const
get total number of free parameters
Definition: FitResult.h:135
virtual Bool_t InheritsFrom(const char *classname) const
Returns kTRUE if object inherits from class "classname".
Definition: TObject.cxx:443
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:8477
virtual void Error(const char *method, const char *msgfmt,...) const
Issue error message.
Definition: TObject.cxx:880
const DataOptions & Opt() const
access to options
Definition: FitData.h:319
virtual Double_t GetSumLog(Int_t i)
Sum of log (un-needed)
Int_t GetN() const
Definition: TGraph.h:122
int Like
Definition: Foption.h:34
Class describing the binned data sets : vectors of x coordinates, y values and optionally error on y ...
Definition: BinData.h:53
float xmax
Definition: THbookFile.cxx:93
double UpperError(unsigned int i) const
upper Minos error. If Minos has not run for parameter i return the parabolic error ...
Definition: FitResult.cxx:396
TGraphErrors * gr
Definition: legend1.C:25
constexpr Double_t E()
Definition: TMath.h:74
Double_t * GetX() const
Definition: TGraph.h:129
virtual Double_t Chisquare(Int_t npar, Double_t *params) const
Do chisquare calculations in case of likelihood fits Do evaluation a the minimum only.
virtual void ReleaseParameter(Int_t ipar)
Release a fit parameter.
class containg the result of the fit and all the related information (fitted parameter values...
Definition: FitResult.h:48
#define ClassImp(name)
Definition: Rtypes.h:359
std::shared_ptr< ROOT::Fit::FitData > fFitData
virtual void SetPoint(Int_t i, Double_t x, Double_t y, Double_t z)
Set x, y and z values for point number i.
double Double_t
Definition: RtypesCore.h:55
bool IsValid() const
True if fit successful, otherwise false.
Definition: FitResult.h:115
Double_t y[n]
Definition: legend1.C:17
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
Definition: TString.h:570
The TH1 histogram class.
Definition: TH1.h:56
static constexpr double s
virtual TObject * Clone(const char *newname="") const
Make a clone of an object using the Streamer facility.
Definition: TNamed.cxx:74
Mother of all ROOT objects.
Definition: TObject.h:37
virtual void SetPoint(Int_t i, Double_t x, Double_t y)
Set x and y values for point number i.
Definition: TGraph.cxx:2184
Double_t * GetY() const
Definition: TGraph.h:130
std::string ToString(const T &val)
Utility function for conversion to strings.
Definition: Util.h:42
auto * l
Definition: textangle.C:4
std::vector< double > fCovar
A Graph is a graphics object made of two arrays X and Y with npoints each.
Definition: TGraph.h:41
virtual Int_t SetParameter(Int_t ipar, const char *parname, Double_t value, Double_t verr, Double_t vlow, Double_t vhigh)
Set (add) a new fit parameter passing initial value, step size (verr) and parameter limits if vlow > ...
A TGraphErrors is a TGraph with error bars.
Definition: TGraphErrors.h:26
void(* fFCN)(Int_t &npar, Double_t *gin, Double_t &f, Double_t *u, Int_t flag)
std::shared_ptr< ROOT::Fit::Fitter > fFitter
data of the fit
virtual const char * GetParName(Int_t ipar) const
Return name of parameter ipar.
void SetLimits(double low, double up)
set a double side limit, if low == up the parameter is fixed if low > up the limits are removed The c...
bool ValidParameterIndex(int ipar) const
Check if ipar is a valid parameter index.
virtual bool Scan(unsigned int ivar, unsigned int &nstep, double *x, double *y, double xmin=0, double xmax=0)
scan function minimum for variable i.
Definition: Minimizer.h:367
virtual void GetConfidenceIntervals(Int_t n, Int_t ndim, const Double_t *x, Double_t *ci, Double_t cl=0.95)
Computes point-by-point confidence intervals for the fitted function.
void SetDimension(int dim)
Definition: FcnAdapter.h:44
virtual void SetPointError(Double_t ex, Double_t ey)
Set ex and ey values for point pointed by the mouse.
virtual void Set(Int_t n)
Set number of points in the graph Existing coordinates are preserved New coordinates above fNpoints a...
Definition: TGraph.cxx:2133
double GlobalCC(unsigned int i) const
parameter global correlation coefficient
Definition: FitResult.h:211
virtual TObject * GetObjectFit() const
virtual void SetFitMethod(const char *name)
Set fit method (chi2 or likelihood).
const Int_t n
Definition: legend1.C:16
char name[80]
Definition: TGX11.cxx:109
ROOT::Math::IParamMultiFunction * fModelFunc
virtual void Warning(const char *method, const char *msgfmt,...) const
Issue warning message.
Definition: TObject.cxx:866
virtual unsigned int NDim() const =0
Retrieve the dimension of the function.
Graph 2D class with errors.
virtual Double_t GetParameter(Int_t ipar) const
Parameter value.