Logo ROOT  
Reference Guide
TF1.cxx
Go to the documentation of this file.
1 // @(#)root/hist:$Id$
2 // Author: Rene Brun 18/08/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 <iostream>
13 #include "strlcpy.h"
14 #include "snprintf.h"
15 #include "TROOT.h"
16 #include "TBuffer.h"
17 #include "TMath.h"
18 #include "TF1.h"
19 #include "TH1.h"
20 #include "TGraph.h"
21 #include "TVirtualPad.h"
22 #include "TStyle.h"
23 #include "TRandom.h"
24 #include "TObjString.h"
25 #include "TInterpreter.h"
26 #include "TPluginManager.h"
27 #include "TBrowser.h"
28 #include "TColor.h"
29 #include "TMethodCall.h"
30 #include "TF1Helper.h"
31 #include "TF1NormSum.h"
32 #include "TF1Convolution.h"
33 #include "TVirtualMutex.h"
34 #include "Math/WrappedFunction.h"
35 #include "Math/WrappedTF1.h"
36 #include "Math/BrentRootFinder.h"
37 #include "Math/BrentMinimizer1D.h"
38 #include "Math/BrentMethods.h"
39 #include "Math/Integrator.h"
41 #include "Math/IntegratorOptions.h"
42 #include "Math/GaussIntegrator.h"
46 #include "Math/Functor.h"
47 #include "Math/Minimizer.h"
48 #include "Math/MinimizerOptions.h"
49 #include "Math/Factory.h"
50 #include "Math/ChebyshevPol.h"
51 #include "Fit/FitResult.h"
52 // for I/O backward compatibility
53 #include "v5/TF1Data.h"
54 
55 #include "AnalyticalIntegrals.h"
56 
57 std::atomic<Bool_t> TF1::fgAbsValue(kFALSE);
59 std::atomic<Bool_t> TF1::fgAddToGlobList(kTRUE);
60 static Double_t gErrorTF1 = 0;
61 
62 using TF1Updater_t = void (*)(Int_t nobjects, TObject **from, TObject **to);
64 
65 
66 namespace {
67 struct TF1v5Convert : public TF1 {
68 public:
69  void Convert(ROOT::v5::TF1Data &from)
70  {
71  // convert old TF1 to new one
72  fNpar = from.GetNpar();
73  fNdim = from.GetNdim();
74  if (from.fType == 0) {
75  // formula functions
76  // if ndim is not 1 set xmin max to zero to avoid error in ctor
77  double xmin = from.fXmin;
78  double xmax = from.fXmax;
79  if (fNdim > 1) {
80  xmin = 0;
81  xmax = 0;
82  }
83  TF1 fnew(from.GetName(), from.GetExpFormula(), xmin, xmax);
84  if (fNdim > 1) {
85  fnew.SetRange(from.fXmin, from.fXmax);
86  }
87  fnew.Copy(*this);
88  // need to set parameter values
89  if (from.GetParameters())
90  fFormula->SetParameters(from.GetParameters());
91  } else {
92  // case of a function pointers
93  fParams.reset(new TF1Parameters(fNpar));
94  fName = from.GetName();
95  fTitle = from.GetTitle();
96  // need to set parameter values
97  if (from.GetParameters())
98  fParams->SetParameters(from.GetParameters());
99  }
100  // copy the other data members
101  fNpx = from.fNpx;
102  fType = (EFType)from.fType;
103  fNpfits = from.fNpfits;
104  fNDF = from.fNDF;
105  fChisquare = from.fChisquare;
106  fMaximum = from.fMaximum;
107  fMinimum = from.fMinimum;
108  fXmin = from.fXmin;
109  fXmax = from.fXmax;
110 
111  if (from.fParErrors)
112  fParErrors = std::vector<Double_t>(from.fParErrors, from.fParErrors + fNpar);
113  if (from.fParMin)
114  fParMin = std::vector<Double_t>(from.fParMin, from.fParMin + fNpar);
115  if (from.fParMax)
116  fParMax = std::vector<Double_t>(from.fParMax, from.fParMax + fNpar);
117  if (from.fNsave > 0) {
118  assert(from.fSave);
119  fSave = std::vector<Double_t>(from.fSave, from.fSave + from.fNsave);
120  }
121  // set the bits
122  for (int ibit = 0; ibit < 24; ++ibit)
123  if (from.TestBit(BIT(ibit)))
124  SetBit(BIT(ibit));
125 
126  // copy the graph attributes
127  auto &fromLine = static_cast<TAttLine &>(from);
128  fromLine.Copy(*this);
129  auto &fromFill = static_cast<TAttFill &>(from);
130  fromFill.Copy(*this);
131  auto &fromMarker = static_cast<TAttMarker &>(from);
132  fromMarker.Copy(*this);
133  }
134 };
135 } // unnamed namespace
136 
137 static void R__v5TF1Updater(Int_t nobjects, TObject **from, TObject **to)
138 {
139  auto **fromv5 = (ROOT::v5::TF1Data **)from;
140  auto **target = (TF1v5Convert **)to;
141 
142  for (int i = 0; i < nobjects; ++i) {
143  if (fromv5[i] && target[i])
144  target[i]->Convert(*fromv5[i]);
145  }
146 }
147 
149 
150 ClassImp(TF1);
151 
152 // class wrapping evaluation of TF1(x) - y0
153 class GFunc {
154  const TF1 *fFunction;
155  const double fY0;
156 public:
157  GFunc(const TF1 *function , double y): fFunction(function), fY0(y) {}
158  double operator()(double x) const
159  {
160  return fFunction->Eval(x) - fY0;
161  }
162 };
163 
164 // class wrapping evaluation of -TF1(x)
165 class GInverseFunc {
166  const TF1 *fFunction;
167 public:
168  GInverseFunc(const TF1 *function): fFunction(function) {}
169 
170  double operator()(double x) const
171  {
172  return - fFunction->Eval(x);
173  }
174 };
175 // class wrapping evaluation of -TF1(x) for multi-dimension
176 class GInverseFuncNdim {
177  TF1 *fFunction;
178 public:
179  GInverseFuncNdim(TF1 *function): fFunction(function) {}
180 
181  double operator()(const double *x) const
182  {
183  return - fFunction->EvalPar(x, (Double_t *)0);
184  }
185 };
186 
187 // class wrapping function evaluation directly in 1D interface (used for integration)
188 // and implementing the methods for the momentum calculations
189 
190 class TF1_EvalWrapper : public ROOT::Math::IGenFunction {
191 public:
192  TF1_EvalWrapper(TF1 *f, const Double_t *par, bool useAbsVal, Double_t n = 1, Double_t x0 = 0) :
193  fFunc(f),
194  fPar(((par) ? par : f->GetParameters())),
195  fAbsVal(useAbsVal),
196  fN(n),
197  fX0(x0)
198  {
199  fFunc->InitArgs(fX, fPar);
200  if (par) fFunc->SetParameters(par);
201  }
202 
204  {
205  // use default copy constructor
206  TF1_EvalWrapper *f = new TF1_EvalWrapper(*this);
207  f->fFunc->InitArgs(f->fX, f->fPar);
208  return f;
209  }
210  // evaluate |f(x)|
211  Double_t DoEval(Double_t x) const
212  {
213  // use evaluation with stored parameters (i.e. pass zero)
214  fX[0] = x;
215  Double_t fval = fFunc->EvalPar(fX, 0);
216  if (fAbsVal && fval < 0) return -fval;
217  return fval;
218  }
219  // evaluate x * |f(x)|
220  Double_t EvalFirstMom(Double_t x)
221  {
222  fX[0] = x;
223  return fX[0] * TMath::Abs(fFunc->EvalPar(fX, 0));
224  }
225  // evaluate (x - x0) ^n * f(x)
226  Double_t EvalNMom(Double_t x) const
227  {
228  fX[0] = x;
229  return TMath::Power(fX[0] - fX0, fN) * TMath::Abs(fFunc->EvalPar(fX, 0));
230  }
231 
232  TF1 *fFunc;
233  mutable Double_t fX[1];
234  const double *fPar;
235  Bool_t fAbsVal;
236  Double_t fN;
237  Double_t fX0;
238 };
239 
240 ////////////////////////////////////////////////////////////////////////////////
241 /** \class TF1
242  \ingroup Hist
243  \brief 1-Dim function class
244 
245 
246 ## TF1: 1-Dim function class
247 
248 A TF1 object is a 1-Dim function defined between a lower and upper limit.
249 The function may be a simple function based on a TFormula expression or a precompiled user function.
250 The function may have associated parameters.
251 TF1 graphics function is via the TH1 and TGraph drawing functions.
252 
253 The following types of functions can be created:
254 
255 1. [Expression using variable x and no parameters](\ref F1)
256 2. [Expression using variable x with parameters](\ref F2)
257 3. [Lambda Expression with variable x and parameters](\ref F3)
258 4. [A general C function with parameters](\ref F4)
259 5. [A general C++ function object (functor) with parameters](\ref F5)
260 6. [A member function with parameters of a general C++ class](\ref F6)
261 
262 
263 
264 \anchor F1
265 ### 1 - Expression using variable x and no parameters
266 
267 #### Case 1: inline expression using standard C++ functions/operators
268 
269 Begin_Macro(source)
270 {
271  TF1 *fa1 = new TF1("fa1","sin(x)/x",0,10);
272  fa1->Draw();
273 }
274 End_Macro
275 
276 #### Case 2: inline expression using a ROOT function (e.g. from TMath) without parameters
277 
278 
279 Begin_Macro(source)
280 {
281  TF1 *fa2 = new TF1("fa2","TMath::DiLog(x)",0,10);
282  fa2->Draw();
283 }
284 End_Macro
285 
286 #### Case 3: inline expression using a user defined CLING function by name
287 
288 ~~~~{.cpp}
289 Double_t myFunc(double x) { return x+sin(x); }
290 ....
291 TF1 *fa3 = new TF1("fa3","myFunc(x)",-3,5);
292 fa3->Draw();
293 ~~~~
294 
295 \anchor F2
296 ### 2 - Expression using variable x with parameters
297 
298 #### Case 1: inline expression using standard C++ functions/operators
299 
300 * Example a:
301 
302 
303 ~~~~{.cpp}
304 TF1 *fa = new TF1("fa","[0]*x*sin([1]*x)",-3,3);
305 ~~~~
306 
307 This creates a function of variable x with 2 parameters. The parameters must be initialized via:
308 
309 ~~~~{.cpp}
310  fa->SetParameter(0,value_first_parameter);
311  fa->SetParameter(1,value_second_parameter);
312 ~~~~
313 
314 
315 Parameters may be given a name:
316 
317 ~~~~{.cpp}
318  fa->SetParName(0,"Constant");
319 ~~~~
320 
321 * Example b:
322 
323 ~~~~{.cpp}
324  TF1 *fb = new TF1("fb","gaus(0)*expo(3)",0,10);
325 ~~~~
326 
327 
328 ``gaus(0)`` is a substitute for ``[0]*exp(-0.5*((x-[1])/[2])**2)`` and ``(0)`` means start numbering parameters at ``0``. ``expo(3)`` is a substitute for ``exp([3]+[4]*x)``.
329 
330 #### Case 2: inline expression using TMath functions with parameters
331 
332 ~~~~{.cpp}
333  TF1 *fb2 = new TF1("fa3","TMath::Landau(x,[0],[1],0)",-5,10);
334  fb2->SetParameters(0.2,1.3);
335  fb2->Draw();
336 ~~~~
337 
338 
339 
340 Begin_Macro
341 {
342  TCanvas *c = new TCanvas("c","c",0,0,500,300);
343  TF1 *fb2 = new TF1("fa3","TMath::Landau(x,[0],[1],0)",-5,10);
344  fb2->SetParameters(0.2,1.3); fb2->Draw();
345  return c;
346 }
347 End_Macro
348 
349 \anchor F3
350 ### 3 - A lambda expression with variables and parameters
351 
352 \since **6.00/00:**
353 TF1 supports using lambda expressions in the formula. This allows, by using a full C++ syntax the full power of lambda
354 functions and still maintain the capability of storing the function in a file which cannot be done with
355 function pointer or lambda written not as expression, but as code (see items below).
356 
357 Example on how using lambda to define a sum of two functions.
358 Note that is necessary to provide the number of parameters
359 
360 ~~~~{.cpp}
361 TF1 f1("f1","sin(x)",0,10);
362 TF1 f2("f2","cos(x)",0,10);
363 TF1 fsum("f1","[&](double *x, double *p){ return p[0]*f1(x) + p[1]*f2(x); }",0,10,2);
364 ~~~~
365 
366 \anchor F4
367 ### 4 - A general C function with parameters
368 
369 Consider the macro myfunc.C below:
370 
371 ~~~~{.cpp}
372  // Macro myfunc.C
373  Double_t myfunction(Double_t *x, Double_t *par)
374  {
375  Float_t xx =x[0];
376  Double_t f = TMath::Abs(par[0]*sin(par[1]*xx)/xx);
377  return f;
378  }
379  void myfunc()
380  {
381  TF1 *f1 = new TF1("myfunc",myfunction,0,10,2);
382  f1->SetParameters(2,1);
383  f1->SetParNames("constant","coefficient");
384  f1->Draw();
385  }
386  void myfit()
387  {
388  TH1F *h1=new TH1F("h1","test",100,0,10);
389  h1->FillRandom("myfunc",20000);
390  TF1 *f1 = (TF1 *)gROOT->GetFunction("myfunc");
391  f1->SetParameters(800,1);
392  h1->Fit("myfunc");
393  }
394 ~~~~
395 
396 
397 
398 In an interactive session you can do:
399 
400 ~~~~
401  Root > .L myfunc.C
402  Root > myfunc();
403  Root > myfit();
404 ~~~~
405 
406 
407 
408 TF1 objects can reference other TF1 objects of type A or B defined above. This excludes CLing or compiled functions. However, there is a restriction. A function cannot reference a basic function if the basic function is a polynomial polN.
409 
410 Example:
411 
412 ~~~~{.cpp}
413 {
414  TF1 *fcos = new TF1 ("fcos", "[0]*cos(x)", 0., 10.);
415  fcos->SetParNames( "cos");
416  fcos->SetParameter( 0, 1.1);
417 
418  TF1 *fsin = new TF1 ("fsin", "[0]*sin(x)", 0., 10.);
419  fsin->SetParNames( "sin");
420  fsin->SetParameter( 0, 2.1);
421 
422  TF1 *fsincos = new TF1 ("fsc", "fcos+fsin");
423 
424  TF1 *fs2 = new TF1 ("fs2", "fsc+fsc");
425 }
426 ~~~~
427 
428 
429 \anchor F5
430 ### 5 - A general C++ function object (functor) with parameters
431 
432 A TF1 can be created from any C++ class implementing the operator()(double *x, double *p). The advantage of the function object is that he can have a state and reference therefore what-ever other object. In this way the user can customize his function.
433 
434 Example:
435 
436 
437 ~~~~{.cpp}
438 class MyFunctionObject {
439  public:
440  // use constructor to customize your function object
441 
442  double operator() (double *x, double *p) {
443  // function implementation using class data members
444  }
445 };
446 {
447  ....
448  MyFunctionObject fobj;
449  TF1 * f = new TF1("f",fobj,0,1,npar); // create TF1 class.
450  .....
451 }
452 ~~~~
453 
454 #### Using a lambda function as a general C++ functor object
455 
456 From C++11 we can use both std::function or even better lambda functions to create the TF1.
457 As above the lambda must have the right signature but can capture whatever we want. For example we can make
458 a TF1 from the TGraph::Eval function as shown below where we use as function parameter the graph normalization.
459 
460 ~~~~{.cpp}
461 TGraph * g = new TGraph(npointx, xvec, yvec);
462 TF1 * f = new TF1("f",[&](double*x, double *p){ return p[0]*g->Eval(x[0]); }, xmin, xmax, 1);
463 ~~~~
464 
465 
466 \anchor F6
467 ### 6 - A member function with parameters of a general C++ class
468 
469 A TF1 can be created in this case from any member function of a class which has the signature of (double * , double *) and returning a double.
470 
471 Example:
472 
473 ~~~~{.cpp}
474 class MyFunction {
475  public:
476  ...
477  double Evaluate() (double *x, double *p) {
478  // function implementation
479  }
480 };
481 {
482  ....
483  MyFunction * fptr = new MyFunction(....); // create the user function class
484  TF1 * f = new TF1("f",fptr,&MyFunction::Evaluate,0,1,npar,"MyFunction","Evaluate"); // create TF1 class.
485 
486  .....
487 }
488 ~~~~
489 
490 See also the tutorial __math/exampleFunctor.C__ for a running example.
491 */
492 ////////////////////////////////////////////////////////////////////////////
493 
494 TF1 *TF1::fgCurrent = 0;
495 
496 
497 ////////////////////////////////////////////////////////////////////////////////
498 /// TF1 default constructor.
499 
501  TNamed(), TAttLine(), TAttFill(), TAttMarker(),
502  fXmin(0), fXmax(0), fNpar(0), fNdim(0), fType(EFType::kFormula)
503 {
504  SetFillStyle(0);
505 }
506 
507 
508 ////////////////////////////////////////////////////////////////////////////////
509 /// F1 constructor using a formula definition
510 ///
511 /// See TFormula constructor for explanation of the formula syntax.
512 ///
513 /// See tutorials: fillrandom, first, fit1, formula1, multifit
514 /// for real examples.
515 ///
516 /// Creates a function of type A or B between xmin and xmax
517 ///
518 /// if formula has the form "fffffff;xxxx;yyyy", it is assumed that
519 /// the formula string is "fffffff" and "xxxx" and "yyyy" are the
520 /// titles for the X and Y axis respectively.
521 
522 TF1::TF1(const char *name, const char *formula, Double_t xmin, Double_t xmax, EAddToList addToGlobList, bool vectorize) :
523  TNamed(name, formula), TAttLine(), TAttFill(), TAttMarker(), fType(EFType::kFormula)
524 {
525  if (xmin < xmax) {
526  fXmin = xmin;
527  fXmax = xmax;
528  } else {
529  fXmin = xmax; //when called from TF2,TF3
530  fXmax = xmin;
531  }
532  // Create rep formula (no need to add to gROOT list since we will add the TF1 object)
533 
534  // First check if we are making a convolution
535  if (TString(formula, 5) == "CONV(" && formula[strlen(formula) - 1] == ')') {
536  // Look for single ',' delimiter
537  int delimPosition = -1;
538  int parenCount = 0;
539  for (unsigned int i = 5; i < strlen(formula) - 1; i++) {
540  if (formula[i] == '(')
541  parenCount++;
542  else if (formula[i] == ')')
543  parenCount--;
544  else if (formula[i] == ',' && parenCount == 0) {
545  if (delimPosition == -1)
546  delimPosition = i;
547  else
548  Error("TF1", "CONV takes 2 arguments. Too many arguments found in : %s", formula);
549  }
550  }
551  if (delimPosition == -1)
552  Error("TF1", "CONV takes 2 arguments. Only one argument found in : %s", formula);
553 
554  // Having found the delimiter, define the first and second formulas
555  TString formula1 = TString(TString(formula)(5, delimPosition - 5));
556  TString formula2 = TString(TString(formula)(delimPosition + 1, strlen(formula) - 1 - (delimPosition + 1)));
557  // remove spaces from these formulas
558  formula1.ReplaceAll(' ', "");
559  formula2.ReplaceAll(' ', "");
560 
561  TF1 *function1 = (TF1 *)(gROOT->GetListOfFunctions()->FindObject(formula1));
562  if (function1 == nullptr)
563  function1 = new TF1((const char *)formula1, (const char *)formula1, xmin, xmax);
564  TF1 *function2 = (TF1 *)(gROOT->GetListOfFunctions()->FindObject(formula2));
565  if (function2 == nullptr)
566  function2 = new TF1((const char *)formula2, (const char *)formula2, xmin, xmax);
567 
568  // std::cout << "functions have been defined" << std::endl;
569 
570  TF1Convolution *conv = new TF1Convolution(function1, function2);
571 
572  // (note: currently ignoring `useFFT` option)
573  fNpar = conv->GetNpar();
574  fNdim = 1; // (note: may want to extend this in the future?)
575 
576  fType = EFType::kCompositionFcn;
577  fComposition = std::unique_ptr<TF1AbsComposition>(conv);
578 
579  fParams = std::unique_ptr<TF1Parameters>(new TF1Parameters(fNpar)); // default to zeros (TF1Convolution has no GetParameters())
580  // set parameter names
581  for (int i = 0; i < fNpar; i++)
582  this->SetParName(i, conv->GetParName(i));
583  // set parameters to default values
584  int f1Npar = function1->GetNpar();
585  int f2Npar = function2->GetNpar();
586  // first, copy parameters from function1
587  for (int i = 0; i < f1Npar; i++)
588  this->SetParameter(i, function1->GetParameter(i));
589  // then, check if the "Constant" parameters were combined
590  // (this code assumes function2 has at most one parameter named "Constant")
591  if (conv->GetNpar() == f1Npar + f2Npar - 1) {
592  int cst1 = function1->GetParNumber("Constant");
593  int cst2 = function2->GetParNumber("Constant");
594  this->SetParameter(cst1, function1->GetParameter(cst1) * function2->GetParameter(cst2));
595  // and copy parameters from function2
596  for (int i = 0; i < f2Npar; i++)
597  if (i < cst2)
598  this->SetParameter(f1Npar + i, function2->GetParameter(i));
599  else if (i > cst2)
600  this->SetParameter(f1Npar + i - 1, function2->GetParameter(i));
601  } else {
602  // or if no constant, simply copy parameters from function2
603  for (int i = 0; i < f2Npar; i++)
604  this->SetParameter(i + f1Npar, function2->GetParameter(i));
605  }
606 
607  // Then check if we need NSUM syntax:
608  } else if (TString(formula, 5) == "NSUM(" && formula[strlen(formula) - 1] == ')') {
609  // using comma as delimiter
610  char delimiter = ',';
611  // first, remove "NSUM(" and ")" and spaces
612  TString formDense = TString(formula)(5,strlen(formula)-5-1);
613  formDense.ReplaceAll(' ', "");
614 
615  // make sure standard functions are defined (e.g. gaus, expo)
617 
618  // Go char-by-char to split terms and define the relevant functions
619  int parenCount = 0;
620  int termStart = 0;
621  TObjArray *newFuncs = new TObjArray();
622  newFuncs->SetOwner(kTRUE);
623  TObjArray *coeffNames = new TObjArray();
624  coeffNames->SetOwner(kTRUE);
625  TString fullFormula("");
626  for (int i = 0; i < formDense.Length(); ++i) {
627  if (formDense[i] == '(')
628  parenCount++;
629  else if (formDense[i] == ')')
630  parenCount--;
631  else if (formDense[i] == delimiter && parenCount == 0) {
632  // term goes from termStart to i
633  DefineNSUMTerm(newFuncs, coeffNames, fullFormula, formDense, termStart, i, xmin, xmax);
634  termStart = i + 1;
635  }
636  }
637  DefineNSUMTerm(newFuncs, coeffNames, fullFormula, formDense, termStart, formDense.Length(), xmin, xmax);
638 
639  TF1NormSum *normSum = new TF1NormSum(fullFormula, xmin, xmax);
640 
641  if (xmin == 0 && xmax == 1.) Info("TF1","Created TF1NormSum object using the default [0,1] range");
642 
643  fNpar = normSum->GetNpar();
644  fNdim = 1; // (note: may want to extend functionality in the future)
645 
646  fType = EFType::kCompositionFcn;
647  fComposition = std::unique_ptr<TF1AbsComposition>(normSum);
648 
649  fParams = std::unique_ptr<TF1Parameters>(new TF1Parameters(fNpar));
650  fParams->SetParameters(&(normSum->GetParameters())[0]); // inherit default parameters from normSum
651 
652  // Parameter names
653  for (int i = 0; i < fNpar; i++) {
654  if (coeffNames->At(i) != nullptr) {
655  TString coeffName = ((TObjString *)coeffNames->At(i))->GetString();
656  this->SetParName(i, (const char *)coeffName);
657  } else {
658  this->SetParName(i, normSum->GetParName(i));
659  }
660  }
661 
662  } else { // regular TFormula
663  fFormula = std::unique_ptr<TFormula>(new TFormula(name, formula, false, vectorize));
664  fNpar = fFormula->GetNpar();
665  // TFormula can have dimension zero, but since this is a TF1 minimal dim is 1
666  fNdim = fFormula->GetNdim() == 0 ? 1 : fFormula->GetNdim();
667  }
668  if (fNpar) {
669  fParErrors.resize(fNpar);
670  fParMin.resize(fNpar);
671  fParMax.resize(fNpar);
672  }
673  // do we want really to have this un-documented feature where we accept cases where dim > 1
674  // by setting xmin >= xmax ??
675  if (fNdim > 1 && xmin < xmax) {
676  Error("TF1", "function: %s/%s has dimension %d instead of 1", name, formula, fNdim);
677  MakeZombie();
678  }
679 
680  DoInitialize(addToGlobList);
681 }
683  if (opt == nullptr) return TF1::EAddToList::kDefault;
684  TString option(opt);
685  option.ToUpper();
686  if (option.Contains("NL")) return TF1::EAddToList::kNo;
687  if (option.Contains("GL")) return TF1::EAddToList::kAdd;
689 }
691  if (opt == nullptr) return false;
692  TString option(opt);
693  option.ToUpper();
694  if (option.Contains("VEC")) return true;
695  return false;
696 }
697 TF1::TF1(const char *name, const char *formula, Double_t xmin, Double_t xmax, Option_t * opt) :
698 ////////////////////////////////////////////////////////////////////////////////
699 /// Same constructor as above (for TFormula based function) but passing an option strings
700 /// available options
701 /// VEC - vectorize the formula expressions (not possible for lambda based expressions)
702 /// NL - function is not stores in the global list of functions
703 /// GL - function will be always stored in the global list of functions ,
704 /// independently of the global setting of TF1::DefaultAddToGlobalList
705 ///////////////////////////////////////////////////////////////////////////////////
706  TF1(name, formula, xmin, xmax, GetGlobalListOption(opt), GetVectorizedOption(opt) )
707 {}
708 ////////////////////////////////////////////////////////////////////////////////
709 /// F1 constructor using name of an interpreted function.
710 ///
711 /// Creates a function of type C between xmin and xmax.
712 /// name is the name of an interpreted C++ function.
713 /// The function is defined with npar parameters
714 /// fcn must be a function of type:
715 ///
716 /// Double_t fcn(Double_t *x, Double_t *params)
717 ///
718 /// This constructor is called for functions of type C by the C++ interpreter.
719 ///
720 /// WARNING! A function created with this constructor cannot be Cloned.
721 
722 TF1::TF1(const char *name, Double_t xmin, Double_t xmax, Int_t npar, Int_t ndim, EAddToList addToGlobList) :
723  TF1(EFType::kInterpreted, name, xmin, xmax, npar, ndim, addToGlobList, new TF1Parameters(npar))
724 {
725  if (fName.Data()[0] == '*') { // case TF1 name starts with a *
726  Info("TF1", "TF1 has a name starting with a \'*\' - it is for saved TF1 objects in a .C file");
727  return; //case happens via SavePrimitive
728  } else if (fName.IsNull()) {
729  Error("TF1", "requires a proper function name!");
730  return;
731  }
732 
733  fMethodCall = std::unique_ptr<TMethodCall>(new TMethodCall());
734  fMethodCall->InitWithPrototype(fName, "Double_t*,Double_t*");
735 
736  if (! fMethodCall->IsValid()) {
737  Error("TF1", "No function found with the signature %s(Double_t*,Double_t*)", name);
738  return;
739  }
740 }
741 
742 
743 ////////////////////////////////////////////////////////////////////////////////
744 /// Constructor using a pointer to a real function.
745 ///
746 /// \param npar is the number of free parameters used by the function
747 ///
748 /// This constructor creates a function of type C when invoked
749 /// with the normal C++ compiler.
750 ///
751 /// see test program test/stress.cxx (function stress1) for an example.
752 /// note the interface with an intermediate pointer.
753 ///
754 /// WARNING! A function created with this constructor cannot be Cloned.
755 
756 TF1::TF1(const char *name, Double_t (*fcn)(Double_t *, Double_t *), Double_t xmin, Double_t xmax, Int_t npar, Int_t ndim, EAddToList addToGlobList) :
757  TF1(EFType::kPtrScalarFreeFcn, name, xmin, xmax, npar, ndim, addToGlobList, new TF1Parameters(npar), new TF1FunctorPointerImpl<double>(ROOT::Math::ParamFunctor(fcn)))
758 {}
759 
760 ////////////////////////////////////////////////////////////////////////////////
761 /// Constructor using a pointer to real function.
762 ///
763 /// \param npar is the number of free parameters used by the function
764 ///
765 /// This constructor creates a function of type C when invoked
766 /// with the normal C++ compiler.
767 ///
768 /// see test program test/stress.cxx (function stress1) for an example.
769 /// note the interface with an intermediate pointer.
770 ///
771 /// WARNING! A function created with this constructor cannot be Cloned.
772 
773 TF1::TF1(const char *name, Double_t (*fcn)(const Double_t *, const Double_t *), Double_t xmin, Double_t xmax, Int_t npar, Int_t ndim, EAddToList addToGlobList) :
774  TF1(EFType::kPtrScalarFreeFcn, name, xmin, xmax, npar, ndim, addToGlobList, new TF1Parameters(npar), new TF1FunctorPointerImpl<double>(ROOT::Math::ParamFunctor(fcn)))
775 {}
776 
777 ////////////////////////////////////////////////////////////////////////////////
778 /// Constructor using the Functor class.
779 ///
780 /// \param xmin and
781 /// \param xmax define the plotting range of the function
782 /// \param npar is the number of free parameters used by the function
783 ///
784 /// This constructor can be used only in compiled code
785 ///
786 /// WARNING! A function created with this constructor cannot be Cloned.
787 
788 TF1::TF1(const char *name, ROOT::Math::ParamFunctor f, Double_t xmin, Double_t xmax, Int_t npar, Int_t ndim, EAddToList addToGlobList) :
789  TF1(EFType::kPtrScalarFreeFcn, name, xmin, xmax, npar, ndim, addToGlobList, new TF1Parameters(npar), new TF1FunctorPointerImpl<double>(ROOT::Math::ParamFunctor(f)))
790 {}
791 
792 ////////////////////////////////////////////////////////////////////////////////
793 /// Common initialization of the TF1. Add to the global list and
794 /// set the default style
795 
796 void TF1::DoInitialize(EAddToList addToGlobalList)
797 {
798  // add to global list of functions if default adding is on OR if bit is set
799  bool doAdd = ((addToGlobalList == EAddToList::kDefault && fgAddToGlobList)
800  || addToGlobalList == EAddToList::kAdd);
801  if (doAdd && gROOT) {
804  // Store formula in linked list of formula in ROOT
805  TF1 *f1old = (TF1 *)gROOT->GetListOfFunctions()->FindObject(fName);
806  if (f1old) {
807  gROOT->GetListOfFunctions()->Remove(f1old);
808  // We removed f1old from the list, it is not longer global.
809  // (See TF1::AddToGlobalList which requires this flag to be correct).
810  f1old->SetBit(kNotGlobal, kTRUE);
811  }
812  gROOT->GetListOfFunctions()->Add(this);
813  } else
815 
816  if (gStyle) {
820  }
821  SetFillStyle(0);
822 }
823 
824 ////////////////////////////////////////////////////////////////////////////////
825 /// Static method to add/avoid to add automatically functions to the global list (gROOT->GetListOfFunctions() )
826 /// After having called this static method, all the functions created afterwards will follow the
827 /// desired behaviour.
828 ///
829 /// By default the functions are added automatically
830 /// It returns the previous status (true if the functions are added automatically)
831 
833 {
834  return fgAddToGlobList.exchange(on);
835 }
836 
837 ////////////////////////////////////////////////////////////////////////////////
838 /// Add to global list of functions (gROOT->GetListOfFunctions() )
839 /// return previous status (true if the function was already in the list false if not)
840 
842 {
843  if (!gROOT) return false;
844 
845  bool prevStatus = !TestBit(kNotGlobal);
846  if (on) {
847  if (prevStatus) {
849  assert(gROOT->GetListOfFunctions()->FindObject(this) != nullptr);
850  return on; // do nothing
851  }
852  // do I need to delete previous one with the same name ???
853  //TF1 * old = dynamic_cast<TF1*>( gROOT->GetListOfFunctions()->FindObject(GetName()) );
854  //if (old) { gROOT->GetListOfFunctions()->Remove(old); old->SetBit(kNotGlobal, kTRUE); }
856  gROOT->GetListOfFunctions()->Add(this);
858  } else if (prevStatus) {
859  // if previous status was on and now is off we need to remove the function
862  TF1 *old = dynamic_cast<TF1 *>(gROOT->GetListOfFunctions()->FindObject(GetName()));
863  if (!old) {
864  Warning("AddToGlobalList", "Function is supposed to be in the global list but it is not present");
865  return kFALSE;
866  }
867  gROOT->GetListOfFunctions()->Remove(this);
868  }
869  return prevStatus;
870 }
871 
872 ////////////////////////////////////////////////////////////////////////////////
873 /// Helper functions for NSUM parsing
874 
875 // Defines the formula that a given term uses, if not already defined,
876 // and appends "sanitized" formula to `fullFormula` string
877 void TF1::DefineNSUMTerm(TObjArray *newFuncs, TObjArray *coeffNames, TString &fullFormula, TString &formula,
878  int termStart, int termEnd, Double_t xmin, Double_t xmax)
879 {
880  TString originalTerm = formula(termStart, termEnd-termStart);
881  int coeffLength = TermCoeffLength(originalTerm);
882  if (coeffLength != -1)
883  termStart += coeffLength + 1;
884 
885  // `originalFunc` is the real formula and `cleanedFunc` is the
886  // sanitized version that will not confuse the TF1NormSum
887  // constructor
888  TString originalFunc = formula(termStart, termEnd-termStart);
889  TString cleanedFunc = TString(formula(termStart, termEnd-termStart))
890  .ReplaceAll('+', "<plus>")
891  .ReplaceAll('*',"<times>");
892 
893  // define function (if necessary)
894  if (!gROOT->GetListOfFunctions()->FindObject(cleanedFunc))
895  newFuncs->Add(new TF1(cleanedFunc, originalFunc, xmin, xmax));
896 
897  // append sanitized term to `fullFormula`
898  if (fullFormula.Length() != 0)
899  fullFormula.Append('+');
900 
901  // include numerical coefficient
902  if (coeffLength != -1 && originalTerm[0] != '[')
903  fullFormula.Append(originalTerm(0, coeffLength+1));
904 
905  // add coefficient name
906  if (coeffLength != -1 && originalTerm[0] == '[')
907  coeffNames->Add(new TObjString(TString(originalTerm(1,coeffLength-2))));
908  else
909  coeffNames->Add(nullptr);
910 
911  fullFormula.Append(cleanedFunc);
912 }
913 
914 
915 // Returns length of coeff at beginning of a given term, not counting the '*'
916 // Returns -1 if no coeff found
917 // Coeff can be either a number or parameter name
919  int firstAsterisk = term.First('*');
920  if (firstAsterisk == -1) // no asterisk found
921  return -1;
922 
923  if (TString(term(0,firstAsterisk)).IsFloat())
924  return firstAsterisk;
925 
926  if (term[0] == '[' && term[firstAsterisk-1] == ']'
927  && TString(term(1,firstAsterisk-2)).IsAlnum())
928  return firstAsterisk;
929 
930  return -1;
931 }
932 
933 ////////////////////////////////////////////////////////////////////////////////
934 /// Operator =
935 
936 TF1 &TF1::operator=(const TF1 &rhs)
937 {
938  if (this != &rhs) {
939  rhs.Copy(*this);
940  }
941  return *this;
942 }
943 
944 
945 ////////////////////////////////////////////////////////////////////////////////
946 /// TF1 default destructor.
947 
949 {
950  if (fHistogram) delete fHistogram;
951 
952  // this was before in TFormula destructor
953  {
955  if (gROOT) gROOT->GetListOfFunctions()->Remove(this);
956  }
957 
958  if (fParent) fParent->RecursiveRemove(this);
959 
960 }
961 
962 
963 ////////////////////////////////////////////////////////////////////////////////
964 
965 TF1::TF1(const TF1 &f1) :
967  fXmin(0), fXmax(0), fNpar(0), fNdim(0), fType(EFType::kFormula)
968 {
969  ((TF1 &)f1).Copy(*this);
970 }
971 
972 
973 ////////////////////////////////////////////////////////////////////////////////
974 /// Static function: set the fgAbsValue flag.
975 /// By default TF1::Integral uses the original function value to compute the integral
976 /// However, TF1::Moment, CentralMoment require to compute the integral
977 /// using the absolute value of the function.
978 
980 {
981  fgAbsValue = flag;
982 }
983 
984 
985 ////////////////////////////////////////////////////////////////////////////////
986 /// Browse.
987 
989 {
990  Draw(b ? b->GetDrawOption() : "");
991  gPad->Update();
992 }
993 
994 
995 ////////////////////////////////////////////////////////////////////////////////
996 /// Copy this F1 to a new F1.
997 /// Note that the cached integral with its related arrays are not copied
998 /// (they are also set as transient data members)
999 
1000 void TF1::Copy(TObject &obj) const
1001 {
1002  delete((TF1 &)obj).fHistogram;
1003 
1004  TNamed::Copy((TF1 &)obj);
1005  TAttLine::Copy((TF1 &)obj);
1006  TAttFill::Copy((TF1 &)obj);
1007  TAttMarker::Copy((TF1 &)obj);
1008  ((TF1 &)obj).fXmin = fXmin;
1009  ((TF1 &)obj).fXmax = fXmax;
1010  ((TF1 &)obj).fNpx = fNpx;
1011  ((TF1 &)obj).fNpar = fNpar;
1012  ((TF1 &)obj).fNdim = fNdim;
1013  ((TF1 &)obj).fType = fType;
1014  ((TF1 &)obj).fChisquare = fChisquare;
1015  ((TF1 &)obj).fNpfits = fNpfits;
1016  ((TF1 &)obj).fNDF = fNDF;
1017  ((TF1 &)obj).fMinimum = fMinimum;
1018  ((TF1 &)obj).fMaximum = fMaximum;
1019 
1020  ((TF1 &)obj).fParErrors = fParErrors;
1021  ((TF1 &)obj).fParMin = fParMin;
1022  ((TF1 &)obj).fParMax = fParMax;
1023  ((TF1 &)obj).fParent = fParent;
1024  ((TF1 &)obj).fSave = fSave;
1025  ((TF1 &)obj).fHistogram = 0;
1026  ((TF1 &)obj).fMethodCall = 0;
1027  ((TF1 &)obj).fNormalized = fNormalized;
1028  ((TF1 &)obj).fNormIntegral = fNormIntegral;
1029  ((TF1 &)obj).fFormula = 0;
1030 
1031  if (fFormula) assert(fFormula->GetNpar() == fNpar);
1032 
1033  // use copy-constructor of TMethodCall
1034  TMethodCall *m = (fMethodCall) ? new TMethodCall(*fMethodCall) : nullptr;
1035  ((TF1 &)obj).fMethodCall.reset(m);
1036 
1037  TFormula *formulaToCopy = (fFormula) ? new TFormula(*fFormula) : nullptr;
1038  ((TF1 &)obj).fFormula.reset(formulaToCopy);
1039 
1040  TF1Parameters *paramsToCopy = (fParams) ? new TF1Parameters(*fParams) : nullptr;
1041  ((TF1 &)obj).fParams.reset(paramsToCopy);
1042 
1043  TF1FunctorPointer *functorToCopy = (fFunctor) ? fFunctor->Clone() : nullptr;
1044  ((TF1 &)obj).fFunctor.reset(functorToCopy);
1045 
1046  TF1AbsComposition *comp = nullptr;
1047  if (fComposition) {
1048  comp = (TF1AbsComposition *)fComposition->IsA()->New();
1049  fComposition->Copy(*comp);
1050  }
1051  ((TF1 &)obj).fComposition.reset(comp);
1052 }
1053 
1054 
1055 ////////////////////////////////////////////////////////////////////////////////
1056 /// Make a complete copy of the underlying object. If 'newname' is set,
1057 /// the copy's name will be set to that name.
1058 
1059 TObject* TF1::Clone(const char* newname) const
1060 {
1061 
1062  TF1* obj = (TF1*) TNamed::Clone(newname);
1063 
1064  if (fHistogram) {
1065  obj->fHistogram = (TH1*)fHistogram->Clone();
1066  obj->fHistogram->SetDirectory(0);
1067  }
1068 
1069  return obj;
1070 }
1071 
1072 
1073 ////////////////////////////////////////////////////////////////////////////////
1074 /// Returns the first derivative of the function at point x,
1075 /// computed by Richardson's extrapolation method (use 2 derivative estimates
1076 /// to compute a third, more accurate estimation)
1077 /// first, derivatives with steps h and h/2 are computed by central difference formulas
1078 /// \f[
1079 /// D(h) = \frac{f(x+h) - f(x-h)}{2h}
1080 /// \f]
1081 /// the final estimate
1082 /// \f[
1083 /// D = \frac{4D(h/2) - D(h)}{3}
1084 /// \f]
1085 /// "Numerical Methods for Scientists and Engineers", H.M.Antia, 2nd edition"
1086 ///
1087 /// if the argument params is null, the current function parameters are used,
1088 /// otherwise the parameters in params are used.
1089 ///
1090 /// the argument eps may be specified to control the step size (precision).
1091 /// the step size is taken as eps*(xmax-xmin).
1092 /// the default value (0.001) should be good enough for the vast majority
1093 /// of functions. Give a smaller value if your function has many changes
1094 /// of the second derivative in the function range.
1095 ///
1096 /// Getting the error via TF1::DerivativeError:
1097 /// (total error = roundoff error + interpolation error)
1098 /// the estimate of the roundoff error is taken as follows:
1099 /// \f[
1100 /// err = k\sqrt{f(x)^{2} + x^{2}deriv^{2}}\sqrt{\sum ai^{2}},
1101 /// \f]
1102 /// where k is the double precision, ai are coefficients used in
1103 /// central difference formulas
1104 /// interpolation error is decreased by making the step size h smaller.
1105 ///
1106 /// \author Anna Kreshuk
1107 
1109 {
1110  if (GetNdim() > 1) {
1111  Warning("Derivative", "Function dimension is larger than one");
1112  }
1113 
1115  double xmin, xmax;
1116  GetRange(xmin, xmax);
1117  // this is not optimal (should be used the average x instead of the range)
1118  double h = eps * std::abs(xmax - xmin);
1119  if (h <= 0) h = 0.001;
1120  double der = 0;
1121  if (params) {
1122  ROOT::Math::WrappedTF1 wtf(*(const_cast<TF1 *>(this)));
1123  wtf.SetParameters(params);
1124  der = rd.Derivative1(wtf, x, h);
1125  } else {
1126  // no need to set parameters used a non-parametric wrapper to avoid allocating
1127  // an array with parameter values
1129  der = rd.Derivative1(wf, x, h);
1130  }
1131 
1132  gErrorTF1 = rd.Error();
1133  return der;
1134 
1135 }
1136 
1137 
1138 ////////////////////////////////////////////////////////////////////////////////
1139 /// Returns the second derivative of the function at point x,
1140 /// computed by Richardson's extrapolation method (use 2 derivative estimates
1141 /// to compute a third, more accurate estimation)
1142 /// first, derivatives with steps h and h/2 are computed by central difference formulas
1143 /// \f[
1144 /// D(h) = \frac{f(x+h) - 2f(x) + f(x-h)}{h^{2}}
1145 /// \f]
1146 /// the final estimate
1147 /// \f[
1148 /// D = \frac{4D(h/2) - D(h)}{3}
1149 /// \f]
1150 /// "Numerical Methods for Scientists and Engineers", H.M.Antia, 2nd edition"
1151 ///
1152 /// if the argument params is null, the current function parameters are used,
1153 /// otherwise the parameters in params are used.
1154 ///
1155 /// the argument eps may be specified to control the step size (precision).
1156 /// the step size is taken as eps*(xmax-xmin).
1157 /// the default value (0.001) should be good enough for the vast majority
1158 /// of functions. Give a smaller value if your function has many changes
1159 /// of the second derivative in the function range.
1160 ///
1161 /// Getting the error via TF1::DerivativeError:
1162 /// (total error = roundoff error + interpolation error)
1163 /// the estimate of the roundoff error is taken as follows:
1164 /// \f[
1165 /// err = k\sqrt{f(x)^{2} + x^{2}deriv^{2}}\sqrt{\sum ai^{2}},
1166 /// \f]
1167 /// where k is the double precision, ai are coefficients used in
1168 /// central difference formulas
1169 /// interpolation error is decreased by making the step size h smaller.
1170 ///
1171 /// \author Anna Kreshuk
1172 
1174 {
1175  if (GetNdim() > 1) {
1176  Warning("Derivative2", "Function dimension is larger than one");
1177  }
1178 
1180  double xmin, xmax;
1181  GetRange(xmin, xmax);
1182  // this is not optimal (should be used the average x instead of the range)
1183  double h = eps * std::abs(xmax - xmin);
1184  if (h <= 0) h = 0.001;
1185  double der = 0;
1186  if (params) {
1187  ROOT::Math::WrappedTF1 wtf(*(const_cast<TF1 *>(this)));
1188  wtf.SetParameters(params);
1189  der = rd.Derivative2(wtf, x, h);
1190  } else {
1191  // no need to set parameters used a non-parametric wrapper to avoid allocating
1192  // an array with parameter values
1194  der = rd.Derivative2(wf, x, h);
1195  }
1196 
1197  gErrorTF1 = rd.Error();
1198 
1199  return der;
1200 }
1201 
1202 
1203 ////////////////////////////////////////////////////////////////////////////////
1204 /// Returns the third derivative of the function at point x,
1205 /// computed by Richardson's extrapolation method (use 2 derivative estimates
1206 /// to compute a third, more accurate estimation)
1207 /// first, derivatives with steps h and h/2 are computed by central difference formulas
1208 /// \f[
1209 /// D(h) = \frac{f(x+2h) - 2f(x+h) + 2f(x-h) - f(x-2h)}{2h^{3}}
1210 /// \f]
1211 /// the final estimate
1212 /// \f[
1213 /// D = \frac{4D(h/2) - D(h)}{3}
1214 /// \f]
1215 /// "Numerical Methods for Scientists and Engineers", H.M.Antia, 2nd edition"
1216 ///
1217 /// if the argument params is null, the current function parameters are used,
1218 /// otherwise the parameters in params are used.
1219 ///
1220 /// the argument eps may be specified to control the step size (precision).
1221 /// the step size is taken as eps*(xmax-xmin).
1222 /// the default value (0.001) should be good enough for the vast majority
1223 /// of functions. Give a smaller value if your function has many changes
1224 /// of the second derivative in the function range.
1225 ///
1226 /// Getting the error via TF1::DerivativeError:
1227 /// (total error = roundoff error + interpolation error)
1228 /// the estimate of the roundoff error is taken as follows:
1229 /// \f[
1230 /// err = k\sqrt{f(x)^{2} + x^{2}deriv^{2}}\sqrt{\sum ai^{2}},
1231 /// \f]
1232 /// where k is the double precision, ai are coefficients used in
1233 /// central difference formulas
1234 /// interpolation error is decreased by making the step size h smaller.
1235 ///
1236 /// \author Anna Kreshuk
1237 
1239 {
1240  if (GetNdim() > 1) {
1241  Warning("Derivative3", "Function dimension is larger than one");
1242  }
1243 
1245  double xmin, xmax;
1246  GetRange(xmin, xmax);
1247  // this is not optimal (should be used the average x instead of the range)
1248  double h = eps * std::abs(xmax - xmin);
1249  if (h <= 0) h = 0.001;
1250  double der = 0;
1251  if (params) {
1252  ROOT::Math::WrappedTF1 wtf(*(const_cast<TF1 *>(this)));
1253  wtf.SetParameters(params);
1254  der = rd.Derivative3(wtf, x, h);
1255  } else {
1256  // no need to set parameters used a non-parametric wrapper to avoid allocating
1257  // an array with parameter values
1259  der = rd.Derivative3(wf, x, h);
1260  }
1261 
1262  gErrorTF1 = rd.Error();
1263  return der;
1264 
1265 }
1266 
1267 
1268 ////////////////////////////////////////////////////////////////////////////////
1269 /// Static function returning the error of the last call to the of Derivative's
1270 /// functions
1271 
1273 {
1274  return gErrorTF1;
1275 }
1276 
1277 
1278 ////////////////////////////////////////////////////////////////////////////////
1279 /// Compute distance from point px,py to a function.
1280 ///
1281 /// Compute the closest distance of approach from point px,py to this
1282 /// function. The distance is computed in pixels units.
1283 ///
1284 /// Note that px is called with a negative value when the TF1 is in
1285 /// TGraph or TH1 list of functions. In this case there is no point
1286 /// looking at the histogram axis.
1287 
1289 {
1290  if (!fHistogram) return 9999;
1291  Int_t distance = 9999;
1292  if (px >= 0) {
1293  distance = fHistogram->DistancetoPrimitive(px, py);
1294  if (distance <= 1) return distance;
1295  } else {
1296  px = -px;
1297  }
1298 
1299  Double_t xx[1];
1300  Double_t x = gPad->AbsPixeltoX(px);
1301  xx[0] = gPad->PadtoX(x);
1302  if (xx[0] < fXmin || xx[0] > fXmax) return distance;
1303  Double_t fval = Eval(xx[0]);
1304  Double_t y = gPad->YtoPad(fval);
1305  Int_t pybin = gPad->YtoAbsPixel(y);
1306  return TMath::Abs(py - pybin);
1307 }
1308 
1309 
1310 ////////////////////////////////////////////////////////////////////////////////
1311 /// Draw this function with its current attributes.
1312 ///
1313 /// Possible option values are:
1314 ///
1315 /// option | description
1316 /// -------|----------------------------------------
1317 /// "SAME" | superimpose on top of existing picture
1318 /// "L" | connect all computed points with a straight line
1319 /// "C" | connect all computed points with a smooth curve
1320 /// "FC" | draw a fill area below a smooth curve
1321 ///
1322 /// Note that the default value is "L". Therefore to draw on top
1323 /// of an existing picture, specify option "LSAME"
1324 ///
1325 /// NB. You must use DrawCopy if you want to draw several times the same
1326 /// function in the current canvas.
1327 
1328 void TF1::Draw(Option_t *option)
1329 {
1330  TString opt = option;
1331  opt.ToLower();
1332  if (gPad && !opt.Contains("same")) gPad->Clear();
1333 
1334  AppendPad(option);
1335 
1336  gPad->IncrementPaletteColor(1, opt);
1337 }
1338 
1339 
1340 ////////////////////////////////////////////////////////////////////////////////
1341 /// Draw a copy of this function with its current attributes.
1342 ///
1343 /// This function MUST be used instead of Draw when you want to draw
1344 /// the same function with different parameters settings in the same canvas.
1345 ///
1346 /// Possible option values are:
1347 ///
1348 /// option | description
1349 /// -------|----------------------------------------
1350 /// "SAME" | superimpose on top of existing picture
1351 /// "L" | connect all computed points with a straight line
1352 /// "C" | connect all computed points with a smooth curve
1353 /// "FC" | draw a fill area below a smooth curve
1354 ///
1355 /// Note that the default value is "L". Therefore to draw on top
1356 /// of an existing picture, specify option "LSAME"
1357 
1358 TF1 *TF1::DrawCopy(Option_t *option) const
1359 {
1360  TF1 *newf1 = (TF1 *)this->IsA()->New();
1361  Copy(*newf1);
1362  newf1->AppendPad(option);
1363  newf1->SetBit(kCanDelete);
1364  return newf1;
1365 }
1366 
1367 
1368 ////////////////////////////////////////////////////////////////////////////////
1369 /// Draw derivative of this function
1370 ///
1371 /// An intermediate TGraph object is built and drawn with option.
1372 /// The function returns a pointer to the TGraph object. Do:
1373 ///
1374 /// TGraph *g = (TGraph*)myfunc.DrawDerivative(option);
1375 ///
1376 /// The resulting graph will be drawn into the current pad.
1377 /// If this function is used via the context menu, it recommended
1378 /// to create a new canvas/pad before invoking this function.
1379 
1381 {
1382  TVirtualPad *pad = gROOT->GetSelectedPad();
1383  TVirtualPad *padsav = gPad;
1384  if (pad) pad->cd();
1385 
1386  TGraph *gr = new TGraph(this, "d");
1387  gr->Draw(option);
1388  if (padsav) padsav->cd();
1389  return gr;
1390 }
1391 
1392 
1393 ////////////////////////////////////////////////////////////////////////////////
1394 /// Draw integral of this function
1395 ///
1396 /// An intermediate TGraph object is built and drawn with option.
1397 /// The function returns a pointer to the TGraph object. Do:
1398 ///
1399 /// TGraph *g = (TGraph*)myfunc.DrawIntegral(option);
1400 ///
1401 /// The resulting graph will be drawn into the current pad.
1402 /// If this function is used via the context menu, it recommended
1403 /// to create a new canvas/pad before invoking this function.
1404 
1406 {
1407  TVirtualPad *pad = gROOT->GetSelectedPad();
1408  TVirtualPad *padsav = gPad;
1409  if (pad) pad->cd();
1410 
1411  TGraph *gr = new TGraph(this, "i");
1412  gr->Draw(option);
1413  if (padsav) padsav->cd();
1414  return gr;
1415 }
1416 
1417 
1418 ////////////////////////////////////////////////////////////////////////////////
1419 /// Draw function between xmin and xmax.
1420 
1422 {
1423 // //if(Compile(formula)) return ;
1424  SetRange(xmin, xmax);
1425 
1426  Draw(option);
1427 }
1428 
1429 
1430 ////////////////////////////////////////////////////////////////////////////////
1431 /// Evaluate this function.
1432 ///
1433 /// Computes the value of this function (general case for a 3-d function)
1434 /// at point x,y,z.
1435 /// For a 1-d function give y=0 and z=0
1436 /// The current value of variables x,y,z is passed through x, y and z.
1437 /// The parameters used will be the ones in the array params if params is given
1438 /// otherwise parameters will be taken from the stored data members fParams
1439 
1441 {
1442  if (fType == EFType::kFormula) return fFormula->Eval(x, y, z, t);
1443 
1444  Double_t xx[4] = {x, y, z, t};
1445  Double_t *pp = (Double_t *)fParams->GetParameters();
1446  // if (fType == EFType::kInterpreted)((TF1 *)this)->InitArgs(xx, pp);
1447  return ((TF1 *)this)->EvalPar(xx, pp);
1448 }
1449 
1450 
1451 ////////////////////////////////////////////////////////////////////////////////
1452 /// Evaluate function with given coordinates and parameters.
1453 ///
1454 /// Compute the value of this function at point defined by array x
1455 /// and current values of parameters in array params.
1456 /// If argument params is omitted or equal 0, the internal values
1457 /// of parameters (array fParams) will be used instead.
1458 /// For a 1-D function only x[0] must be given.
1459 /// In case of a multi-dimensional function, the arrays x must be
1460 /// filled with the corresponding number of dimensions.
1461 ///
1462 /// WARNING. In case of an interpreted function (fType=2), it is the
1463 /// user's responsibility to initialize the parameters via InitArgs
1464 /// before calling this function.
1465 /// InitArgs should be called at least once to specify the addresses
1466 /// of the arguments x and params.
1467 /// InitArgs should be called every time these addresses change.
1468 
1469 Double_t TF1::EvalPar(const Double_t *x, const Double_t *params)
1470 {
1471  //fgCurrent = this;
1472 
1473  if (fType == EFType::kFormula) {
1474  assert(fFormula);
1475 
1476  if (fNormalized && fNormIntegral != 0)
1477  return fFormula->EvalPar(x, params) / fNormIntegral;
1478  else
1479  return fFormula->EvalPar(x, params);
1480  }
1481  Double_t result = 0;
1482  if (fType == EFType::kPtrScalarFreeFcn || fType == EFType::kTemplScalar) {
1483  if (fFunctor) {
1484  assert(fParams);
1485  if (params) result = ((TF1FunctorPointerImpl<Double_t> *)fFunctor.get())->fImpl((Double_t *)x, (Double_t *)params);
1486  else result = ((TF1FunctorPointerImpl<Double_t> *)fFunctor.get())->fImpl((Double_t *)x, (Double_t *)fParams->GetParameters());
1487 
1488  } else result = GetSave(x);
1489 
1490  if (fNormalized && fNormIntegral != 0)
1491  result = result / fNormIntegral;
1492 
1493  return result;
1494  }
1495  if (fType == EFType::kInterpreted) {
1496  if (fMethodCall) fMethodCall->Execute(result);
1497  else result = GetSave(x);
1498 
1499  if (fNormalized && fNormIntegral != 0)
1500  result = result / fNormIntegral;
1501 
1502  return result;
1503  }
1504 
1505 #ifdef R__HAS_VECCORE
1506  if (fType == EFType::kTemplVec) {
1507  if (fFunctor) {
1508  if (params) result = EvalParVec(x, params);
1509  else result = EvalParVec(x, (Double_t *) fParams->GetParameters());
1510  }
1511  else {
1512  result = GetSave(x);
1513  }
1514 
1515  if (fNormalized && fNormIntegral != 0)
1516  result = result / fNormIntegral;
1517 
1518  return result;
1519  }
1520 #endif
1521 
1522  if (fType == EFType::kCompositionFcn) {
1523  if (!fComposition)
1524  Error("EvalPar", "Composition function not found");
1525 
1526  result = (*fComposition)(x, params);
1527  }
1528 
1529  return result;
1530 }
1531 
1532 ////////////////////////////////////////////////////////////////////////////////
1533 /// Execute action corresponding to one event.
1534 ///
1535 /// This member function is called when a F1 is clicked with the locator
1536 
1537 void TF1::ExecuteEvent(Int_t event, Int_t px, Int_t py)
1538 {
1539  if (!gPad) return;
1540 
1541  if (fHistogram) fHistogram->ExecuteEvent(event, px, py);
1542 
1543  if (!gPad->GetView()) {
1544  if (event == kMouseMotion) gPad->SetCursor(kHand);
1545  }
1546 }
1547 
1548 
1549 ////////////////////////////////////////////////////////////////////////////////
1550 /// Fix the value of a parameter
1551 /// The specified value will be used in a fit operation
1552 
1554 {
1555  if (ipar < 0 || ipar > GetNpar() - 1) return;
1556  SetParameter(ipar, value);
1557  if (value != 0) SetParLimits(ipar, value, value);
1558  else SetParLimits(ipar, 1, 1);
1559 }
1560 
1561 
1562 ////////////////////////////////////////////////////////////////////////////////
1563 /// Static function returning the current function being processed
1564 
1566 {
1567  ::Warning("TF1::GetCurrent", "This function is obsolete and is working only for the current painted functions");
1568  return fgCurrent;
1569 }
1570 
1571 
1572 ////////////////////////////////////////////////////////////////////////////////
1573 /// Return a pointer to the histogram used to visualise the function
1574 /// Note that this histogram is managed by the function and
1575 /// in same case it is automatically deleted when some TF1 functions are called
1576 /// such as TF1::SetParameters, TF1::SetNpx, TF1::SetRange
1577 /// It is then reccomended either to clone the return object or calling again teh GetHistogram
1578 /// function whenever is needed
1579 
1581 {
1582  if (fHistogram) return fHistogram;
1583 
1584  // histogram has not been yet created - create it
1585  // should not we make this function not const ??
1586  const_cast<TF1 *>(this)->fHistogram = const_cast<TF1 *>(this)->CreateHistogram();
1587  if (!fHistogram) Error("GetHistogram", "Error creating histogram for function %s of type %s", GetName(), IsA()->GetName());
1588  return fHistogram;
1589 }
1590 
1591 
1592 ////////////////////////////////////////////////////////////////////////////////
1593 /// Returns the maximum value of the function
1594 ///
1595 /// Method:
1596 /// First, the grid search is used to bracket the maximum
1597 /// with the step size = (xmax-xmin)/fNpx.
1598 /// This way, the step size can be controlled via the SetNpx() function.
1599 /// If the function is unimodal or if its extrema are far apart, setting
1600 /// the fNpx to a small value speeds the algorithm up many times.
1601 /// Then, Brent's method is applied on the bracketed interval
1602 /// epsilon (default = 1.E-10) controls the relative accuracy (if |x| > 1 )
1603 /// and absolute (if |x| < 1) and maxiter (default = 100) controls the maximum number
1604 /// of iteration of the Brent algorithm
1605 /// If the flag logx is set the grid search is done in log step size
1606 /// This is done automatically if the log scale is set in the current Pad
1607 ///
1608 /// NOTE: see also TF1::GetMaximumX and TF1::GetX
1609 
1611 {
1612  if (xmin >= xmax) {
1613  xmin = fXmin;
1614  xmax = fXmax;
1615  }
1616 
1617  if (!logx && gPad != 0) logx = gPad->GetLogx();
1618 
1620  GInverseFunc g(this);
1622  bm.SetFunction(wf1, xmin, xmax);
1623  bm.SetNpx(fNpx);
1624  bm.SetLogScan(logx);
1625  bm.Minimize(maxiter, epsilon, epsilon);
1626  Double_t x;
1627  x = - bm.FValMinimum();
1628 
1629  return x;
1630 }
1631 
1632 
1633 ////////////////////////////////////////////////////////////////////////////////
1634 /// Returns the X value corresponding to the maximum value of the function
1635 ///
1636 /// Method:
1637 /// First, the grid search is used to bracket the maximum
1638 /// with the step size = (xmax-xmin)/fNpx.
1639 /// This way, the step size can be controlled via the SetNpx() function.
1640 /// If the function is unimodal or if its extrema are far apart, setting
1641 /// the fNpx to a small value speeds the algorithm up many times.
1642 /// Then, Brent's method is applied on the bracketed interval
1643 /// epsilon (default = 1.E-10) controls the relative accuracy (if |x| > 1 )
1644 /// and absolute (if |x| < 1) and maxiter (default = 100) controls the maximum number
1645 /// of iteration of the Brent algorithm
1646 /// If the flag logx is set the grid search is done in log step size
1647 /// This is done automatically if the log scale is set in the current Pad
1648 ///
1649 /// NOTE: see also TF1::GetX
1650 
1652 {
1653  if (xmin >= xmax) {
1654  xmin = fXmin;
1655  xmax = fXmax;
1656  }
1657 
1658  if (!logx && gPad != 0) logx = gPad->GetLogx();
1659 
1661  GInverseFunc g(this);
1663  bm.SetFunction(wf1, xmin, xmax);
1664  bm.SetNpx(fNpx);
1665  bm.SetLogScan(logx);
1666  bm.Minimize(maxiter, epsilon, epsilon);
1667  Double_t x;
1668  x = bm.XMinimum();
1669 
1670  return x;
1671 }
1672 
1673 
1674 ////////////////////////////////////////////////////////////////////////////////
1675 /// Returns the minimum value of the function on the (xmin, xmax) interval
1676 ///
1677 /// Method:
1678 /// First, the grid search is used to bracket the maximum
1679 /// with the step size = (xmax-xmin)/fNpx. This way, the step size
1680 /// can be controlled via the SetNpx() function. If the function is
1681 /// unimodal or if its extrema are far apart, setting the fNpx to
1682 /// a small value speeds the algorithm up many times.
1683 /// Then, Brent's method is applied on the bracketed interval
1684 /// epsilon (default = 1.E-10) controls the relative accuracy (if |x| > 1 )
1685 /// and absolute (if |x| < 1) and maxiter (default = 100) controls the maximum number
1686 /// of iteration of the Brent algorithm
1687 /// If the flag logx is set the grid search is done in log step size
1688 /// This is done automatically if the log scale is set in the current Pad
1689 ///
1690 /// NOTE: see also TF1::GetMaximumX and TF1::GetX
1691 
1693 {
1694  if (xmin >= xmax) {
1695  xmin = fXmin;
1696  xmax = fXmax;
1697  }
1698 
1699  if (!logx && gPad != 0) logx = gPad->GetLogx();
1700 
1703  bm.SetFunction(wf1, xmin, xmax);
1704  bm.SetNpx(fNpx);
1705  bm.SetLogScan(logx);
1706  bm.Minimize(maxiter, epsilon, epsilon);
1707  Double_t x;
1708  x = bm.FValMinimum();
1709 
1710  return x;
1711 }
1712 
1713 ////////////////////////////////////////////////////////////////////////////////
1714 /// Find the minimum of a function of whatever dimension.
1715 /// While GetMinimum works only for 1D function , GetMinimumNDim works for all dimensions
1716 /// since it uses the minimizer interface
1717 /// vector x at beginning will contained the initial point, on exit will contain the result
1718 
1719 Double_t TF1::GetMinMaxNDim(Double_t *x , bool findmax, Double_t epsilon, Int_t maxiter) const
1720 {
1721  R__ASSERT(x != 0);
1722 
1723  int ndim = GetNdim();
1724  if (ndim == 0) {
1725  Error("GetMinimumNDim", "Function of dimension 0 - return Eval(x)");
1726  return (const_cast<TF1 &>(*this))(x);
1727  }
1728 
1729  // create minimizer class
1730  const char *minimName = ROOT::Math::MinimizerOptions::DefaultMinimizerType().c_str();
1731  const char *minimAlgo = ROOT::Math::MinimizerOptions::DefaultMinimizerAlgo().c_str();
1732  ROOT::Math::Minimizer *min = ROOT::Math::Factory::CreateMinimizer(minimName, minimAlgo);
1733 
1734  if (min == 0) {
1735  Error("GetMinimumNDim", "Error creating minimizer %s", minimName);
1736  return 0;
1737  }
1738 
1739  // minimizer will be set using default values
1740  if (epsilon > 0) min->SetTolerance(epsilon);
1741  if (maxiter > 0) min->SetMaxFunctionCalls(maxiter);
1742 
1743  // create wrapper class from TF1 (cannot use Functor, t.b.i.)
1744  ROOT::Math::WrappedMultiFunction<TF1 &> objFunc(const_cast<TF1 &>(*this), ndim);
1745  // create -f(x) when searching for the maximum
1746  GInverseFuncNdim invFunc(const_cast<TF1 *>(this));
1747  ROOT::Math::WrappedMultiFunction<GInverseFuncNdim &> objFuncInv(invFunc, ndim);
1748  if (!findmax)
1749  min->SetFunction(objFunc);
1750  else
1751  min->SetFunction(objFuncInv);
1752 
1753  std::vector<double> rmin(ndim);
1754  std::vector<double> rmax(ndim);
1755  GetRange(&rmin[0], &rmax[0]);
1756  for (int i = 0; i < ndim; ++i) {
1757  const char *xname = 0;
1758  double stepSize = 0.1;
1759  // use range for step size or give some value depending on x if range is not defined
1760  if (rmax[i] > rmin[i])
1761  stepSize = (rmax[i] - rmin[i]) / 100;
1762  else if (std::abs(x[i]) > 1.)
1763  stepSize = 0.1 * x[i];
1764 
1765  // set variable names
1766  if (ndim <= 3) {
1767  if (i == 0) {
1768  xname = "x";
1769  } else if (i == 1) {
1770  xname = "y";
1771  } else {
1772  xname = "z";
1773  }
1774  } else {
1775  xname = TString::Format("x_%d", i);
1776  // arbitrary step sie (should be computed from range)
1777  }
1778 
1779  if (rmin[i] < rmax[i]) {
1780  //Info("GetMinMax","setting limits on %s - [ %f , %f ]",xname,rmin[i],rmax[i]);
1781  min->SetLimitedVariable(i, xname, x[i], stepSize, rmin[i], rmax[i]);
1782  } else {
1783  min->SetVariable(i, xname, x[i], stepSize);
1784  }
1785  }
1786 
1787  bool ret = min->Minimize();
1788  if (!ret) {
1789  Error("GetMinimumNDim", "Error minimizing function %s", GetName());
1790  }
1791  if (min->X()) std::copy(min->X(), min->X() + ndim, x);
1792  double fmin = min->MinValue();
1793  delete min;
1794  // need to revert sign in case looking for maximum
1795  return (findmax) ? -fmin : fmin;
1796 
1797 }
1798 
1799 
1800 ////////////////////////////////////////////////////////////////////////////////
1801 /// Returns the X value corresponding to the minimum value of the function
1802 /// on the (xmin, xmax) interval
1803 ///
1804 /// Method:
1805 /// First, the grid search is used to bracket the maximum
1806 /// with the step size = (xmax-xmin)/fNpx. This way, the step size
1807 /// can be controlled via the SetNpx() function. If the function is
1808 /// unimodal or if its extrema are far apart, setting the fNpx to
1809 /// a small value speeds the algorithm up many times.
1810 /// Then, Brent's method is applied on the bracketed interval
1811 /// epsilon (default = 1.E-10) controls the relative accuracy (if |x| > 1 )
1812 /// and absolute (if |x| < 1) and maxiter (default = 100) controls the maximum number
1813 /// of iteration of the Brent algorithm
1814 /// If the flag logx is set the grid search is done in log step size
1815 /// This is done automatically if the log scale is set in the current Pad
1816 ///
1817 /// NOTE: see also TF1::GetX
1818 
1820 {
1821  if (xmin >= xmax) {
1822  xmin = fXmin;
1823  xmax = fXmax;
1824  }
1825 
1828  bm.SetFunction(wf1, xmin, xmax);
1829  bm.SetNpx(fNpx);
1830  bm.SetLogScan(logx);
1831  bm.Minimize(maxiter, epsilon, epsilon);
1832  Double_t x;
1833  x = bm.XMinimum();
1834 
1835  return x;
1836 }
1837 
1838 
1839 ////////////////////////////////////////////////////////////////////////////////
1840 /// Returns the X value corresponding to the function value fy for (xmin<x<xmax).
1841 /// in other words it can find the roots of the function when fy=0 and successive calls
1842 /// by changing the next call to [xmin+eps,xmax] where xmin is the previous root.
1843 ///
1844 /// Method:
1845 /// First, the grid search is used to bracket the maximum
1846 /// with the step size = (xmax-xmin)/fNpx. This way, the step size
1847 /// can be controlled via the SetNpx() function. If the function is
1848 /// unimodal or if its extrema are far apart, setting the fNpx to
1849 /// a small value speeds the algorithm up many times.
1850 /// Then, Brent's method is applied on the bracketed interval
1851 /// epsilon (default = 1.E-10) controls the relative accuracy (if |x| > 1 )
1852 /// and absolute (if |x| < 1) and maxiter (default = 100) controls the maximum number
1853 /// of iteration of the Brent algorithm
1854 /// If the flag logx is set the grid search is done in log step size
1855 /// This is done automatically if the log scale is set in the current Pad
1856 ///
1857 /// NOTE: see also TF1::GetMaximumX, TF1::GetMinimumX
1858 
1860 {
1861  if (xmin >= xmax) {
1862  xmin = fXmin;
1863  xmax = fXmax;
1864  }
1865 
1866  if (!logx && gPad != 0) logx = gPad->GetLogx();
1867 
1868  GFunc g(this, fy);
1871  brf.SetFunction(wf1, xmin, xmax);
1872  brf.SetNpx(fNpx);
1873  brf.SetLogScan(logx);
1874  bool ret = brf.Solve(maxiter, epsilon, epsilon);
1875  if (!ret) Error("GetX","[%f,%f] is not a valid interval",xmin,xmax);
1876  return (ret) ? brf.Root() : TMath::QuietNaN();
1877 }
1878 
1879 ////////////////////////////////////////////////////////////////////////////////
1880 /// Return the number of degrees of freedom in the fit
1881 /// the fNDF parameter has been previously computed during a fit.
1882 /// The number of degrees of freedom corresponds to the number of points
1883 /// used in the fit minus the number of free parameters.
1884 
1886 {
1887  Int_t npar = GetNpar();
1888  if (fNDF == 0 && (fNpfits > npar)) return fNpfits - npar;
1889  return fNDF;
1890 }
1891 
1892 
1893 ////////////////////////////////////////////////////////////////////////////////
1894 /// Return the number of free parameters
1895 
1897 {
1898  Int_t ntot = GetNpar();
1899  Int_t nfree = ntot;
1900  Double_t al, bl;
1901  for (Int_t i = 0; i < ntot; i++) {
1902  ((TF1 *)this)->GetParLimits(i, al, bl);
1903  if (al * bl != 0 && al >= bl) nfree--;
1904  }
1905  return nfree;
1906 }
1907 
1908 
1909 ////////////////////////////////////////////////////////////////////////////////
1910 /// Redefines TObject::GetObjectInfo.
1911 /// Displays the function info (x, function value)
1912 /// corresponding to cursor position px,py
1913 
1914 char *TF1::GetObjectInfo(Int_t px, Int_t /* py */) const
1915 {
1916  static char info[64];
1917  Double_t x = gPad->PadtoX(gPad->AbsPixeltoX(px));
1918  snprintf(info, 64, "(x=%g, f=%g)", x, ((TF1 *)this)->Eval(x));
1919  return info;
1920 }
1921 
1922 
1923 ////////////////////////////////////////////////////////////////////////////////
1924 /// Return value of parameter number ipar
1925 
1927 {
1928  if (ipar < 0 || ipar > GetNpar() - 1) return 0;
1929  return fParErrors[ipar];
1930 }
1931 
1932 
1933 ////////////////////////////////////////////////////////////////////////////////
1934 /// Return limits for parameter ipar.
1935 
1936 void TF1::GetParLimits(Int_t ipar, Double_t &parmin, Double_t &parmax) const
1937 {
1938  parmin = 0;
1939  parmax = 0;
1940  int n = fParMin.size();
1941  assert(n == int(fParMax.size()) && n <= fNpar);
1942  if (ipar < 0 || ipar > n - 1) return;
1943  parmin = fParMin[ipar];
1944  parmax = fParMax[ipar];
1945 }
1946 
1947 
1948 ////////////////////////////////////////////////////////////////////////////////
1949 /// Return the fit probability
1950 
1952 {
1953  if (fNDF <= 0) return 0;
1954  return TMath::Prob(fChisquare, fNDF);
1955 }
1956 
1957 
1958 ////////////////////////////////////////////////////////////////////////////////
1959 /// Compute Quantiles for density distribution of this function
1960 ///
1961 /// Quantile x_q of a probability distribution Function F is defined as
1962 /// \f[
1963 /// F(x_{q}) = \int_{xmin}^{x_{q}} f dx = q with 0 <= q <= 1.
1964 /// \f]
1965 /// For instance the median \f$ x_{\frac{1}{2}} \f$ of a distribution is defined as that value
1966 /// of the random variable for which the distribution function equals 0.5:
1967 /// \f[
1968 /// F(x_{\frac{1}{2}}) = \prod(x < x_{\frac{1}{2}}) = \frac{1}{2}
1969 /// \f]
1970 ///
1971 /// \param[in] nprobSum maximum size of array q and size of array probSum
1972 /// \param[out] q array filled with nq quantiles
1973 /// \param[in] probSum array of positions where quantiles will be computed.
1974 /// It is assumed to contain at least nprobSum values.
1975 /// \return value nq (<=nprobSum) with the number of quantiles computed
1976 ///
1977 /// Getting quantiles from two histograms and storing results in a TGraph,
1978 /// a so-called QQ-plot
1979 ///
1980 /// TGraph *gr = new TGraph(nprob);
1981 /// f1->GetQuantiles(nprob,gr->GetX());
1982 /// f2->GetQuantiles(nprob,gr->GetY());
1983 /// gr->Draw("alp");
1984 ///
1985 /// \author Eddy Offermann
1986 
1987 
1988 Int_t TF1::GetQuantiles(Int_t nprobSum, Double_t *q, const Double_t *probSum)
1989 {
1990  // LM: change to use fNpx
1991  // should we change code to use a root finder ?
1992  // It should be more precise and more efficient
1993  const Int_t npx = TMath::Max(fNpx, 2 * nprobSum);
1994  const Double_t xMin = GetXmin();
1995  const Double_t xMax = GetXmax();
1996  const Double_t dx = (xMax - xMin) / npx;
1997 
1998  TArrayD integral(npx + 1);
1999  TArrayD alpha(npx);
2000  TArrayD beta(npx);
2001  TArrayD gamma(npx);
2002 
2003  integral[0] = 0;
2004  Int_t intNegative = 0;
2005  Int_t i;
2006  for (i = 0; i < npx; i++) {
2007  Double_t integ = Integral(Double_t(xMin + i * dx), Double_t(xMin + i * dx + dx), 0.0);
2008  if (integ < 0) {
2009  intNegative++;
2010  integ = -integ;
2011  }
2012  integral[i + 1] = integral[i] + integ;
2013  }
2014 
2015  if (intNegative > 0)
2016  Warning("GetQuantiles", "function:%s has %d negative values: abs assumed",
2017  GetName(), intNegative);
2018  if (integral[npx] == 0) {
2019  Error("GetQuantiles", "Integral of function is zero");
2020  return 0;
2021  }
2022 
2023  const Double_t total = integral[npx];
2024  for (i = 1; i <= npx; i++) integral[i] /= total;
2025  //the integral r for each bin is approximated by a parabola
2026  // x = alpha + beta*r +gamma*r**2
2027  // compute the coefficients alpha, beta, gamma for each bin
2028  for (i = 0; i < npx; i++) {
2029  const Double_t x0 = xMin + dx * i;
2030  const Double_t r2 = integral[i + 1] - integral[i];
2031  const Double_t r1 = Integral(x0, x0 + 0.5 * dx, 0.0) / total;
2032  gamma[i] = (2 * r2 - 4 * r1) / (dx * dx);
2033  beta[i] = r2 / dx - gamma[i] * dx;
2034  alpha[i] = x0;
2035  gamma[i] *= 2;
2036  }
2037 
2038  // Be careful because of finite precision in the integral; Use the fact that the integral
2039  // is monotone increasing
2040  for (i = 0; i < nprobSum; i++) {
2041  const Double_t r = probSum[i];
2042  Int_t bin = TMath::Max(TMath::BinarySearch(npx + 1, integral.GetArray(), r), (Long64_t)0);
2043  // in case the prob is 1
2044  if (bin == npx) {
2045  q[i] = xMax;
2046  continue;
2047  }
2048  // LM use a tolerance 1.E-12 (integral precision)
2049  while (bin < npx - 1 && TMath::AreEqualRel(integral[bin + 1], r, 1E-12)) {
2050  if (TMath::AreEqualRel(integral[bin + 2], r, 1E-12)) bin++;
2051  else break;
2052  }
2053 
2054  const Double_t rr = r - integral[bin];
2055  if (rr != 0.0) {
2056  Double_t xx = 0.0;
2057  const Double_t fac = -2.*gamma[bin] * rr / beta[bin] / beta[bin];
2058  if (fac != 0 && fac <= 1)
2059  xx = (-beta[bin] + TMath::Sqrt(beta[bin] * beta[bin] + 2 * gamma[bin] * rr)) / gamma[bin];
2060  else if (beta[bin] != 0.)
2061  xx = rr / beta[bin];
2062  q[i] = alpha[bin] + xx;
2063  } else {
2064  q[i] = alpha[bin];
2065  if (integral[bin + 1] == r) q[i] += dx;
2066  }
2067  }
2068 
2069  return nprobSum;
2070 }
2071 ////////////////////////////////////////////////////////////////////////////////
2072 ///
2073 /// Compute the cumulative function at fNpx points between fXmin and fXmax.
2074 /// Option can be used to force a log scale (option = "log"), linear (option = "lin") or automatic if empty.
2076 
2077  fIntegral.resize(fNpx + 1);
2078  fAlpha.resize(fNpx + 1);
2079  fBeta.resize(fNpx);
2080  fGamma.resize(fNpx);
2081  fIntegral[0] = 0;
2082  fAlpha[fNpx] = 0;
2083  Double_t integ;
2084  Int_t intNegative = 0;
2085  Int_t i;
2086  Bool_t logbin = kFALSE;
2087  Double_t dx;
2088  Double_t xmin = fXmin;
2089  Double_t xmax = fXmax;
2090  TString opt(option);
2091  opt.ToUpper();
2092  // perform a log binning if specified by user (option="Log") or if some conditions are met
2093  // and the user explicitly does not specify a Linear binning option
2094  if (opt.Contains("LOG") || ((xmin > 0 && xmax / xmin > fNpx) && !opt.Contains("LIN"))) {
2095  logbin = kTRUE;
2096  fAlpha[fNpx] = 1;
2097  xmin = TMath::Log10(fXmin);
2098  xmax = TMath::Log10(fXmax);
2099  if (gDebug)
2100  Info("GetRandom", "Use log scale for tabulating the integral in [%f,%f] with %d points", fXmin, fXmax, fNpx);
2101  }
2102  dx = (xmax - xmin) / fNpx;
2103 
2104  std::vector<Double_t> xx(fNpx + 1);
2105  for (i = 0; i < fNpx; i++) {
2106  xx[i] = xmin + i * dx;
2107  }
2108  xx[fNpx] = xmax;
2109  for (i = 0; i < fNpx; i++) {
2110  if (logbin) {
2111  integ = Integral(TMath::Power(10, xx[i]), TMath::Power(10, xx[i + 1]), 0.0);
2112  } else {
2113  integ = Integral(xx[i], xx[i + 1], 0.0);
2114  }
2115  if (integ < 0) {
2116  intNegative++;
2117  integ = -integ;
2118  }
2119  fIntegral[i + 1] = fIntegral[i] + integ;
2120  }
2121  if (intNegative > 0) {
2122  Warning("GetRandom", "function:%s has %d negative values: abs assumed", GetName(), intNegative);
2123  }
2124  if (fIntegral[fNpx] == 0) {
2125  Error("GetRandom", "Integral of function is zero");
2126  return kFALSE;
2127  }
2129  for (i = 1; i <= fNpx; i++) { // normalize integral to 1
2130  fIntegral[i] /= total;
2131  }
2132  // the integral r for each bin is approximated by a parabola
2133  // x = alpha + beta*r +gamma*r**2
2134  // compute the coefficients alpha, beta, gamma for each bin
2135  Double_t x0, r1, r2, r3;
2136  for (i = 0; i < fNpx; i++) {
2137  x0 = xx[i];
2138  r2 = fIntegral[i + 1] - fIntegral[i];
2139  if (logbin)
2140  r1 = Integral(TMath::Power(10, x0), TMath::Power(10, x0 + 0.5 * dx), 0.0) / total;
2141  else
2142  r1 = Integral(x0, x0 + 0.5 * dx, 0.0) / total;
2143  r3 = 2 * r2 - 4 * r1;
2144  if (TMath::Abs(r3) > 1e-8)
2145  fGamma[i] = r3 / (dx * dx);
2146  else
2147  fGamma[i] = 0;
2148  fBeta[i] = r2 / dx - fGamma[i] * dx;
2149  fAlpha[i] = x0;
2150  fGamma[i] *= 2;
2151  }
2152  return kTRUE;
2153 }
2154 
2155 ////////////////////////////////////////////////////////////////////////////////
2156 /// Return a random number following this function shape.
2157 ///
2158 /// @param rng Random number generator. By default (or when passing a nullptr) the global gRandom is used
2159 /// @param option Option string which controls the binning used to compute the integral. Default mode is automatic depending of
2160 /// xmax, xmin and Npx (function points).
2161 /// Possible values are:
2162 /// - "LOG" to force usage of log scale for tabulating the integral
2163 /// - "LIN" to force usage of linear scale when tabulating the integral
2164 ///
2165 /// The distribution contained in the function fname (TF1) is integrated
2166 /// over the channel contents.
2167 /// It is normalized to 1.
2168 /// For each bin the integral is approximated by a parabola.
2169 /// The parabola coefficients are stored as non persistent data members
2170 /// Getting one random number implies:
2171 /// - Generating a random number between 0 and 1 (say r1)
2172 /// - Look in which bin in the normalized integral r1 corresponds to
2173 /// - Evaluate the parabolic curve in the selected bin to find the corresponding X value.
2174 ///
2175 /// The user can provide as optional parameter a Random number generator.
2176 /// By default gRandom is used
2177 ///
2178 /// If the ratio fXmax/fXmin > fNpx the integral is tabulated in log scale in x
2179 /// A log scale for the intergral is also always used if a user specifies the "LOG" option
2180 /// Instead if a user requestes a "LIN" option the integral binning is never done in log scale
2181 /// whatever the fXmax/fXmin ratio is
2182 ///
2183 /// Note that the parabolic approximation is very good as soon as the number of bins is greater than 50.
2184 
2185 
2187 {
2188  // Check if integral array must be built
2189  if (fIntegral.size() == 0) {
2190  Bool_t ret = ComputeCdfTable(option);
2191  if (!ret) return TMath::QuietNaN();
2192  }
2193 
2194 
2195  // return random number
2196  Double_t r = (rng) ? rng->Rndm() : gRandom->Rndm();
2197  Int_t bin = TMath::BinarySearch(fNpx, fIntegral.data(), r);
2198  Double_t rr = r - fIntegral[bin];
2199 
2200  Double_t yy;
2201  if (fGamma[bin] != 0)
2202  yy = (-fBeta[bin] + TMath::Sqrt(fBeta[bin] * fBeta[bin] + 2 * fGamma[bin] * rr)) / fGamma[bin];
2203  else
2204  yy = rr / fBeta[bin];
2205  Double_t x = fAlpha[bin] + yy;
2206  if (fAlpha[fNpx] > 0) return TMath::Power(10, x);
2207  return x;
2208 }
2209 
2210 
2211 ////////////////////////////////////////////////////////////////////////////////
2212 /// Return a random number following this function shape in [xmin,xmax]
2213 ///
2214 /// The distribution contained in the function fname (TF1) is integrated
2215 /// over the channel contents.
2216 /// It is normalized to 1.
2217 /// For each bin the integral is approximated by a parabola.
2218 /// The parabola coefficients are stored as non persistent data members
2219 /// Getting one random number implies:
2220 /// - Generating a random number between 0 and 1 (say r1)
2221 /// - Look in which bin in the normalized integral r1 corresponds to
2222 /// - Evaluate the parabolic curve in the selected bin to find
2223 /// the corresponding X value.
2224 ///
2225 /// The parabolic approximation is very good as soon as the number
2226 /// of bins is greater than 50.
2227 ///
2228 /// @param xmin minimum value for generated random numbers
2229 /// @param xmax maximum value for generated random numbers
2230 /// @param rng (optional) random number generator pointer
2231 /// @param option (optional) : `LOG` or `LIN` to force the usage of a log or linear scale for computing the cumulative integral table
2232 ///
2233 /// IMPORTANT NOTE
2234 ///
2235 /// The integral of the function is computed at fNpx points. If the function
2236 /// has sharp peaks, you should increase the number of points (SetNpx)
2237 /// such that the peak is correctly tabulated at several points.
2238 
2240 {
2241  // Check if integral array must be built
2242  if (fIntegral.size() == 0) {
2243  Bool_t ret = ComputeCdfTable(option);
2244  if (!ret) return TMath::QuietNaN();
2245  }
2246 
2247  // return random number
2248  Double_t dx = (fXmax - fXmin) / fNpx;
2249  Int_t nbinmin = (Int_t)((xmin - fXmin) / dx);
2250  Int_t nbinmax = (Int_t)((xmax - fXmin) / dx) + 2;
2251  if (nbinmax > fNpx) nbinmax = fNpx;
2252 
2253  Double_t pmin = fIntegral[nbinmin];
2254  Double_t pmax = fIntegral[nbinmax];
2255 
2256  Double_t r, x, xx, rr;
2257  do {
2258  r = (rng) ? rng->Uniform(pmin, pmax) : gRandom->Uniform(pmin, pmax);
2259 
2260  Int_t bin = TMath::BinarySearch(fNpx, fIntegral.data(), r);
2261  rr = r - fIntegral[bin];
2262 
2263  if (fGamma[bin] != 0)
2264  xx = (-fBeta[bin] + TMath::Sqrt(fBeta[bin] * fBeta[bin] + 2 * fGamma[bin] * rr)) / fGamma[bin];
2265  else
2266  xx = rr / fBeta[bin];
2267  x = fAlpha[bin] + xx;
2268  } while (x < xmin || x > xmax);
2269  return x;
2270 }
2271 
2272 ////////////////////////////////////////////////////////////////////////////////
2273 /// Return range of a generic N-D function.
2274 
2275 void TF1::GetRange(Double_t *rmin, Double_t *rmax) const
2276 {
2277  int ndim = GetNdim();
2278 
2279  double xmin = 0, ymin = 0, zmin = 0, xmax = 0, ymax = 0, zmax = 0;
2280  GetRange(xmin, ymin, zmin, xmax, ymax, zmax);
2281  for (int i = 0; i < ndim; ++i) {
2282  if (i == 0) {
2283  rmin[0] = xmin;
2284  rmax[0] = xmax;
2285  } else if (i == 1) {
2286  rmin[1] = ymin;
2287  rmax[1] = ymax;
2288  } else if (i == 2) {
2289  rmin[2] = zmin;
2290  rmax[2] = zmax;
2291  } else {
2292  rmin[i] = 0;
2293  rmax[i] = 0;
2294  }
2295  }
2296 }
2297 
2298 
2299 ////////////////////////////////////////////////////////////////////////////////
2300 /// Return range of a 1-D function.
2301 
2303 {
2304  xmin = fXmin;
2305  xmax = fXmax;
2306 }
2307 
2308 
2309 ////////////////////////////////////////////////////////////////////////////////
2310 /// Return range of a 2-D function.
2311 
2313 {
2314  xmin = fXmin;
2315  xmax = fXmax;
2316  ymin = 0;
2317  ymax = 0;
2318 }
2319 
2320 
2321 ////////////////////////////////////////////////////////////////////////////////
2322 /// Return range of function.
2323 
2325 {
2326  xmin = fXmin;
2327  xmax = fXmax;
2328  ymin = 0;
2329  ymax = 0;
2330  zmin = 0;
2331  zmax = 0;
2332 }
2333 
2334 
2335 ////////////////////////////////////////////////////////////////////////////////
2336 /// Get value corresponding to X in array of fSave values
2337 
2339 {
2340  if (fSave.size() == 0) return 0;
2341  //if (fSave == 0) return 0;
2342  int fNsave = fSave.size();
2343  Double_t x = Double_t(xx[0]);
2344  Double_t y, dx, xmin, xmax, xlow, xup, ylow, yup;
2345  if (fParent && fParent->InheritsFrom(TH1::Class())) {
2346  //if parent is a histogram the function had been saved at the center of the bins
2347  //we make a linear interpolation between the saved values
2348  xmin = fSave[fNsave - 3];
2349  xmax = fSave[fNsave - 2];
2350  if (fSave[fNsave - 1] == xmax) {
2351  TH1 *h = (TH1 *)fParent;
2352  TAxis *xaxis = h->GetXaxis();
2353  Int_t bin1 = xaxis->FindBin(xmin);
2354  Int_t binup = xaxis->FindBin(xmax);
2355  Int_t bin = xaxis->FindBin(x);
2356  if (bin < binup) {
2357  xlow = xaxis->GetBinCenter(bin);
2358  xup = xaxis->GetBinCenter(bin + 1);
2359  ylow = fSave[bin - bin1];
2360  yup = fSave[bin - bin1 + 1];
2361  } else {
2362  xlow = xaxis->GetBinCenter(bin - 1);
2363  xup = xaxis->GetBinCenter(bin);
2364  ylow = fSave[bin - bin1 - 1];
2365  yup = fSave[bin - bin1];
2366  }
2367  dx = xup - xlow;
2368  y = ((xup * ylow - xlow * yup) + x * (yup - ylow)) / dx;
2369  return y;
2370  }
2371  }
2372  Int_t np = fNsave - 3;
2373  xmin = Double_t(fSave[np + 1]);
2374  xmax = Double_t(fSave[np + 2]);
2375  dx = (xmax - xmin) / np;
2376  if (x < xmin || x > xmax) return 0;
2377  // return a Nan in case of x=nan, otherwise will crash later
2378  if (TMath::IsNaN(x)) return x;
2379  if (dx <= 0) return 0;
2380 
2381  Int_t bin = Int_t((x - xmin) / dx);
2382  xlow = xmin + bin * dx;
2383  xup = xlow + dx;
2384  ylow = fSave[bin];
2385  yup = fSave[bin + 1];
2386  y = ((xup * ylow - xlow * yup) + x * (yup - ylow)) / dx;
2387  return y;
2388 }
2389 
2390 
2391 ////////////////////////////////////////////////////////////////////////////////
2392 /// Get x axis of the function.
2393 
2395 {
2396  TH1 *h = GetHistogram();
2397  if (!h) return 0;
2398  return h->GetXaxis();
2399 }
2400 
2401 
2402 ////////////////////////////////////////////////////////////////////////////////
2403 /// Get y axis of the function.
2404 
2406 {
2407  TH1 *h = GetHistogram();
2408  if (!h) return 0;
2409  return h->GetYaxis();
2410 }
2411 
2412 
2413 ////////////////////////////////////////////////////////////////////////////////
2414 /// Get z axis of the function. (In case this object is a TF2 or TF3)
2415 
2417 {
2418  TH1 *h = GetHistogram();
2419  if (!h) return 0;
2420  return h->GetZaxis();
2421 }
2422 
2423 
2424 
2425 ////////////////////////////////////////////////////////////////////////////////
2426 /// Compute the gradient (derivative) wrt a parameter ipar
2427 ///
2428 /// \param ipar index of parameter for which the derivative is computed
2429 /// \param x point, where the derivative is computed
2430 /// \param eps - if the errors of parameters have been computed, the step used in
2431 /// numerical differentiation is eps*parameter_error.
2432 ///
2433 /// if the errors have not been computed, step=eps is used
2434 /// default value of eps = 0.01
2435 /// Method is the same as in Derivative() function
2436 ///
2437 /// If a parameter is fixed, the gradient on this parameter = 0
2438 
2440 {
2441  return GradientParTempl<Double_t>(ipar, x, eps);
2442 }
2443 
2444 ////////////////////////////////////////////////////////////////////////////////
2445 /// Compute the gradient wrt parameters
2446 /// If the TF1 object is based on a formula expression (TFormula)
2447 /// and TFormula::GenerateGradientPar() has been successfully called
2448 /// automatic differentiation using CLAD is used instead of the default
2449 /// numerical differentiation
2450 ///
2451 /// \param x point, were the gradient is computed
2452 /// \param grad used to return the computed gradient, assumed to be of at least fNpar size
2453 /// \param eps if the errors of parameters have been computed, the step used in
2454 /// numerical differentiation is eps*parameter_error.
2455 ///
2456 /// if the errors have not been computed, step=eps is used
2457 /// default value of eps = 0.01
2458 /// Method is the same as in Derivative() function
2459 ///
2460 /// If a parameter is fixed, the gradient on this parameter = 0
2461 
2462 void TF1::GradientPar(const Double_t *x, Double_t *grad, Double_t eps)
2463 {
2464  if (fFormula && fFormula->HasGeneratedGradient())
2465  fFormula->GradientPar(x,grad);
2466  else
2467  GradientParTempl<Double_t>(x, grad, eps);
2468 }
2469 
2470 ////////////////////////////////////////////////////////////////////////////////
2471 /// Initialize parameters addresses.
2472 
2473 void TF1::InitArgs(const Double_t *x, const Double_t *params)
2474 {
2475  if (fMethodCall) {
2476  Longptr_t args[2];
2477  args[0] = (Longptr_t)x;
2478  if (params) args[1] = (Longptr_t)params;
2479  else args[1] = (Longptr_t)GetParameters();
2480  fMethodCall->SetParamPtrs(args);
2481  }
2482 }
2483 
2484 
2485 ////////////////////////////////////////////////////////////////////////////////
2486 /// Create the basic function objects
2487 
2489 {
2490  TF1 *f1;
2492  if (!gROOT->GetListOfFunctions()->FindObject("gaus")) {
2493  f1 = new TF1("gaus", "gaus", -1, 1);
2494  f1->SetParameters(1, 0, 1);
2495  f1 = new TF1("gausn", "gausn", -1, 1);
2496  f1->SetParameters(1, 0, 1);
2497  f1 = new TF1("landau", "landau", -1, 1);
2498  f1->SetParameters(1, 0, 1);
2499  f1 = new TF1("landaun", "landaun", -1, 1);
2500  f1->SetParameters(1, 0, 1);
2501  f1 = new TF1("expo", "expo", -1, 1);
2502  f1->SetParameters(1, 1);
2503  for (Int_t i = 0; i < 10; i++) {
2504  f1 = new TF1(Form("pol%d", i), Form("pol%d", i), -1, 1);
2505  f1->SetParameters(1, 1, 1, 1, 1, 1, 1, 1, 1, 1);
2506  // create also chebyshev polynomial
2507  // (note polynomial object will not be deleted)
2508  // note that these functions cannot be stored
2510  Double_t min = -1;
2511  Double_t max = 1;
2512  f1 = new TF1(TString::Format("chebyshev%d", i), pol, min, max, i + 1, 1);
2513  f1->SetParameters(1, 1, 1, 1, 1, 1, 1, 1, 1, 1);
2514  }
2515 
2516  }
2517 }
2518 ////////////////////////////////////////////////////////////////////////////////
2519 /// IntegralOneDim or analytical integral
2520 
2522 {
2523  Double_t error = 0;
2524  if (GetNumber() > 0) {
2525  Double_t result = 0.;
2526  if (gDebug) {
2527  Info("computing analytical integral for function %s with number %d", GetName(), GetNumber());
2528  }
2529  result = AnalyticalIntegral(this, a, b);
2530  // if it is a formula that havent been implemented in analytical integral a NaN is return
2531  if (!TMath::IsNaN(result)) return result;
2532  if (gDebug)
2533  Warning("analytical integral not available for %s - with number %d compute numerical integral", GetName(), GetNumber());
2534  }
2535  return IntegralOneDim(a, b, epsrel, epsrel, error);
2536 }
2537 
2538 ////////////////////////////////////////////////////////////////////////////////
2539 /// Return Integral of function between a and b using the given parameter values and
2540 /// relative and absolute tolerance.
2541 ///
2542 /// The default integrator defined in ROOT::Math::IntegratorOneDimOptions::DefaultIntegrator() is used
2543 /// If ROOT contains the MathMore library the default integrator is set to be
2544 /// the adaptive ROOT::Math::GSLIntegrator (based on QUADPACK) or otherwise the
2545 /// ROOT::Math::GaussIntegrator is used
2546 /// See the reference documentation of these classes for more information about the
2547 /// integration algorithms
2548 /// To change integration algorithm just do :
2549 /// ROOT::Math::IntegratorOneDimOptions::SetDefaultIntegrator(IntegratorName);
2550 /// Valid integrator names are:
2551 /// - Gauss : for ROOT::Math::GaussIntegrator
2552 /// - GaussLegendre : for ROOT::Math::GaussLegendreIntegrator
2553 /// - Adaptive : for ROOT::Math::GSLIntegrator adaptive method (QAG)
2554 /// - AdaptiveSingular : for ROOT::Math::GSLIntegrator adaptive singular method (QAGS)
2555 /// - NonAdaptive : for ROOT::Math::GSLIntegrator non adaptive (QNG)
2556 ///
2557 /// In order to use the GSL integrators one needs to have the MathMore library installed
2558 ///
2559 /// Note 1:
2560 ///
2561 /// Values of the function f(x) at the interval end-points A and B are not
2562 /// required. The subprogram may therefore be used when these values are
2563 /// undefined.
2564 ///
2565 /// Note 2:
2566 ///
2567 /// Instead of TF1::Integral, you may want to use the combination of
2568 /// TF1::CalcGaussLegendreSamplingPoints and TF1::IntegralFast.
2569 /// See an example with the following script:
2570 ///
2571 /// ~~~ {.cpp}
2572 /// void gint() {
2573 /// TF1 *g = new TF1("g","gaus",-5,5);
2574 /// g->SetParameters(1,0,1);
2575 /// //default gaus integration method uses 6 points
2576 /// //not suitable to integrate on a large domain
2577 /// double r1 = g->Integral(0,5);
2578 /// double r2 = g->Integral(0,1000);
2579 ///
2580 /// //try with user directives computing more points
2581 /// Int_t np = 1000;
2582 /// double *x=new double[np];
2583 /// double *w=new double[np];
2584 /// g->CalcGaussLegendreSamplingPoints(np,x,w,1e-15);
2585 /// double r3 = g->IntegralFast(np,x,w,0,5);
2586 /// double r4 = g->IntegralFast(np,x,w,0,1000);
2587 /// double r5 = g->IntegralFast(np,x,w,0,10000);
2588 /// double r6 = g->IntegralFast(np,x,w,0,100000);
2589 /// printf("g->Integral(0,5) = %g\n",r1);
2590 /// printf("g->Integral(0,1000) = %g\n",r2);
2591 /// printf("g->IntegralFast(n,x,w,0,5) = %g\n",r3);
2592 /// printf("g->IntegralFast(n,x,w,0,1000) = %g\n",r4);
2593 /// printf("g->IntegralFast(n,x,w,0,10000) = %g\n",r5);
2594 /// printf("g->IntegralFast(n,x,w,0,100000)= %g\n",r6);
2595 /// delete [] x;
2596 /// delete [] w;
2597 /// }
2598 /// ~~~
2599 ///
2600 /// This example produces the following results:
2601 ///
2602 /// ~~~ {.cpp}
2603 /// g->Integral(0,5) = 1.25331
2604 /// g->Integral(0,1000) = 1.25319
2605 /// g->IntegralFast(n,x,w,0,5) = 1.25331
2606 /// g->IntegralFast(n,x,w,0,1000) = 1.25331
2607 /// g->IntegralFast(n,x,w,0,10000) = 1.25331
2608 /// g->IntegralFast(n,x,w,0,100000)= 1.253
2609 /// ~~~
2610 
2612 {
2613  //Double_t *parameters = GetParameters();
2614  TF1_EvalWrapper wf1(this, 0, fgAbsValue);
2615  Double_t result = 0;
2616  Int_t status = 0;
2620  ROOT::Math::GaussIntegrator iod(epsabs, epsrel);
2621  iod.SetFunction(wf1);
2622  if (a != - TMath::Infinity() && b != TMath::Infinity())
2623  result = iod.Integral(a, b);
2624  else if (a == - TMath::Infinity() && b != TMath::Infinity())
2625  result = iod.IntegralLow(b);
2626  else if (a != - TMath::Infinity() && b == TMath::Infinity())
2627  result = iod.IntegralUp(a);
2628  else if (a == - TMath::Infinity() && b == TMath::Infinity())
2629  result = iod.Integral();
2630  error = iod.Error();
2631  status = iod.Status();
2632  } else {
2634  if (a != - TMath::Infinity() && b != TMath::Infinity())
2635  result = iod.Integral(a, b);
2636  else if (a == - TMath::Infinity() && b != TMath::Infinity())
2637  result = iod.IntegralLow(b);
2638  else if (a != - TMath::Infinity() && b == TMath::Infinity())
2639  result = iod.IntegralUp(a);
2640  else if (a == - TMath::Infinity() && b == TMath::Infinity())
2641  result = iod.Integral();
2642  error = iod.Error();
2643  status = iod.Status();
2644  }
2645  if (status != 0) {
2647  Warning("IntegralOneDim", "Error found in integrating function %s in [%f,%f] using %s. Result = %f +/- %f - status = %d", GetName(), a, b, igName.c_str(), result, error, status);
2648  TString msg("\t\tFunction Parameters = {");
2649  for (int ipar = 0; ipar < GetNpar(); ++ipar) {
2650  msg += TString::Format(" %s = %f ", GetParName(ipar), GetParameter(ipar));
2651  if (ipar < GetNpar() - 1) msg += TString(",");
2652  else msg += TString("}");
2653  }
2654  Info("IntegralOneDim", "%s", msg.Data());
2655  }
2656  return result;
2657 }
2658 
2659 ////////////////////////////////////////////////////////////////////////////////
2660 /// Return Error on Integral of a parametric function between a and b
2661 /// due to the parameter uncertainties and their covariance matrix from the fit.
2662 /// In addition to the integral limits, this method takes as input a pointer to the fitted parameter values
2663 /// and a pointer the covariance matrix from the fit. These pointers should be retrieved from the
2664 /// previously performed fit using the TFitResult class.
2665 /// Note that to get the TFitResult, te fit should be done using the fit option `S`.
2666 /// Example:
2667 /// ~~~~{.cpp}
2668 /// TFitResultPtr r = histo->Fit(func, "S");
2669 /// func->IntegralError(x1,x2,r->GetParams(), r->GetCovarianceMatrix()->GetMatrixArray() );
2670 /// ~~~~
2671 ///
2672 /// IMPORTANT NOTE1:
2673 ///
2674 /// A null pointer to the parameter values vector and to the covariance matrix can be passed.
2675 /// In this case, when the parameter values pointer is null, the parameter values stored in this
2676 /// TF1 function object are used in the integral error computation.
2677 /// When the poassed pointer to the covariance matrix is null, a covariance matrix from the last fit is retrieved
2678 /// from a global fitter instance when it exists. Note that the global fitter instance
2679 /// esists only when ROOT is not running with multi-threading enabled (ROOT::IsImplicitMTEnabled() == True).
2680 /// When the ovariance matrix from the last fit cannot be retrieved, an error message is printed and a a zero value is
2681 /// returned.
2682 ///
2683 ///
2684 /// IMPORTANT NOTE2:
2685 ///
2686 /// When no covariance matrix is passed and in the meantime a fit is done
2687 /// using another function, the routine will signal an error and it will return zero only
2688 /// when the number of fit parameter is different than the values stored in TF1 (TF1::GetNpar() ).
2689 /// In the case that npar is the same, an incorrect result is returned.
2690 ///
2691 /// IMPORTANT NOTE3:
2692 ///
2693 /// The user must pass a pointer to the elements of the full covariance matrix
2694 /// dimensioned with the right size (npar*npar), where npar is the total number of parameters (TF1::GetNpar()),
2695 /// including also the fixed parameters. The covariance matrix must be retrieved from the TFitResult class as
2696 /// shown above and not from TVirtualFitter::GetCovarianceMatrix() function.
2697 
2699 {
2700  Double_t x1[1];
2701  Double_t x2[1];
2702  x1[0] = a, x2[0] = b;
2703  return ROOT::TF1Helper::IntegralError(this, 1, x1, x2, params, covmat, epsilon);
2704 }
2705 
2706 ////////////////////////////////////////////////////////////////////////////////
2707 /// Return Error on Integral of a parametric function with dimension larger than one
2708 /// between a[] and b[] due to the parameters uncertainties.
2709 /// For a TF1 with dimension larger than 1 (for example a TF2 or TF3)
2710 /// TF1::IntegralMultiple is used for the integral calculation
2711 ///
2712 /// In addition to the integral limits, this method takes as input a pointer to the fitted parameter values
2713 /// and a pointer the covariance matrix from the fit. These pointers should be retrieved from the
2714 /// previously performed fit using the TFitResult class.
2715 /// Note that to get the TFitResult, te fit should be done using the fit option `S`.
2716 /// Example:
2717 /// ~~~~{.cpp}
2718 /// TFitResultPtr r = histo2d->Fit(func2, "S");
2719 /// func2->IntegralError(a,b,r->GetParams(), r->GetCovarianceMatrix()->GetMatrixArray() );
2720 /// ~~~~
2721 ///
2722 /// IMPORTANT NOTE1:
2723 ///
2724 /// A null pointer to the parameter values vector and to the covariance matrix can be passed.
2725 /// In this case, when the parameter values pointer is null, the parameter values stored in this
2726 /// TF1 function object are used in the integral error computation.
2727 /// When the poassed pointer to the covariance matrix is null, a covariance matrix from the last fit is retrieved
2728 /// from a global fitter instance when it exists. Note that the global fitter instance
2729 /// esists only when ROOT is not running with multi-threading enabled (ROOT::IsImplicitMTEnabled() == True).
2730 /// When the ovariance matrix from the last fit cannot be retrieved, an error message is printed and a a zero value is
2731 /// returned.
2732 ///
2733 ///
2734 /// IMPORTANT NOTE2:
2735 ///
2736 /// When no covariance matrix is passed and in the meantime a fit is done
2737 /// using another function, the routine will signal an error and it will return zero only
2738 /// when the number of fit parameter is different than the values stored in TF1 (TF1::GetNpar() ).
2739 /// In the case that npar is the same, an incorrect result is returned.
2740 ///
2741 /// IMPORTANT NOTE3:
2742 ///
2743 /// The user must pass a pointer to the elements of the full covariance matrix
2744 /// dimensioned with the right size (npar*npar), where npar is the total number of parameters (TF1::GetNpar()),
2745 /// including also the fixed parameters. The covariance matrix must be retrieved from the TFitResult class as
2746 /// shown above and not from TVirtualFitter::GetCovarianceMatrix() function.
2747 
2748 Double_t TF1::IntegralError(Int_t n, const Double_t *a, const Double_t *b, const Double_t *params, const Double_t *covmat, Double_t epsilon)
2749 {
2750  return ROOT::TF1Helper::IntegralError(this, n, a, b, params, covmat, epsilon);
2751 }
2752 
2753 #ifdef INTHEFUTURE
2754 ////////////////////////////////////////////////////////////////////////////////
2755 /// Gauss-Legendre integral, see CalcGaussLegendreSamplingPoints
2756 
2758 {
2759  if (!g) return 0;
2760  return IntegralFast(g->GetN(), g->GetX(), g->GetY(), a, b, params);
2761 }
2762 #endif
2763 
2764 
2765 ////////////////////////////////////////////////////////////////////////////////
2766 /// Gauss-Legendre integral, see CalcGaussLegendreSamplingPoints
2767 
2769 {
2770  // Now x and w are not used!
2771 
2772  ROOT::Math::WrappedTF1 wf1(*this);
2773  if (params)
2774  wf1.SetParameters(params);
2776  gli.SetFunction(wf1);
2777  return gli.Integral(a, b);
2778 
2779 }
2780 
2781 
2782 ////////////////////////////////////////////////////////////////////////////////
2783 /// See more general prototype below.
2784 /// This interface kept for back compatibility
2785 /// It is recommended to use the other interface where one can specify also epsabs and the maximum number of
2786 /// points
2787 
2789 {
2790  Int_t nfnevl, ifail;
2792  Double_t result = IntegralMultiple(n, a, b, maxpts, epsrel, epsrel, relerr, nfnevl, ifail);
2793  if (ifail > 0) {
2794  Warning("IntegralMultiple", "failed code=%d, ", ifail);
2795  }
2796  return result;
2797 }
2798 
2799 
2800 ////////////////////////////////////////////////////////////////////////////////
2801 /// This function computes, to an attempted specified accuracy, the value of
2802 /// the integral
2803 ///
2804 /// \param[in] n Number of dimensions [2,15]
2805 /// \param[in] a,b One-dimensional arrays of length >= N . On entry A[i], and B[i],
2806 /// contain the lower and upper limits of integration, respectively.
2807 /// \param[in] maxpts Maximum number of function evaluations to be allowed.
2808 /// maxpts >= 2^n +2*n*(n+1) +1
2809 /// if maxpts<minpts, maxpts is set to 10*minpts
2810 /// \param[in] epsrel Specified relative accuracy.
2811 /// \param[in] epsabs Specified absolute accuracy.
2812 /// The integration algorithm will attempt to reach either the relative or the absolute accuracy.
2813 /// In case the maximum function called is reached the algorithm will stop earlier without having reached
2814 /// the desired accuracy
2815 ///
2816 /// \param[out] relerr Contains, on exit, an estimation of the relative accuracy of the result.
2817 /// \param[out] nfnevl number of function evaluations performed.
2818 /// \param[out] ifail
2819 /// \parblock
2820 /// 0 Normal exit. At least minpts and at most maxpts calls to the function were performed.
2821 ///
2822 /// 1 maxpts is too small for the specified accuracy eps. The result and relerr contain the values obtainable for the
2823 /// specified value of maxpts.
2824 ///
2825 /// 3 n<2 or n>15
2826 /// \endparblock
2827 ///
2828 /// Method:
2829 ///
2830 /// The default method used is the Genz-Mallik adaptive multidimensional algorithm
2831 /// using the class ROOT::Math::AdaptiveIntegratorMultiDim (see the reference documentation of the class)
2832 ///
2833 /// Other methods can be used by setting ROOT::Math::IntegratorMultiDimOptions::SetDefaultIntegrator()
2834 /// to different integrators.
2835 /// Other possible integrators are MC integrators based on the ROOT::Math::GSLMCIntegrator class
2836 /// Possible methods are : Vegas, Miser or Plain
2837 /// IN case of MC integration the accuracy is determined by the number of function calls, one should be
2838 /// careful not to use a too large value of maxpts
2839 ///
2840 
2841 Double_t TF1::IntegralMultiple(Int_t n, const Double_t *a, const Double_t *b, Int_t maxpts, Double_t epsrel, Double_t epsabs, Double_t &relerr, Int_t &nfnevl, Int_t &ifail)
2842 {
2844 
2845  double result = 0;
2849  ROOT::Math::AdaptiveIntegratorMultiDim aimd(wf1, epsabs, epsrel, maxpts);
2850  //aimd.SetMinPts(minpts); // use default minpts ( n^2 + 2 * n * (n+1) +1 )
2851  result = aimd.Integral(a, b);
2852  relerr = aimd.RelError();
2853  nfnevl = aimd.NEval();
2854  ifail = aimd.Status();
2855  } else {
2856  // use default abs tolerance = relative tolerance
2858  result = imd.Integral(a, b);
2859  relerr = (result != 0) ? imd.Error() / std::abs(result) : imd.Error();
2860  nfnevl = 0;
2861  ifail = imd.Status();
2862  }
2863 
2864 
2865  return result;
2866 }
2867 
2868 
2869 ////////////////////////////////////////////////////////////////////////////////
2870 /// Return kTRUE if the function is valid
2871 
2873 {
2874  if (fFormula) return fFormula->IsValid();
2875  if (fMethodCall) return fMethodCall->IsValid();
2876  // function built on compiled functors are always valid by definition
2877  // (checked at compiled time)
2878  // invalid is a TF1 where the functor is null pointer and has not been saved
2879  if (!fFunctor && fSave.empty()) return kFALSE;
2880  return kTRUE;
2881 }
2882 
2883 
2884 //______________________________________________________________________________
2885 
2886 
2887 void TF1::Print(Option_t *option) const
2888 {
2889  if (fType == EFType::kFormula) {
2890  printf("Formula based function: %s \n", GetName());
2891  assert(fFormula);
2892  fFormula->Print(option);
2893  } else if (fType > 0) {
2894  if (fType == EFType::kInterpreted)
2895  printf("Interpreted based function: %s(double *x, double *p). Ndim = %d, Npar = %d \n", GetName(), GetNdim(),
2896  GetNpar());
2897  else if (fType == EFType::kCompositionFcn) {
2898  printf("Composition based function: %s. Ndim = %d, Npar = %d \n", GetName(), GetNdim(), GetNpar());
2899  if (!fComposition)
2900  printf("fComposition not found!\n"); // this would be bad
2901  } else {
2902  if (fFunctor)
2903  printf("Compiled based function: %s based on a functor object. Ndim = %d, Npar = %d\n", GetName(),
2904  GetNdim(), GetNpar());
2905  else {
2906  printf("Function based on a list of points from a compiled based function: %s. Ndim = %d, Npar = %d, Npx "
2907  "= %zu\n",
2908  GetName(), GetNdim(), GetNpar(), fSave.size());
2909  if (fSave.empty())
2910  Warning("Print", "Function %s is based on a list of points but list is empty", GetName());
2911  }
2912  }
2913  TString opt(option);
2914  opt.ToUpper();
2915  if (opt.Contains("V")) {
2916  // print list of parameters
2917  if (fNpar > 0) {
2918  printf("List of Parameters: \n");
2919  for (int i = 0; i < fNpar; ++i)
2920  printf(" %20s = %10f \n", GetParName(i), GetParameter(i));
2921  }
2922  if (!fSave.empty()) {
2923  // print list of saved points
2924  printf("List of Saved points (N=%d): \n", int(fSave.size()));
2925  for (auto &x : fSave)
2926  printf("( %10f ) ", x);
2927  printf("\n");
2928  }
2929  }
2930  }
2931  if (fHistogram) {
2932  printf("Contained histogram\n");
2933  fHistogram->Print(option);
2934  }
2935 }
2936 
2937 ////////////////////////////////////////////////////////////////////////////////
2938 /// Paint this function with its current attributes.
2939 /// The function is going to be converted in an histogram and the corresponding
2940 /// histogram is painted.
2941 /// The painted histogram can be retrieved calling afterwards the method TF1::GetHistogram()
2942 
2943 void TF1::Paint(Option_t *choptin)
2944 {
2945  fgCurrent = this;
2946 
2947  char option[32];
2948  strlcpy(option,choptin,32);
2949 
2950  TString opt = option;
2951  opt.ToLower();
2952 
2953  Bool_t optSAME = kFALSE;
2954  if (opt.Contains("same")) {
2955  opt.ReplaceAll("same","");
2956  optSAME = kTRUE;
2957  }
2958  opt.ReplaceAll(' ', "");
2959 
2960  Double_t xmin = fXmin, xmax = fXmax, pmin = fXmin, pmax = fXmax;
2961  if (gPad) {
2962  pmin = gPad->PadtoX(gPad->GetUxmin());
2963  pmax = gPad->PadtoX(gPad->GetUxmax());
2964  }
2965  if (optSAME) {
2966  if (xmax < pmin) return; // Completely outside.
2967  if (xmin > pmax) return;
2968  if (xmin < pmin) xmin = pmin;
2969  if (xmax > pmax) xmax = pmax;
2970  }
2971 
2972  // create an histogram using the function content (re-use it if already existing)
2974 
2975  char *l1 = strstr(option,"PFC"); // Automatic Fill Color
2976  char *l2 = strstr(option,"PLC"); // Automatic Line Color
2977  char *l3 = strstr(option,"PMC"); // Automatic Marker Color
2978  if (l1 || l2 || l3) {
2979  Int_t i = gPad->NextPaletteColor();
2980  if (l1) {memcpy(l1," ",3); fHistogram->SetFillColor(i);}
2981  if (l2) {memcpy(l2," ",3); fHistogram->SetLineColor(i);}
2982  if (l3) {memcpy(l3," ",3); fHistogram->SetMarkerColor(i);}
2983  }
2984 
2985  // set the optimal minimum and maximum
2986  Double_t minimum = fHistogram->GetMinimumStored();
2987  Double_t maximum = fHistogram->GetMaximumStored();
2988  if (minimum <= 0 && gPad && gPad->GetLogy()) minimum = -1111; // This can happen when switching from lin to log scale.
2989  if (gPad && gPad->GetUymin() < fHistogram->GetMinimum() &&
2990  !fHistogram->TestBit(TH1::kIsZoomed)) minimum = -1111; // This can happen after unzooming a fit.
2991  if (minimum == -1111) { // This can happen after unzooming.
2993  minimum = fHistogram->GetYaxis()->GetXmin();
2994  } else {
2995  minimum = fMinimum;
2996  // Optimize the computation of the scale in Y in case the min/max of the
2997  // function oscillate around a constant value
2998  if (minimum == -1111) {
2999  Double_t hmin;
3000  if (optSAME && gPad) hmin = gPad->GetUymin();
3001  else hmin = fHistogram->GetMinimum();
3002  if (hmin > 0) {
3003  Double_t hmax;
3004  Double_t hminpos = hmin;
3005  if (optSAME && gPad) hmax = gPad->GetUymax();
3006  else hmax = fHistogram->GetMaximum();
3007  hmin -= 0.05 * (hmax - hmin);
3008  if (hmin < 0) hmin = 0;
3009  if (hmin <= 0 && gPad && gPad->GetLogy()) hmin = hminpos;
3010  minimum = hmin;
3011  }
3012  }
3013  }
3014  fHistogram->SetMinimum(minimum);
3015  }
3016  if (maximum == -1111) {
3018  maximum = fHistogram->GetYaxis()->GetXmax();
3019  } else {
3020  maximum = fMaximum;
3021  }
3022  fHistogram->SetMaximum(maximum);
3023  }
3024 
3025 
3026  // Draw the histogram.
3027  if (!gPad) return;
3028  if (opt.Length() == 0) {
3029  if (optSAME) fHistogram->Paint("lfsame");
3030  else fHistogram->Paint("lf");
3031  } else {
3032  fHistogram->Paint(option);
3033  }
3034 }
3035 
3036 ////////////////////////////////////////////////////////////////////////////////
3037 /// Create histogram with bin content equal to function value
3038 /// computed at the bin center
3039 /// This histogram will be used to paint the function
3040 /// A re-creation is forced and a new histogram is done if recreate=true
3041 
3043 {
3044  Int_t i;
3045  Double_t xv[1];
3046 
3047  TH1 *histogram = 0;
3048 
3049 
3050  // Create a temporary histogram and fill each channel with the function value
3051  // Preserve axis titles
3052  TString xtitle = "";
3053  TString ytitle = "";
3054  char *semicol = (char *)strstr(GetTitle(), ";");
3055  if (semicol) {
3056  Int_t nxt = strlen(semicol);
3057  char *ctemp = new char[nxt];
3058  strlcpy(ctemp, semicol + 1, nxt);
3059  semicol = (char *)strstr(ctemp, ";");
3060  if (semicol) {
3061  *semicol = 0;
3062  ytitle = semicol + 1;
3063  }
3064  xtitle = ctemp;
3065  delete [] ctemp;
3066  }
3067  if (fHistogram) {
3068  // delete previous histograms if were done if done in different mode
3069  xtitle = fHistogram->GetXaxis()->GetTitle();
3070  ytitle = fHistogram->GetYaxis()->GetTitle();
3071  Bool_t test_logx = fHistogram->TestBit(TH1::kLogX);
3072  if (!gPad->GetLogx() && test_logx) {
3073  delete fHistogram;
3074  fHistogram = nullptr;
3075  recreate = kTRUE;
3076  }
3077  if (gPad->GetLogx() && !test_logx) {
3078  delete fHistogram;
3079  fHistogram = nullptr;
3080  recreate = kTRUE;
3081  }
3082  }
3083 
3084  if (fHistogram && !recreate) {
3085  histogram = fHistogram;
3087  } else {
3088  // If logx, we must bin in logx and not in x
3089  // otherwise in case of several decades, one gets wrong results.
3090  if (xmin > 0 && gPad && gPad->GetLogx()) {
3091  Double_t *xbins = new Double_t[fNpx + 1];
3092  Double_t xlogmin = TMath::Log10(xmin);
3093  Double_t xlogmax = TMath::Log10(xmax);
3094  Double_t dlogx = (xlogmax - xlogmin) / ((Double_t)fNpx);
3095  for (i = 0; i <= fNpx; i++) {
3096  xbins[i] = gPad->PadtoX(xlogmin + i * dlogx);
3097  }
3098  histogram = new TH1D("Func", GetTitle(), fNpx, xbins);
3099  histogram->SetBit(TH1::kLogX);
3100  delete [] xbins;
3101  } else {
3102  histogram = new TH1D("Func", GetTitle(), fNpx, xmin, xmax);
3103  }
3104  if (fMinimum != -1111) histogram->SetMinimum(fMinimum);
3105  if (fMaximum != -1111) histogram->SetMaximum(fMaximum);
3106  histogram->SetDirectory(0);
3107  }
3108  R__ASSERT(histogram);
3109 
3110  // Restore axis titles.
3111  histogram->GetXaxis()->SetTitle(xtitle.Data());
3112  histogram->GetYaxis()->SetTitle(ytitle.Data());
3113  Double_t *parameters = GetParameters();
3114 
3115  InitArgs(xv, parameters);
3116  for (i = 1; i <= fNpx; i++) {
3117  xv[0] = histogram->GetBinCenter(i);
3118  histogram->SetBinContent(i, EvalPar(xv, parameters));
3119  }
3120 
3121  // Copy Function attributes to histogram attributes.
3122  histogram->SetBit(TH1::kNoStats);
3123  histogram->SetLineColor(GetLineColor());
3124  histogram->SetLineStyle(GetLineStyle());
3125  histogram->SetLineWidth(GetLineWidth());
3126  histogram->SetFillColor(GetFillColor());
3127  histogram->SetFillStyle(GetFillStyle());
3128  histogram->SetMarkerColor(GetMarkerColor());
3129  histogram->SetMarkerStyle(GetMarkerStyle());
3130  histogram->SetMarkerSize(GetMarkerSize());
3131 
3132  // update saved histogram in case it was deleted or if it is the first time the method is called
3133  // for example when called from TF1::GetHistogram()
3134  if (!fHistogram) fHistogram = histogram;
3135  return histogram;
3136 
3137 }
3138 
3139 
3140 ////////////////////////////////////////////////////////////////////////////////
3141 /// Release parameter number ipar If used in a fit, the parameter
3142 /// can vary freely. The parameter limits are reset to 0,0.
3143 
3145 {
3146  if (ipar < 0 || ipar > GetNpar() - 1) return;
3147  SetParLimits(ipar, 0, 0);
3148 }
3149 
3150 
3151 ////////////////////////////////////////////////////////////////////////////////
3152 /// Save values of function in array fSave
3153 
3155 {
3156  Double_t *parameters = GetParameters();
3157  //if (fSave != 0) {delete [] fSave; fSave = 0;}
3158  if (fParent && fParent->InheritsFrom(TH1::Class())) {
3159  //if parent is a histogram save the function at the center of the bins
3160  if ((xmin > 0 && xmax > 0) && TMath::Abs(TMath::Log10(xmax / xmin) > TMath::Log10(fNpx))) {
3161  TH1 *h = (TH1 *)fParent;
3162  Int_t bin1 = h->GetXaxis()->FindBin(xmin);
3163  Int_t bin2 = h->GetXaxis()->FindBin(xmax);
3164  int fNsave = bin2 - bin1 + 4;
3165  //fSave = new Double_t[fNsave];
3166  fSave.resize(fNsave);
3167  Double_t xv[1];
3168 
3169  InitArgs(xv, parameters);
3170  for (Int_t i = bin1; i <= bin2; i++) {
3171  xv[0] = h->GetXaxis()->GetBinCenter(i);
3172  fSave[i - bin1] = EvalPar(xv, parameters);
3173  }
3174  fSave[fNsave - 3] = xmin;
3175  fSave[fNsave - 2] = xmax;
3176  fSave[fNsave - 1] = xmax;
3177  return;
3178  }
3179  }
3180  int fNsave = fNpx + 3;
3181  if (fNsave <= 3) {
3182  return;
3183  }
3184  //fSave = new Double_t[fNsave];
3185  fSave.resize(fNsave);
3186  Double_t dx = (xmax - xmin) / fNpx;
3187  if (dx <= 0) {
3188  dx = (fXmax - fXmin) / fNpx;
3189  fNsave--;
3190  xmin = fXmin + 0.5 * dx;
3191  xmax = fXmax - 0.5 * dx;
3192  }
3193  Double_t xv[1];
3194  InitArgs(xv, parameters);
3195  for (Int_t i = 0; i <= fNpx; i++) {
3196  xv[0] = xmin + dx * i;
3197  fSave[i] = EvalPar(xv, parameters);
3198  }
3199  fSave[fNpx + 1] = xmin;
3200  fSave[fNpx + 2] = xmax;
3201 }
3202 
3203 
3204 ////////////////////////////////////////////////////////////////////////////////
3205 /// Save primitive as a C++ statement(s) on output stream out
3206 
3207 void TF1::SavePrimitive(std::ostream &out, Option_t *option /*= ""*/)
3208 {
3209  Int_t i;
3210  char quote = '"';
3211 
3212  // Save the function as C code independant from ROOT.
3213  if (strstr(option, "cc")) {
3214  out << "double " << GetName() << "(double xv) {" << std::endl;
3215  Double_t dx = (fXmax - fXmin) / (fNpx - 1);
3216  out << " double x[" << fNpx << "] = {" << std::endl;
3217  out << " ";
3218  Int_t n = 0;
3219  for (i = 0; i < fNpx; i++) {
3220  out << fXmin + dx *i ;
3221  if (i < fNpx - 1) out << ", ";
3222  if (n++ == 10) {
3223  out << std::endl;
3224  out << " ";
3225  n = 0;
3226  }
3227  }
3228  out << std::endl;
3229  out << " };" << std::endl;
3230  out << " double y[" << fNpx << "] = {" << std::endl;
3231  out << " ";
3232  n = 0;
3233  for (i = 0; i < fNpx; i++) {
3234  out << Eval(fXmin + dx * i);
3235  if (i < fNpx - 1) out << ", ";
3236  if (n++ == 10) {
3237  out << std::endl;
3238  out << " ";
3239  n = 0;
3240  }
3241  }
3242  out << std::endl;
3243  out << " };" << std::endl;
3244  out << " if (xv<x[0]) return y[0];" << std::endl;
3245  out << " if (xv>x[" << fNpx - 1 << "]) return y[" << fNpx - 1 << "];" << std::endl;
3246  out << " int i, j=0;" << std::endl;
3247  out << " for (i=1; i<" << fNpx << "; i++) { if (xv < x[i]) break; j++; }" << std::endl;
3248  out << " return y[j] + (y[j + 1] - y[j]) / (x[j + 1] - x[j]) * (xv - x[j]);" << std::endl;
3249  out << "}" << std::endl;
3250  return;
3251  }
3252 
3253  out << " " << std::endl;
3254 
3255  // Either f1Number is computed locally or set from outside
3256  static Int_t f1Number = 0;
3257  TString f1Name(GetName());
3258  const char *l = strstr(option, "#");
3259  if (l != 0) {
3260  sscanf(&l[1], "%d", &f1Number);
3261  } else {
3262  ++f1Number;
3263  }
3264  f1Name += f1Number;
3265 
3266  const char *addToGlobList = fParent ? ", TF1::EAddToList::kNo" : ", TF1::EAddToList::kDefault";
3267 
3268  if (!fType) {
3269  out << " TF1 *" << f1Name.Data() << " = new TF1(" << quote << GetName() << quote << "," << quote << GetTitle() << quote << "," << fXmin << "," << fXmax << addToGlobList << ");" << std::endl;
3270  if (fNpx != 100) {
3271  out << " " << f1Name.Data() << "->SetNpx(" << fNpx << ");" << std::endl;
3272  }
3273  } else {
3274  out << " TF1 *" << f1Name.Data() << " = new TF1(" << quote << "*" << GetName() << quote << "," << fXmin << "," << fXmax << "," << GetNpar() << ");" << std::endl;
3275  out << " //The original function : " << GetTitle() << " had originally been created by:" << std::endl;
3276  out << " //TF1 *" << GetName() << " = new TF1(" << quote << GetName() << quote << "," << GetTitle() << "," << fXmin << "," << fXmax << "," << GetNpar();
3277  out << ", 1" << addToGlobList << ");" << std::endl;
3278  out << " " << f1Name.Data() << "->SetRange(" << fXmin << "," << fXmax << ");" << std::endl;
3279  out << " " << f1Name.Data() << "->SetName(" << quote << GetName() << quote << ");" << std::endl;
3280  out << " " << f1Name.Data() << "->SetTitle(" << quote << GetTitle() << quote << ");" << std::endl;
3281  if (fNpx != 100) {
3282  out << " " << f1Name.Data() << "->SetNpx(" << fNpx << ");" << std::endl;
3283  }
3284  Double_t dx = (fXmax - fXmin) / fNpx;
3285  Double_t xv[1];
3286  Double_t *parameters = GetParameters();
3287  InitArgs(xv, parameters);
3288  for (i = 0; i <= fNpx; i++) {
3289  xv[0] = fXmin + dx * i;
3290  Double_t save = EvalPar(xv, parameters);
3291  out << " " << f1Name.Data() << "->SetSavedPoint(" << i << "," << save << ");" << std::endl;
3292  }
3293  out << " " << f1Name.Data() << "->SetSavedPoint(" << fNpx + 1 << "," << fXmin << ");" << std::endl;
3294  out << " " << f1Name.Data() << "->SetSavedPoint(" << fNpx + 2 << "," << fXmax << ");" << std::endl;
3295  }
3296 
3297  if (TestBit(kNotDraw)) {
3298  out << " " << f1Name.Data() << "->SetBit(TF1::kNotDraw);" << std::endl;
3299  }
3300  if (GetFillColor() != 0) {
3301  if (GetFillColor() > 228) {
3303  out << " " << f1Name.Data() << "->SetFillColor(ci);" << std::endl;
3304  } else
3305  out << " " << f1Name.Data() << "->SetFillColor(" << GetFillColor() << ");" << std::endl;
3306  }
3307  if (GetFillStyle() != 1001) {
3308  out << " " << f1Name.Data() << "->SetFillStyle(" << GetFillStyle() << ");" << std::endl;
3309  }
3310  if (GetMarkerColor() != 1) {
3311  if (GetMarkerColor() > 228) {
3313  out << " " << f1Name.Data() << "->SetMarkerColor(ci);" << std::endl;
3314  } else
3315  out << " " << f1Name.Data() << "->SetMarkerColor(" << GetMarkerColor() << ");" << std::endl;
3316  }
3317  if (GetMarkerStyle() != 1) {
3318  out << " " << f1Name.Data() << "->SetMarkerStyle(" << GetMarkerStyle() << ");" << std::endl;
3319  }
3320  if (GetMarkerSize() != 1) {
3321  out << " " << f1Name.Data() << "->SetMarkerSize(" << GetMarkerSize() << ");" << std::endl;
3322  }
3323  if (GetLineColor() != 1) {
3324  if (GetLineColor() > 228) {
3326  out << " " << f1Name.Data() << "->SetLineColor(ci);" << std::endl;
3327  } else
3328  out << " " << f1Name.Data() << "->SetLineColor(" << GetLineColor() << ");" << std::endl;
3329  }
3330  if (GetLineWidth() != 4) {
3331  out << " " << f1Name.Data() << "->SetLineWidth(" << GetLineWidth() << ");" << std::endl;
3332  }
3333  if (GetLineStyle() != 1) {
3334  out << " " << f1Name.Data() << "->SetLineStyle(" << GetLineStyle() << ");" << std::endl;
3335  }
3336  if (GetChisquare() != 0) {
3337  out << " " << f1Name.Data() << "->SetChisquare(" << GetChisquare() << ");" << std::endl;
3338  out << " " << f1Name.Data() << "->SetNDF(" << GetNDF() << ");" << std::endl;
3339  }
3340 
3341  if (GetXaxis()) GetXaxis()->SaveAttributes(out, f1Name.Data(), "->GetXaxis()");
3342  if (GetYaxis()) GetYaxis()->SaveAttributes(out, f1Name.Data(), "->GetYaxis()");
3343 
3344  Double_t parmin, parmax;
3345  for (i = 0; i < GetNpar(); i++) {
3346  out << " " << f1Name.Data() << "->SetParameter(" << i << "," << GetParameter(i) << ");" << std::endl;
3347  out << " " << f1Name.Data() << "->SetParError(" << i << "," << GetParError(i) << ");" << std::endl;
3348  GetParLimits(i, parmin, parmax);
3349  out << " " << f1Name.Data() << "->SetParLimits(" << i << "," << parmin << "," << parmax << ");" << std::endl;
3350  }
3351  if (!strstr(option, "nodraw")) {
3352  out << " " << f1Name.Data() << "->Draw("
3353  << quote << option << quote << ");" << std::endl;
3354  }
3355 }
3356 
3357 
3358 ////////////////////////////////////////////////////////////////////////////////
3359 /// Static function setting the current function.
3360 /// the current function may be accessed in static C-like functions
3361 /// when fitting or painting a function.
3362 
3364 {
3365  fgCurrent = f1;
3366 }
3367 
3368 ////////////////////////////////////////////////////////////////////////////////
3369 /// Set the result from the fit
3370 /// parameter values, errors, chi2, etc...
3371 /// Optionally a pointer to a vector (with size fNpar) of the parameter indices in the FitResult can be passed
3372 /// This is useful in the case of a combined fit with different functions, and the FitResult contains the global result
3373 /// By default it is assume that indpar = {0,1,2,....,fNpar-1}.
3374 
3375 void TF1::SetFitResult(const ROOT::Fit::FitResult &result, const Int_t *indpar)
3376 {
3377  Int_t npar = GetNpar();
3378  if (result.IsEmpty()) {
3379  Warning("SetFitResult", "Empty Fit result - nothing is set in TF1");
3380  return;
3381  }
3382  if (indpar == 0 && npar != (int) result.NPar()) {
3383  Error("SetFitResult", "Invalid Fit result passed - number of parameter is %d , different than TF1::GetNpar() = %d", npar, result.NPar());
3384  return;
3385  }
3386  if (result.Chi2() > 0)
3387  SetChisquare(result.Chi2());
3388  else
3389  SetChisquare(result.MinFcnValue());
3390 
3391  SetNDF(result.Ndf());
3392  SetNumberFitPoints(result.Ndf() + result.NFreeParameters());
3393 
3394 
3395  for (Int_t i = 0; i < npar; ++i) {
3396  Int_t ipar = (indpar != 0) ? indpar[i] : i;
3397  if (ipar < 0) continue;
3398  GetParameters()[i] = result.Parameter(ipar);
3399  // in case errors are not present do not set them
3400  if (ipar < (int) result.Errors().size())
3401  fParErrors[i] = result.Error(ipar);
3402  }
3403  //invalidate cached integral since parameters have changed
3404  Update();
3405 
3406 }
3407 
3408 
3409 ////////////////////////////////////////////////////////////////////////////////
3410 /// Set the maximum value along Y for this function
3411 /// In case the function is already drawn, set also the maximum in the
3412 /// helper histogram
3413 
3415 {
3416  fMaximum = maximum;
3417  if (fHistogram) fHistogram->SetMaximum(maximum);
3418  if (gPad) gPad->Modified();
3419 }
3420 
3421 
3422 ////////////////////////////////////////////////////////////////////////////////
3423 /// Set the minimum value along Y for this function
3424 /// In case the function is already drawn, set also the minimum in the
3425 /// helper histogram
3426 
3428 {
3429  fMinimum = minimum;
3430  if (fHistogram) fHistogram->SetMinimum(minimum);
3431  if (gPad) gPad->Modified();
3432 }
3433 
3434 
3435 ////////////////////////////////////////////////////////////////////////////////
3436 /// Set the number of degrees of freedom
3437 /// ndf should be the number of points used in a fit - the number of free parameters
3438 
3440 {
3441  fNDF = ndf;
3442 }
3443 
3444 
3445 ////////////////////////////////////////////////////////////////////////////////
3446 /// Set the number of points used to draw the function
3447 ///
3448 /// The default number of points along x is 100 for 1-d functions and 30 for 2-d/3-d functions
3449 /// You can increase this value to get a better resolution when drawing
3450 /// pictures with sharp peaks or to get a better result when using TF1::GetRandom
3451 /// the minimum number of points is 4, the maximum is 10000000 for 1-d and 10000 for 2-d/3-d functions
3452 
3454 {
3455  const Int_t minPx = 4;
3456  Int_t maxPx = 10000000;
3457  if (GetNdim() > 1) maxPx = 10000;
3458  if (npx >= minPx && npx <= maxPx) {
3459  fNpx = npx;
3460  } else {
3461  if (npx < minPx) fNpx = minPx;
3462  if (npx > maxPx) fNpx = maxPx;
3463  Warning("SetNpx", "Number of points must be >=%d && <= %d, fNpx set to %d", minPx, maxPx, fNpx);
3464  }
3465  Update();
3466 }
3467 ////////////////////////////////////////////////////////////////////////////////
3468 /// Set name of parameter number ipar
3469 
3470 void TF1::SetParName(Int_t ipar, const char *name)
3471 {
3472  if (fFormula) {
3473  if (ipar < 0 || ipar >= GetNpar()) return;
3474  fFormula->SetParName(ipar, name);
3475  } else
3476  fParams->SetParName(ipar, name);
3477 }
3478 
3479 ////////////////////////////////////////////////////////////////////////////////
3480 /// Set up to 10 parameter names
3481 
3482 void TF1::SetParNames(const char *name0, const char *name1, const char *name2, const char *name3, const char *name4,
3483  const char *name5, const char *name6, const char *name7, const char *name8, const char *name9, const char *name10)
3484 {
3485  if (fFormula)
3486  fFormula->SetParNames(name0, name1, name2, name3, name4, name5, name6, name7, name8, name9, name10);
3487  else
3488  fParams->SetParNames(name0, name1, name2, name3, name4, name5, name6, name7, name8, name9, name10);
3489 }
3490 ////////////////////////////////////////////////////////////////////////////////
3491 /// Set error for parameter number ipar
3492 
3494 {
3495  if (ipar < 0 || ipar > GetNpar() - 1) return;
3496  fParErrors[ipar] = error;
3497 }
3498 
3499 
3500 ////////////////////////////////////////////////////////////////////////////////
3501 /// Set errors for all active parameters
3502 /// when calling this function, the array errors must have at least fNpar values
3503 
3504 void TF1::SetParErrors(const Double_t *errors)
3505 {
3506  if (!errors) return;
3507  for (Int_t i = 0; i < GetNpar(); i++) fParErrors[i] = errors[i];
3508 }
3509 
3510 
3511 ////////////////////////////////////////////////////////////////////////////////
3512 /// Set limits for parameter ipar.
3513 ///
3514 /// The specified limits will be used in a fit operation
3515 /// when the option "B" is specified (Bounds).
3516 /// To fix a parameter, use TF1::FixParameter
3517 
3518 void TF1::SetParLimits(Int_t ipar, Double_t parmin, Double_t parmax)
3519 {
3520  Int_t npar = GetNpar();
3521  if (ipar < 0 || ipar > npar - 1) return;
3522  if (int(fParMin.size()) != npar) {
3523  fParMin.resize(npar);
3524  }
3525  if (int(fParMax.size()) != npar) {
3526  fParMax.resize(npar);
3527  }
3528  fParMin[ipar] = parmin;
3529  fParMax[ipar] = parmax;
3530 }
3531 
3532 
3533 ////////////////////////////////////////////////////////////////////////////////
3534 /// Initialize the upper and lower bounds to draw the function.
3535 ///
3536 /// The function range is also used in an histogram fit operation
3537 /// when the option "R" is specified.
3538 
3540 {
3541  fXmin = xmin;
3542  fXmax = xmax;
3543  if (fType == EFType::kCompositionFcn && fComposition) {
3544  fComposition->SetRange(xmin, xmax); // automatically updates sub-functions
3545  }
3546  Update();
3547 }
3548 
3549 
3550 ////////////////////////////////////////////////////////////////////////////////
3551 /// Restore value of function saved at point
3552 
3554 {
3555  if (fSave.size() == 0) {
3556  fSave.resize(fNpx + 3);
3557  }
3558  if (point < 0 || point >= int(fSave.size())) return;
3559  fSave[point] = value;
3560 }
3561 
3562 
3563 ////////////////////////////////////////////////////////////////////////////////
3564 /// Set function title
3565 /// if title has the form "fffffff;xxxx;yyyy", it is assumed that
3566 /// the function title is "fffffff" and "xxxx" and "yyyy" are the
3567 /// titles for the X and Y axis respectively.
3568 
3569 void TF1::SetTitle(const char *title)
3570 {
3571  if (!title) return;
3572  fTitle = title;
3573  if (!fHistogram) return;
3574  fHistogram->SetTitle(title);
3575  if (gPad) gPad->Modified();
3576 }
3577 
3578 
3579 ////////////////////////////////////////////////////////////////////////////////
3580 /// Stream a class object.
3581 
3582 void TF1::Streamer(TBuffer &b)
3583 {
3584  if (b.IsReading()) {
3585  UInt_t R__s, R__c;
3586  Version_t v = b.ReadVersion(&R__s, &R__c);
3587  // process new version with new TFormula class which is contained in TF1
3588  //printf("reading TF1....- version %d..\n",v);
3589 
3590  if (v > 7) {
3591  // new classes with new TFormula
3592  // need to register the objects
3593  b.ReadClassBuffer(TF1::Class(), this, v, R__s, R__c);
3594  if (!TestBit(kNotGlobal)) {
3596  gROOT->GetListOfFunctions()->Add(this);
3597  }
3598  return;
3599  } else {
3600  ROOT::v5::TF1Data fold;
3601  //printf("Reading TF1 as v5::TF1Data- version %d \n",v);
3602  fold.Streamer(b, v, R__s, R__c, TF1::Class());
3603  // convert old TF1 to new one
3604  ((TF1v5Convert *)this)->Convert(fold);
3605  }
3606  }
3607 
3608  // Writing
3609  else {
3610  Int_t saved = 0;
3611  // save not-formula functions as array of points
3612  if (fType > 0 && fSave.empty() && fType != EFType::kCompositionFcn) {
3613  saved = 1;
3614  Save(fXmin, fXmax, 0, 0, 0, 0);
3615  }
3616  b.WriteClassBuffer(TF1::Class(), this);
3617 
3618  // clear vector contents
3619  if (saved) {
3620  fSave.clear();
3621  }
3622  }
3623 }
3624 
3625 
3626 ////////////////////////////////////////////////////////////////////////////////
3627 /// Called by functions such as SetRange, SetNpx, SetParameters
3628 /// to force the deletion of the associated histogram or Integral
3629 
3631 {
3632  delete fHistogram;
3633  fHistogram = 0;
3634  if (!fIntegral.empty()) {
3635  fIntegral.clear();
3636  fAlpha.clear();
3637  fBeta.clear();
3638  fGamma.clear();
3639  }
3640  if (fNormalized) {
3641  // need to compute the integral of the not-normalized function
3642  fNormalized = false;
3643  fNormIntegral = Integral(fXmin, fXmax, 0.0);
3644  fNormalized = true;
3645  } else
3646  fNormIntegral = 0;
3647 
3648  // std::vector<double>x(fNdim);
3649  // if ((fType == 1) && !fFunctor->Empty()) (*fFunctor)x.data(), (Double_t*)fParams);
3650  if (fType == EFType::kCompositionFcn && fComposition) {
3651  // double-check that the parameters are correct
3652  fComposition->SetParameters(GetParameters());
3653 
3654  fComposition->Update(); // should not be necessary, but just to be safe
3655  }
3656 }
3657 
3658 ////////////////////////////////////////////////////////////////////////////////
3659 /// Static function to set the global flag to reject points
3660 /// the fgRejectPoint global flag is tested by all fit functions
3661 /// if TRUE the point is not included in the fit.
3662 /// This flag can be set by a user in a fitting function.
3663 /// The fgRejectPoint flag is reset by the TH1 and TGraph fitting functions.
3664 
3666 {
3667  fgRejectPoint = reject;
3668 }
3669 
3670 
3671 ////////////////////////////////////////////////////////////////////////////////
3672 /// See TF1::RejectPoint above
3673 
3675 {
3676  return fgRejectPoint;
3677 }
3678 
3679 ////////////////////////////////////////////////////////////////////////////////
3680 /// Return nth moment of function between a and b
3681 ///
3682 /// See TF1::Integral() for parameter definitions
3683 
3685 {
3686  // wrapped function in interface for integral calculation
3687  // using abs value of integral
3688 
3689  TF1_EvalWrapper func(this, params, kTRUE, n);
3690 
3692 
3693  giod.SetFunction(func);
3694  giod.SetRelTolerance(epsilon);
3695 
3696  Double_t norm = giod.Integral(a, b);
3697  if (norm == 0) {
3698  Error("Moment", "Integral zero over range");
3699  return 0;
3700  }
3701 
3702  // calculate now integral of x^n f(x)
3703  // wrapped the member function EvalNum in interface required by integrator using the functor class
3704  ROOT::Math::Functor1D xnfunc(&func, &TF1_EvalWrapper::EvalNMom);
3705  giod.SetFunction(xnfunc);
3706 
3707  Double_t res = giod.Integral(a, b) / norm;
3708 
3709  return res;
3710 }
3711 
3712 
3713 ////////////////////////////////////////////////////////////////////////////////
3714 /// Return nth central moment of function between a and b
3715 /// (i.e the n-th moment around the mean value)
3716 ///
3717 /// See TF1::Integral() for parameter definitions
3718 ///
3719 /// \author Gene Van Buren <gene@bnl.gov>
3720 
3722 {
3723  TF1_EvalWrapper func(this, params, kTRUE, n);
3724 
3726 
3727  giod.SetFunction(func);
3728  giod.SetRelTolerance(epsilon);
3729 
3730  Double_t norm = giod.Integral(a, b);
3731  if (norm == 0) {
3732  Error("Moment", "Integral zero over range");
3733  return 0;
3734  }
3735 
3736  // calculate now integral of xf(x)
3737  // wrapped the member function EvalFirstMom in interface required by integrator using the functor class
3738  ROOT::Math::Functor1D xfunc(&func, &TF1_EvalWrapper::EvalFirstMom);
3739  giod.SetFunction(xfunc);
3740 
3741  // estimate of mean value
3742  Double_t xbar = giod.Integral(a, b) / norm;
3743 
3744  // use different mean value in function wrapper
3745  func.fX0 = xbar;
3746  ROOT::Math::Functor1D xnfunc(&func, &TF1_EvalWrapper::EvalNMom);
3747  giod.SetFunction(xnfunc);
3748 
3749  Double_t res = giod.Integral(a, b) / norm;
3750  return res;
3751 }
3752 
3753 
3754 //______________________________________________________________________________
3755 // some useful static utility functions to compute sampling points for IntegralFast
3756 ////////////////////////////////////////////////////////////////////////////////
3757 /// Type safe interface (static method)
3758 /// The number of sampling points are taken from the TGraph
3759 
3760 #ifdef INTHEFUTURE
3762 {
3763  if (!g) return;
3764  CalcGaussLegendreSamplingPoints(g->GetN(), g->GetX(), g->GetY(), eps);
3765 }
3766 
3767 
3768 ////////////////////////////////////////////////////////////////////////////////
3769 /// Type safe interface (static method)
3770 /// A TGraph is created with new with num points and the pointer to the
3771 /// graph is returned by the function. It is the responsibility of the
3772 /// user to delete the object.
3773 /// if num is invalid (<=0) NULL is returned
3774 
3776 {
3777  if (num <= 0)
3778  return 0;
3779 
3780  TGraph *g = new TGraph(num);
3781  CalcGaussLegendreSamplingPoints(g->GetN(), g->GetX(), g->GetY(), eps);
3782  return g;
3783 }
3784 #endif
3785 
3786 
3787 ////////////////////////////////////////////////////////////////////////////////
3788 /// Type: unsafe but fast interface filling the arrays x and w (static method)
3789 ///
3790 /// Given the number of sampling points this routine fills the arrays x and w
3791 /// of length num, containing the abscissa and weight of the Gauss-Legendre
3792 /// n-point quadrature formula.
3793 ///
3794 /// Gauss-Legendre:
3795 /** \f[
3796  W(x)=1 -1<x<1 \\
3797  (j+1)P_{j+1} = (2j+1)xP_j-jP_{j-1}
3798  \f]
3799 **/
3800 /// num is the number of sampling points (>0)
3801 /// x and w are arrays of size num
3802 /// eps is the relative precision
3803 ///
3804 /// If num<=0 or eps<=0 no action is done.
3805 ///
3806 /// Reference: Numerical Recipes in C, Second Edition
3807 
3809 {
3810  // This function is just kept like this for backward compatibility!
3811 
3813  gli.GetWeightVectors(x, w);
3814 
3815 
3816 }
3817 
3818 
3819 /** \class TF1Parameters
3820 TF1 Parameters class
3821 */
3822 
3823 ////////////////////////////////////////////////////////////////////////////////
3824 /// Returns the parameter number given a name
3825 /// not very efficient but list of parameters is typically small
3826 /// could use a map if needed
3827 
3829 {
3830  for (unsigned int i = 0; i < fParNames.size(); ++i) {
3831  if (fParNames[i] == std::string(name)) return i;
3832  }
3833  return -1;
3834 }
3835 
3836 ////////////////////////////////////////////////////////////////////////////////
3837 /// Set parameter values
3838 
3840  Double_t p5, Double_t p6, Double_t p7, Double_t p8,
3841  Double_t p9, Double_t p10)
3842 {
3843  unsigned int npar = fParameters.size();
3844  if (npar > 0) fParameters[0] = p0;
3845  if (npar > 1) fParameters[1] = p1;
3846  if (npar > 2) fParameters[2] = p2;
3847  if (npar > 3) fParameters[3] = p3;
3848  if (npar > 4) fParameters[4] = p4;
3849  if (npar > 5) fParameters[5] = p5;
3850  if (npar > 6) fParameters[6] = p6;
3851  if (npar > 7) fParameters[7] = p7;
3852  if (npar > 8) fParameters[8] = p8;
3853  if (npar > 9) fParameters[9] = p9;
3854  if (npar > 10) fParameters[10] = p10;
3855 }
3856 
3857 ////////////////////////////////////////////////////////////////////////////////
3858 /// Set parameter names
3859 
3860 void TF1Parameters::SetParNames(const char *name0, const char *name1, const char *name2, const char *name3,
3861  const char *name4, const char *name5, const char *name6, const char *name7,
3862  const char *name8, const char *name9, const char *name10)
3863 {
3864  unsigned int npar = fParNames.size();
3865  if (npar > 0) fParNames[0] = name0;
3866  if (npar > 1) fParNames[1] = name1;
3867  if (npar > 2) fParNames[2] = name2;
3868  if (npar > 3) fParNames[3] = name3;
3869  if (npar > 4) fParNames[4] = name4;
3870  if (npar > 5) fParNames[5] = name5;
3871  if (npar > 6) fParNames[6] = name6;
3872  if (npar > 7) fParNames[7] = name7;
3873  if (npar > 8) fParNames[8] = name8;
3874  if (npar > 9) fParNames[9] = name9;
3875  if (npar > 10) fParNames[10] = name10;
3876 }
ROOT::v5::TF1Data::fNpx
Int_t fNpx
Definition: TF1Data.h:41
ROOT::Math::GaussIntegrator::SetFunction
void SetFunction(const IGenFunction &)
Set integration function (flag control if function must be copied inside).
Definition: GaussIntegrator.cxx:182
ROOT::Math::IntegratorOneDim::Error
double Error() const
return the estimate of the absolute Error of the last Integral calculation
Definition: Integrator.h:416
TF1::GetMinimumX
virtual Double_t GetMinimumX(Double_t xmin=0, Double_t xmax=0, Double_t epsilon=1.E-10, Int_t maxiter=100, Bool_t logx=false) const
Returns the X value corresponding to the minimum value of the function on the (xmin,...
Definition: TF1.cxx:1819
l
auto * l
Definition: textangle.C:4
TF1::fNDF
Int_t fNDF
Number of degrees of freedom in the fit.
Definition: TF1.h:250
TF1::GetHistogram
virtual TH1 * GetHistogram() const
Return a pointer to the histogram used to visualise the function Note that this histogram is managed ...
Definition: TF1.cxx:1580
TF1::DrawF1
virtual void DrawF1(Double_t xmin, Double_t xmax, Option_t *option="")
Draw function between xmin and xmax.
Definition: TF1.cxx:1421
ROOT::v5::TF1Data::fNsave
Int_t fNsave
Definition: TF1Data.h:45
TF1::EAddToList::kDefault
@ kDefault
TAttMarker::SetMarkerSize
virtual void SetMarkerSize(Size_t msize=1)
Set the marker size.
Definition: TAttMarker.h:41
ROOT::Math::Cephes::gamma
double gamma(double x)
Definition: SpecFuncCephes.cxx:339
m
auto * m
Definition: textangle.C:8
R__v5TF1Updater
static void R__v5TF1Updater(Int_t nobjects, TObject **from, TObject **to)
Definition: TF1.cxx:137
TMath::AreEqualRel
Bool_t AreEqualRel(Double_t af, Double_t bf, Double_t relPrec)
Definition: TMath.h:430
ROOT::v5::TFormula::GetNpar
virtual Int_t GetNpar() const
Definition: TFormula.h:238
n
const Int_t n
Definition: legend1.C:16
ROOT::Fit::FitResult::Parameter
double Parameter(unsigned int i) const
parameter value by index
Definition: FitResult.h:181
TF1::EAddToList::kAdd
@ kAdd
TAxis
Class to manage histogram axis.
Definition: TAxis.h:30
TF1::GetCurrent
static TF1 * GetCurrent()
Static function returning the current function being processed.
Definition: TF1.cxx:1565
TF1::fgAbsValue
static std::atomic< Bool_t > fgAbsValue
Definition: TF1.h:304
Minimizer.h
GetGlobalListOption
TF1::EAddToList GetGlobalListOption(Option_t *opt)
Definition: TF1.cxx:682
TBrowser
Using a TBrowser one can browse all ROOT objects.
Definition: TBrowser.h:37
ymax
float ymax
Definition: THbookFile.cxx:95
TF1::RejectPoint
static void RejectPoint(Bool_t reject=kTRUE)
Static function to set the global flag to reject points the fgRejectPoint global flag is tested by al...
Definition: TF1.cxx:3665
TF1::ExecuteEvent
virtual void ExecuteEvent(Int_t event, Int_t px, Int_t py)
Execute action corresponding to one event.
Definition: TF1.cxx:1537
kTRUE
const Bool_t kTRUE
Definition: RtypesCore.h:100
ROOT::Math::WrappedFunction
Template class to wrap any C++ callable object which takes one argument i.e.
Definition: WrappedFunction.h:56
ROOT::Math::Minimizer::SetLimitedVariable
virtual bool SetLimitedVariable(unsigned int ivar, const std::string &name, double val, double step, double lower, double upper)
set a new upper/lower limited variable (override if minimizer supports them ) otherwise as default se...
Definition: Minimizer.h:160
e
#define e(i)
Definition: RSha256.hxx:103
TF1::GetObjectInfo
virtual char * GetObjectInfo(Int_t px, Int_t py) const
Redefines TObject::GetObjectInfo.
Definition: TF1.cxx:1914
TObject::TestBit
R__ALWAYS_INLINE Bool_t TestBit(UInt_t f) const
Definition: TObject.h:187
Version_t
short Version_t
Definition: RtypesCore.h:65
TGraph::Draw
virtual void Draw(Option_t *chopt="")
Draw this graph with its current attributes.
Definition: TGraph.cxx:769
snprintf
#define snprintf
Definition: civetweb.c:1540
TStyle::GetFuncColor
Color_t GetFuncColor() const
Definition: TStyle.h:210
TF1::fSave
std::vector< Double_t > fSave
Array of fNsave function values.
Definition: TF1.h:257
TObjArray
An array of TObjects.
Definition: TObjArray.h:37
TF1::fHistogram
TH1 * fHistogram
! Pointer to histogram used for visualisation
Definition: TF1.h:263
f
#define f(i)
Definition: RSha256.hxx:104
TF1Parameters::SetParameters
void SetParameters(const Double_t *params)
Definition: TF1.h:108
TF1::fNpar
Int_t fNpar
Number of parameters.
Definition: TF1.h:245
TF1::GetMaximum
virtual Double_t GetMaximum(Double_t xmin=0, Double_t xmax=0, Double_t epsilon=1.E-10, Int_t maxiter=100, Bool_t logx=false) const
Returns the maximum value of the function.
Definition: TF1.cxx:1610
TAttFill::SetFillStyle
virtual void SetFillStyle(Style_t fstyle)
Set the fill area style.
Definition: TAttFill.h:39
TAxis::SaveAttributes
virtual void SaveAttributes(std::ostream &out, const char *name, const char *subname)
Save axis attributes as C++ statement(s) on output stream out.
Definition: TAxis.cxx:661
Option_t
const char Option_t
Definition: RtypesCore.h:66
TMath::Max
Short_t Max(Short_t a, Short_t b)
Definition: TMathBase.h:212
ROOT::Math::Minimizer::X
virtual const double * X() const =0
return pointer to X values at the minimum
TF1::GetX
virtual Double_t GetX(Double_t y, Double_t xmin=0, Double_t xmax=0, Double_t epsilon=1.E-10, Int_t maxiter=100, Bool_t logx=false) const
Returns the X value corresponding to the function value fy for (xmin<x<xmax).
Definition: TF1.cxx:1859
TFormula
The Formula class.
Definition: TFormula.h:87
TMath::QuietNaN
Double_t QuietNaN()
Returns a quiet NaN as defined by IEEE 754
Definition: TMath.h:901
Integrator.h
TH1::SetMinimum
virtual void SetMinimum(Double_t minimum=-1111)
Definition: TH1.h:399
ROOT::Math::WrappedTF1::SetParameters
void SetParameters(const double *p)
set parameter values need to call also SetParameters in TF1 in ace some other operations (re-normaliz...
Definition: WrappedTF1.h:90
TF1::fNormalized
Bool_t fNormalized
Normalization option (false by default)
Definition: TF1.h:265
ROOT::Math::IntegratorOneDim::IntegralLow
double IntegralLow(const IGenFunction &f, double b)
evaluate the Integral of a function f over the over the semi-infinite interval (-inf,...
Definition: Integrator.h:296
TF1::fgCurrent
static TF1 * fgCurrent
Definition: TF1.h:307
TF1::SetNpx
virtual void SetNpx(Int_t npx=100)
Set the number of points used to draw the function.
Definition: TF1.cxx:3453
Functor.h
TAxis::SetLimits
virtual void SetLimits(Double_t xmin, Double_t xmax)
Definition: TAxis.h:154
TF1::Integral
virtual Double_t Integral(Double_t a, Double_t b, Double_t epsrel=1.e-12)
IntegralOneDim or analytical integral.
Definition: TF1.cxx:2521
TF1::GetParameters
virtual Double_t * GetParameters() const
Definition: TF1.h:520
TString::Data
const char * Data() const
Definition: TString.h:369
ROOT::v5::TF1Data::fParMax
Double_t * fParMax
Definition: TF1Data.h:49
ROOT::Math::IntegratorMultiDim::Error
double Error() const
return integration error
Definition: IntegratorMultiDim.h:163
ROOT::Math::Minimizer::Minimize
virtual bool Minimize()=0
method to perform the minimization
TF1::fNormIntegral
Double_t fNormIntegral
Integral of the function before being normalized.
Definition: TF1.h:266
ClassImp
#define ClassImp(name)
Definition: Rtypes.h:364
Form
char * Form(const char *fmt,...)
TNamed::GetTitle
virtual const char * GetTitle() const
Returns title of object.
Definition: TNamed.h:48
ROOT::Math::IntegratorMultiDim
User class for performing multidimensional integration.
Definition: IntegratorMultiDim.h:51
TObjString.h
TAttMarker::GetMarkerSize
virtual Size_t GetMarkerSize() const
Return the marker size.
Definition: TAttMarker.h:33
ROOT::Math::Functor1D
Functor1D class for one-dimensional functions.
Definition: Functor.h:493
TF1::GetNdim
virtual Int_t GetNdim() const
Definition: TF1.h:485
TF1::CreateHistogram
virtual TH1 * CreateHistogram()
Definition: TF1.h:449
TF1::GetNpar
virtual Int_t GetNpar() const
Definition: TF1.h:481
TF1::SetParNames
virtual void SetParNames(const char *name0="p0", const char *name1="p1", const char *name2="p2", const char *name3="p3", const char *name4="p4", const char *name5="p5", const char *name6="p6", const char *name7="p7", const char *name8="p8", const char *name9="p9", const char *name10="p10")
Set up to 10 parameter names.
Definition: TF1.cxx:3482
TF1::SetMaximum
virtual void SetMaximum(Double_t maximum=-1111)
Set the maximum value along Y for this function In case the function is already drawn,...
Definition: TF1.cxx:3414
r
ROOT::R::TRInterface & r
Definition: Object.C:4
ROOT::Math::BrentMinimizer1D::SetFunction
void SetFunction(const ROOT::Math::IGenFunction &f, double xlow, double xup)
Sets function to be minimized.
Definition: BrentMinimizer1D.cxx:59
TGraph.h
TF1NormSum
Class adding two functions: c1*f1+c2*f2.
Definition: TF1NormSum.h:19
xmax
float xmax
Definition: THbookFile.cxx:95
ROOT::Math::GaussIntegrator::Integral
double Integral(double a, double b)
Returns Integral of function between a and b.
Definition: GaussIntegrator.cxx:52
TF1::~TF1
virtual ~TF1()
TF1 default destructor.
Definition: TF1.cxx:948
ROOT::Math::RichardsonDerivator::Derivative2
double Derivative2(double x)
Returns the second derivative of the function at point x, computed by Richardson's extrapolation meth...
Definition: RichardsonDerivator.h:172
TObject::Info
virtual void Info(const char *method, const char *msgfmt,...) const
Issue info message.
Definition: TObject.cxx:867
Long64_t
long long Long64_t
Definition: RtypesCore.h:80
ROOT::Math::GaussLegendreIntegrator::GetWeightVectors
void GetWeightVectors(double *x, double *w) const
Returns the arrays x and w containing the abscissa and weight of the Gauss-Legendre n-point quadratur...
Definition: GaussLegendreIntegrator.cxx:51
TObject::Error
virtual void Error(const char *method, const char *msgfmt,...) const
Issue error message.
Definition: TObject.cxx:893
TF1AbsComposition
Definition: TF1AbsComposition.h:16
TF1::GetProb
virtual Double_t GetProb() const
Return the fit probability.
Definition: TF1.cxx:1951
ROOT::Math::BrentMinimizer1D::SetLogScan
void SetLogScan(bool on)
Set a log grid scan (default is equidistant bins) will work only if xlow > 0.
Definition: BrentMinimizer1D.h:133
TAttMarker::Copy
void Copy(TAttMarker &attmarker) const
Copy this marker attributes to a new TAttMarker.
Definition: TAttMarker.cxx:239
TMath::Sqrt
Double_t Sqrt(Double_t x)
Definition: TMath.h:691
TCollection::SetOwner
virtual void SetOwner(Bool_t enable=kTRUE)
Set whether this collection is the owner (enable==true) of its content.
Definition: TCollection.cxx:746
TH1D
1-D histogram with a double per channel (see TH1 documentation)}
Definition: TH1.h:618
ROOT::v5::TF1Data::Streamer
void Streamer(TBuffer &b, Int_t version, UInt_t start, UInt_t count, const TClass *onfile_class=0)
Stream a class object.
Definition: TF1Data_v5.cxx:59
TF1::Derivative3
virtual Double_t Derivative3(Double_t x, Double_t *params=0, Double_t epsilon=0.001) const
Returns the third derivative of the function at point x, computed by Richardson's extrapolation metho...
Definition: TF1.cxx:1238
TF1::Moment
virtual Double_t Moment(Double_t n, Double_t a, Double_t b, const Double_t *params=0, Double_t epsilon=0.000001)
Return nth moment of function between a and b.
Definition: TF1.cxx:3684
TF1::fType
EFType fType
Definition: TF1.h:248
TF1::fIntegral
std::vector< Double_t > fIntegral
! Integral of function binned on fNpx bins
Definition: TF1.h:258
TRandom.h
TStyle.h
ROOT::Math::WrappedMultiFunction
Template class to wrap any C++ callable object implementing operator() (const double * x) in a multi-...
Definition: WrappedFunction.h:154
TVirtualPad::cd
virtual TVirtualPad * cd(Int_t subpadnumber=0)=0
TF1::SetCurrent
static void SetCurrent(TF1 *f1)
Static function setting the current function.
Definition: TF1.cxx:3363
ROOT::Math::IntegratorMultiDim::Status
int Status() const
return the Error Status of the last Integral calculation
Definition: IntegratorMultiDim.h:166
Int_t
int Int_t
Definition: RtypesCore.h:45
TAxis::GetBinCenter
virtual Double_t GetBinCenter(Int_t bin) const
Return center of bin.
Definition: TAxis.cxx:478
TRandom::Uniform
virtual Double_t Uniform(Double_t x1=1)
Returns a uniform deviate on the interval (0, x1).
Definition: TRandom.cxx:672
TF1::GetXmax
virtual Double_t GetXmax() const
Definition: TF1.h:556
RichardsonDerivator.h
TF1::DistancetoPrimitive
virtual Int_t DistancetoPrimitive(Int_t px, Int_t py)
Compute distance from point px,py to a function.
Definition: TF1.cxx:1288
TBrowser.h
TNamed::fName
TString fName
Definition: TNamed.h:32
TObject::AppendPad
virtual void AppendPad(Option_t *option="")
Append graphics object to current pad.
Definition: TObject.cxx:107
ROOT::v5::TF1Data::fParMin
Double_t * fParMin
Definition: TF1Data.h:48
TString::Contains
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
Definition: TString.h:624
ROOT::v5::TF1Data::fType
Int_t fType
Definition: TF1Data.h:42
TF1::TF1FunctorPointer
Definition: TF1.h:227
TH1::SetBinContent
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:9055
TF1::SavePrimitive
virtual void SavePrimitive(std::ostream &out, Option_t *option="")
Save primitive as a C++ statement(s) on output stream out.
Definition: TF1.cxx:3207
x
Double_t x[n]
Definition: legend1.C:17
TString::Length
Ssiz_t Length() const
Definition: TString.h:410
ROOT::Math::RichardsonDerivator
User class for calculating the derivatives of a function.
Definition: RichardsonDerivator.h:55
operator()
TRObject operator()(const T1 &t1) const
Definition: TRFunctionImport__oprtr.h:14
TF1::fXmin
Double_t fXmin
Lower bounds for the range.
Definition: TF1.h:243
TAttMarker::GetMarkerStyle
virtual Style_t GetMarkerStyle() const
Return the marker style.
Definition: TAttMarker.h:32
TColor.h
TF1::GetMinMaxNDim
virtual Double_t GetMinMaxNDim(Double_t *x, Bool_t findmax, Double_t epsilon=0, Int_t maxiter=0) const
Find the minimum of a function of whatever dimension.
Definition: TF1.cxx:1719
TF1::SetParErrors
virtual void SetParErrors(const Double_t *errors)
Set errors for all active parameters when calling this function, the array errors must have at least ...
Definition: TF1.cxx:3504
ROOT::v5::TF1Data::fMaximum
Double_t fMaximum
Definition: TF1Data.h:51
TF1::EAddToList::kNo
@ kNo
TMath::Abs
Short_t Abs(Short_t d)
Definition: TMathBase.h:120
TBuffer
Buffer base class used for serializing objects.
Definition: TBuffer.h:43
TF1::kNotDraw
@ kNotDraw
Definition: TF1.h:326
TF1::DefineNSUMTerm
void DefineNSUMTerm(TObjArray *newFuncs, TObjArray *coeffNames, TString &fullFormula, TString &formula, int termStart, int termEnd, Double_t xmin, Double_t xmax)
Helper functions for NSUM parsing.
Definition: TF1.cxx:877
ROOT::Math::IntegratorOneDimOptions::DefaultIntegratorType
static IntegrationOneDim::Type DefaultIntegratorType()
Definition: IntegratorOptions.cxx:241
TAttLine::SetLineColor
virtual void SetLineColor(Color_t lcolor)
Set the line color.
Definition: TAttLine.h:40
TF1::CalcGaussLegendreSamplingPoints
static void CalcGaussLegendreSamplingPoints(Int_t num, Double_t *x, Double_t *w, Double_t eps=3.0e-11)
Type safe interface (static method) The number of sampling points are taken from the TGraph.
Definition: TF1.cxx:3808
TMath::Prob
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
TObjArray::At
TObject * At(Int_t idx) const
Definition: TObjArray.h:166
kMouseMotion
@ kMouseMotion
Definition: Buttons.h:23
TString::Format
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:2333
BrentRootFinder.h
TF1::SetMinimum
virtual void SetMinimum(Double_t minimum=-1111)
Set the minimum value along Y for this function In case the function is already drawn,...
Definition: TF1.cxx:3427
Factory.h
TColor::SaveColor
static void SaveColor(std::ostream &out, Int_t ci)
Save a color with index > 228 as a C++ statement(s) on output stream out.
Definition: TColor.cxx:2127
TF1::kNotGlobal
@ kNotGlobal
Definition: TF1.h:325
ROOT::v5::TF1Data::fXmin
Double_t fXmin
Definition: TF1Data.h:39
ROOT::Math::RichardsonDerivator::Derivative1
double Derivative1(double x)
Returns the first derivative of the function at point x, computed by Richardson's extrapolation metho...
Definition: RichardsonDerivator.h:116
TString
Basic string class.
Definition: TString.h:136
TH1::Print
virtual void Print(Option_t *option="") const
Print some global quantities for this histogram.
Definition: TH1.cxx:6975
TF1::DerivativeError
static Double_t DerivativeError()
Static function returning the error of the last call to the of Derivative's functions.
Definition: TF1.cxx:1272
MinimizerOptions.h
Bool_t
bool Bool_t
Definition: RtypesCore.h:63
ROOT::Fit::FitResult::NPar
unsigned int NPar() const
total number of parameters (abbreviation)
Definition: FitResult.h:131
ROOT::Math::IntegratorOneDim::GetName
static std::string GetName(IntegrationOneDim::Type)
static function to get a string from the enumeration
Definition: Integrator.cxx:66
ROOT::Math::beta
double beta(double x, double y)
Calculates the beta function.
Definition: SpecFuncMathCore.cxx:111
TObject::InheritsFrom
virtual Bool_t InheritsFrom(const char *classname) const
Returns kTRUE if object inherits from class "classname".
Definition: TObject.cxx:445
v
@ v
Definition: rootcling_impl.cxx:3664
TF1::Paint
virtual void Paint(Option_t *option="")
Paint this function with its current attributes.
Definition: TF1.cxx:2943
ROOT::Math::Minimizer::MinValue
virtual double MinValue() const =0
return minimum function value
b
#define b(i)
Definition: RSha256.hxx:100
TObject::RecursiveRemove
virtual void RecursiveRemove(TObject *obj)
Recursively remove this object from a list.
Definition: TObject.cxx:574
TF1::ComputeCdfTable
Bool_t ComputeCdfTable(Option_t *opt)
Compute the cumulative function at fNpx points between fXmin and fXmax.
Definition: TF1.cxx:2075
ROOT::v5::TF1Data::fChisquare
Double_t fChisquare
Definition: TF1Data.h:46
ROOT::Fit::FitResult::Ndf
unsigned int Ndf() const
Number of degree of freedom.
Definition: FitResult.h:163
ROOT::Math::IntegratorMultiDim::Integral
double Integral(const double *xmin, const double *xmax)
evaluate the integral with the previously given function between xmin[] and xmax[]
Definition: IntegratorMultiDim.h:126
ROOT::Math::Factory::CreateMinimizer
static ROOT::Math::Minimizer * CreateMinimizer(const std::string &minimizerType="", const std::string &algoType="")
static method to create the corrisponding Minimizer given the string Supported Minimizers types are: ...
Definition: Factory.cxx:63
bool
TF1::IntegralOneDim
virtual Double_t IntegralOneDim(Double_t a, Double_t b, Double_t epsrel, Double_t epsabs, Double_t &err)
Return Integral of function between a and b using the given parameter values and relative and absolut...
Definition: TF1.cxx:2611
TF1::GetParLimits
virtual void GetParLimits(Int_t ipar, Double_t &parmin, Double_t &parmax) const
Return limits for parameter ipar.
Definition: TF1.cxx:1936
TString::ReplaceAll
TString & ReplaceAll(const TString &s1, const TString &s2)
Definition: TString.h:692
TF1::SetNDF
virtual void SetNDF(Int_t ndf)
Set the number of degrees of freedom ndf should be the number of points used in a fit - the number of...
Definition: TF1.cxx:3439
ROOT::Fit::FitResult::NFreeParameters
unsigned int NFreeParameters() const
get total number of free parameters
Definition: FitResult.h:134
formula1
Definition: formula1.py:1
AdaptiveIntegratorMultiDim.h
TObjArray::Add
void Add(TObject *obj)
Definition: TObjArray.h:74
TAxis::GetTitle
const char * GetTitle() const
Returns title of object.
Definition: TAxis.h:129
ROOT::Math::IntegrationMultiDim::kADAPTIVE
@ kADAPTIVE
adaptive multi-dimensional integration
Definition: AllIntegrationTypes.h:49
TNamed::fTitle
TString fTitle
Definition: TNamed.h:33
q
float * q
Definition: THbookFile.cxx:89
ROOT::Math::BrentMinimizer1D::Minimize
virtual bool Minimize(int maxIter, double absTol=1.E-8, double relTol=1.E-10)
Find minimum position iterating until convergence specified by the absolute and relative tolerance or...
Definition: BrentMinimizer1D.cxx:87
x1
static const double x1[5]
Definition: RooGaussKronrodIntegrator1D.cxx:346
TF1::fMethodCall
std::unique_ptr< TMethodCall > fMethodCall
! Pointer to MethodCall in case of interpreted function
Definition: TF1.h:264
TF1::GetRange
virtual void GetRange(Double_t *xmin, Double_t *xmax) const
Return range of a generic N-D function.
Definition: TF1.cxx:2275
TF1::GetNumber
virtual Int_t GetNumber() const
Definition: TF1.h:498
TF1::Clone
TObject * Clone(const char *newname=0) const
Make a complete copy of the underlying object.
Definition: TF1.cxx:1059
TROOT.h
TF1::GetRandom
virtual Double_t GetRandom(TRandom *rng=nullptr, Option_t *opt=nullptr)
Return a random number following this function shape.
Definition: TF1.cxx:2186
TF1::SetParameter
virtual void SetParameter(Int_t param, Double_t value)
Definition: TF1.h:634
TF1::SetParameters
virtual void SetParameters(const Double_t *params)
Definition: TF1.h:644
TStyle::GetFuncStyle
Style_t GetFuncStyle() const
Definition: TStyle.h:211
TH1::SetTitle
virtual void SetTitle(const char *title)
See GetStatOverflows for more information.
Definition: TH1.cxx:6678
AnalyticalIntegrals.h
TF1::GradientPar
virtual Double_t GradientPar(Int_t ipar, const Double_t *x, Double_t eps=0.01)
Compute the gradient (derivative) wrt a parameter ipar.
Definition: TF1.cxx:2439
TF1::IntegralFast
virtual Double_t IntegralFast(Int_t num, Double_t *x, Double_t *w, Double_t a, Double_t b, Double_t *params=0, Double_t epsilon=1e-12)
Gauss-Legendre integral, see CalcGaussLegendreSamplingPoints.
Definition: TF1.cxx:2768
TH1::Clone
TObject * Clone(const char *newname=0) const
Make a complete copy of the underlying object.
Definition: TH1.cxx:2740
TString::ToUpper
void ToUpper()
Change string to upper case.
Definition: TString.cxx:1160
ROOT::Math::GaussIntegrator::IntegralLow
double IntegralLow(double b)
Returns Integral of function on a lower semi-infinite interval.
Definition: GaussIntegrator.cxx:66
TF1::SetFitResult
virtual void SetFitResult(const ROOT::Fit::FitResult &result, const Int_t *indpar=0)
Set the result from the fit parameter values, errors, chi2, etc...
Definition: TF1.cxx:3375
TObjString
Collectable string class.
Definition: TObjString.h:28
TF1::IsValid
virtual Bool_t IsValid() const
Return kTRUE if the function is valid.
Definition: TF1.cxx:2872
TF1::GetParNumber
virtual Int_t GetParNumber(const char *name) const
Definition: TF1.h:533
TF1::fNpfits
Int_t fNpfits
Number of points used in the fit.
Definition: TF1.h:249
total
static unsigned int total
Definition: TGWin32ProxyDefs.h:40
BrentMinimizer1D.h
ROOT::v5::TF1Data::fNDF
Int_t fNDF
Definition: TF1Data.h:44
TF1::fNdim
Int_t fNdim
Function dimension.
Definition: TF1.h:246
TNamed::Copy
virtual void Copy(TObject &named) const
Copy this to obj.
Definition: TNamed.cxx:94
TAttLine::Copy
void Copy(TAttLine &attline) const
Copy this line attributes to a new TAttLine.
Definition: TAttLine.cxx:175
ROOT::Math::BrentMinimizer1D::XMinimum
virtual double XMinimum() const
Return current estimate of the position of the minimum.
Definition: BrentMinimizer1D.h:86
TF1Parameters::GetParNumber
Int_t GetParNumber(const char *name) const
Returns the parameter number given a name not very efficient but list of parameters is typically smal...
Definition: TF1.cxx:3828
TF1::SetParError
virtual void SetParError(Int_t ipar, Double_t error)
Set error for parameter number ipar.
Definition: TF1.cxx:3493
TF1::GetYaxis
TAxis * GetYaxis() const
Get y axis of the function.
Definition: TF1.cxx:2405
ROOT::Fit::FitResult::MinFcnValue
double MinFcnValue() const
Return value of the objective function (chi2 or likelihood) used in the fit.
Definition: FitResult.h:120
TF1::fXmax
Double_t fXmax
Upper bounds for the range.
Definition: TF1.h:244
TF1::fAlpha
std::vector< Double_t > fAlpha
! Array alpha. for each bin in x the deconvolution r of fIntegral
Definition: TF1.h:259
ROOT::Math::AdaptiveIntegratorMultiDim::Status
int Status() const
return status of integration
Definition: AdaptiveIntegratorMultiDim.h:149
ROOT::v5::TF1Data::fSave
Double_t * fSave
Definition: TF1Data.h:50
ROOT::Math::ChebyshevPol
Definition: ChebyshevPol.h:129
TArrayD::GetArray
const Double_t * GetArray() const
Definition: TArrayD.h:43
TF1Helper.h
TAttFill::Copy
void Copy(TAttFill &attfill) const
Copy this fill attributes to a new TAttFill.
Definition: TAttFill.cxx:204
ROOT::Math::WrappedTF1
Class to Wrap a ROOT Function class (like TF1) in a IParamFunction interface of one dimensions to be ...
Definition: WrappedTF1.h:39
TBuffer.h
ROOT::TF1Helper::IntegralError
double IntegralError(TF1 *func, Int_t ndim, const double *a, const double *b, const double *params, const double *covmat, double epsilon)
Definition: TF1Helper.cxx:39
TRandom
This is the base class for the ROOT Random number generators.
Definition: TRandom.h:27
ROOT::Math::MinimizerOptions::DefaultMinimizerType
static const std::string & DefaultMinimizerType()
Definition: MinimizerOptions.cxx:92
TFormula::fFormula
TString fFormula
String representing the formula expression.
Definition: TFormula.h:140
TAttLine
Line Attributes class.
Definition: TAttLine.h:18
TMath::Log10
Double_t Log10(Double_t x)
Definition: TMath.h:764
TAxis::GetXmin
Double_t GetXmin() const
Definition: TAxis.h:133
GaussLegendreIntegrator.h
gStyle
R__EXTERN TStyle * gStyle
Definition: TStyle.h:412
TF1::InitStandardFunctions
static void InitStandardFunctions()
Create the basic function objects.
Definition: TF1.cxx:2488
TH1::GetYaxis
TAxis * GetYaxis()
Definition: TH1.h:321
ROOT::v5::TFormula::GetParameters
virtual Double_t * GetParameters() const
Definition: TFormula.h:243
TF1::DrawDerivative
virtual TObject * DrawDerivative(Option_t *option="al")
Draw derivative of this function.
Definition: TF1.cxx:1380
GetVectorizedOption
bool GetVectorizedOption(Option_t *opt)
Definition: TF1.cxx:690
xmin
float xmin
Definition: THbookFile.cxx:95
TF1::Update
virtual void Update()
Called by functions such as SetRange, SetNpx, SetParameters to force the deletion of the associated h...
Definition: TF1.cxx:3630
gROOTMutex
R__EXTERN TVirtualMutex * gROOTMutex
Definition: TROOT.h:61
TF1NormSum::GetParName
const char * GetParName(Int_t ipar) const
Definition: TF1NormSum.h:66
h
#define h(i)
Definition: RSha256.hxx:106
TAttLine::GetLineColor
virtual Color_t GetLineColor() const
Return the line color.
Definition: TAttLine.h:33
TH1::GetMaximumStored
virtual Double_t GetMaximumStored() const
Definition: TH1.h:288
TObject::SetBit
void SetBit(UInt_t f, Bool_t set)
Set or unset the user status bits as specified in f.
Definition: TObject.cxx:696
TF1::GetXaxis
TAxis * GetXaxis() const
Get x axis of the function.
Definition: TF1.cxx:2394
gr
TGraphErrors * gr
Definition: legend1.C:25
TMath::IsNaN
Bool_t IsNaN(Double_t x)
Definition: TMath.h:892
ROOT::v5::TF1Data::fMinimum
Double_t fMinimum
Definition: TF1Data.h:52
TF1::InitArgs
virtual void InitArgs(const Double_t *x, const Double_t *params)
Initialize parameters addresses.
Definition: TF1.cxx:2473
epsilon
REAL epsilon
Definition: triangle.c:617
TAttMarker::SetMarkerColor
virtual void SetMarkerColor(Color_t mcolor=1)
Set the marker color.
Definition: TAttMarker.h:38
a
auto * a
Definition: textangle.C:12
TF1::fMinimum
Double_t fMinimum
Minimum value for plotting.
Definition: TF1.h:252
TNamed
The TNamed class is the base class for all named ROOT classes.
Definition: TNamed.h:29
TAttLine::GetLineStyle
virtual Style_t GetLineStyle() const
Return the line style.
Definition: TAttLine.h:34
TF1::Derivative2
virtual Double_t Derivative2(Double_t x, Double_t *params=0, Double_t epsilon=0.001) const
Returns the second derivative of the function at point x, computed by Richardson's extrapolation meth...
Definition: TF1.cxx:1173
kFALSE
const Bool_t kFALSE
Definition: RtypesCore.h:101
TF1::GetParName
virtual const char * GetParName(Int_t ipar) const
Definition: TF1.h:529
TString::Append
TString & Append(const char *cs)
Definition: TString.h:564
TH1::GetBinCenter
virtual Double_t GetBinCenter(Int_t bin) const
Return bin center for 1D histogram.
Definition: TH1.cxx:8974
ROOT::R::function
void function(const Char_t *name_, T fun, const Char_t *docstring=0)
Definition: RExports.h:151
TNamed::Clone
virtual TObject * Clone(const char *newname="") const
Make a clone of an object using the Streamer facility.
Definition: TNamed.cxx:74
TH1::DistancetoPrimitive
virtual Int_t DistancetoPrimitive(Int_t px, Int_t py)
Compute distance from point px,py to a line.
Definition: TH1.cxx:2811
TF1::CentralMoment
virtual Double_t CentralMoment(Double_t n, Double_t a, Double_t b, const Double_t *params=0, Double_t epsilon=0.000001)
Return nth central moment of function between a and b (i.e the n-th moment around the mean value)
Definition: TF1.cxx:3721
TString::First
Ssiz_t First(char c) const
Find first occurrence of a character c.
Definition: TString.cxx:520
TH1::ExecuteEvent
virtual void ExecuteEvent(Int_t event, Int_t px, Int_t py)
Execute action corresponding to one event.
Definition: TH1.cxx:3246
TH1::SetMaximum
virtual void SetMaximum(Double_t maximum=-1111)
Definition: TH1.h:398
TMath::Power
LongDouble_t Power(LongDouble_t x, LongDouble_t y)
Definition: TMath.h:735
ROOT::Math::GaussIntegrator::IntegralUp
double IntegralUp(double a)
Returns Integral of function on an upper semi-infinite interval.
Definition: GaussIntegrator.cxx:61
ROOT::v5::TFormula::GetExpFormula
virtual TString GetExpFormula(Option_t *option="") const
Reconstruct the formula expression from the internal TFormula member variables.
Definition: TFormula_v5.cxx:3022
TF1::DoCreateHistogram
virtual TH1 * DoCreateHistogram(Double_t xmin, Double_t xmax, Bool_t recreate=kFALSE)
Create histogram with bin content equal to function value computed at the bin center This histogram w...
Definition: TF1.cxx:3042
TF1::Browse
virtual void Browse(TBrowser *b)
Browse.
Definition: TF1.cxx:988
ROOT::Fit::FitResult
class containg the result of the fit and all the related information (fitted parameter values,...
Definition: FitResult.h:47
TF1::SetChisquare
virtual void SetChisquare(Double_t chi2)
Definition: TF1.h:612
ROOT::Math::AdaptiveIntegratorMultiDim::Integral
double Integral(const double *xmin, const double *xmax)
evaluate the integral with the previously given function between xmin[] and xmax[]
Definition: AdaptiveIntegratorMultiDim.h:119
TF1::Copy
virtual void Copy(TObject &f1) const
Copy this F1 to a new F1.
Definition: TF1.cxx:1000
TF1::EFType
EFType
Definition: TF1.h:234
gRandom
R__EXTERN TRandom * gRandom
Definition: TRandom.h:62
TAttMarker
Marker Attributes class.
Definition: TAttMarker.h:19
ROOT::Fit::FitResult::IsEmpty
bool IsEmpty() const
True if a fit result does not exist (even invalid) with parameter values.
Definition: FitResult.h:117
TF1::fgRejectPoint
static Bool_t fgRejectPoint
Definition: TF1.h:305
R__RegisterTF1UpdaterTrigger
int R__RegisterTF1UpdaterTrigger
Definition: TF1.cxx:148
ROOT::Math::BrentMinimizer1D::SetNpx
void SetNpx(int npx)
Set the number of point used to bracket root using a grid.
Definition: BrentMinimizer1D.h:127
ROOT::Math::Minimizer::SetFunction
virtual void SetFunction(const ROOT::Math::IMultiGenFunction &func)=0
set the function to minimize
TH1::GetMinimum
virtual Double_t GetMinimum(Double_t minval=-FLT_MAX) const
Return minimum value larger than minval of bins in the range, unless the value has been overridden by...
Definition: TH1.cxx:8468
ChebyshevPol.h
gDebug
Int_t gDebug
Definition: TROOT.cxx:590
BIT
#define BIT(n)
Definition: Rtypes.h:85
R__LOCKGUARD
#define R__LOCKGUARD(mutex)
Definition: TVirtualMutex.h:104
ROOT::Math::Minimizer::SetTolerance
void SetTolerance(double tol)
set the tolerance
Definition: Minimizer.h:453
TVirtualPad.h
TF1Convolution
Class wrapping convolution of two functions.
Definition: TF1Convolution.h:20
TF1NormSum.h
UInt_t
unsigned int UInt_t
Definition: RtypesCore.h:46
gErrorTF1
static Double_t gErrorTF1
Definition: TF1.cxx:60
TH1::SetDirectory
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:8770
double
double
Definition: Converters.cxx:939
TRandom::Rndm
virtual Double_t Rndm()
Machine independent random number generator.
Definition: TRandom.cxx:552
TAttFill::GetFillStyle
virtual Style_t GetFillStyle() const
Return the fill area style.
Definition: TAttFill.h:31
y
Double_t y[n]
Definition: legend1.C:17
TMath::Infinity
Double_t Infinity()
Returns an infinity as defined by the IEEE standard.
Definition: TMath.h:914
ROOT::Math::BrentRootFinder::SetLogScan
void SetLogScan(bool on)
Set a log grid scan (default is equidistant bins) will work only if xlow > 0.
Definition: BrentRootFinder.h:106
TObject::MakeZombie
void MakeZombie()
Definition: TObject.h:49
TF1::GetZaxis
TAxis * GetZaxis() const
Get z axis of the function. (In case this object is a TF2 or TF3)
Definition: TF1.cxx:2416
TF1::fFunctor
std::unique_ptr< TF1FunctorPointer > fFunctor
! Functor object to wrap any C++ callable object
Definition: TF1.h:267
ROOT::Math::IntegratorOneDim::Integral
double Integral(Function &f, double a, double b)
evaluate the Integral of a function f over the defined interval (a,b)
Definition: Integrator.h:500
TH1::GetMinimumStored
virtual Double_t GetMinimumStored() const
Definition: TH1.h:292
TNamed::SetTitle
virtual void SetTitle(const char *title="")
Set the title of the TNamed.
Definition: TNamed.cxx:164
ROOT::Math::AdaptiveIntegratorMultiDim::NEval
int NEval() const
return number of function evaluations in calculating the integral
Definition: AdaptiveIntegratorMultiDim.h:152
TAttMarker::GetMarkerColor
virtual Color_t GetMarkerColor() const
Return the marker color.
Definition: TAttMarker.h:31
TVirtualMutex.h
TH1::kLogX
@ kLogX
X-axis in log scale.
Definition: TH1.h:167
TObject::Warning
virtual void Warning(const char *method, const char *msgfmt,...) const
Issue warning message.
Definition: TObject.cxx:879
ROOT::Math::Minimizer::SetMaxFunctionCalls
void SetMaxFunctionCalls(unsigned int maxfcn)
set maximum of function calls
Definition: Minimizer.h:447
ROOT::Math::BrentRootFinder::SetNpx
void SetNpx(int npx)
Set the number of point used to bracket root using a grid.
Definition: BrentRootFinder.h:100
ROOT::Math::AdaptiveIntegratorMultiDim
Class for adaptive quadrature integration in multi-dimensions using rectangular regions.
Definition: AdaptiveIntegratorMultiDim.h:84
TF1::fParErrors
std::vector< Double_t > fParErrors
Array of errors of the fNpar parameters.
Definition: TF1.h:254
TF1::fMaximum
Double_t fMaximum
Maximum value for plotting.
Definition: TF1.h:253
TObject::kCanDelete
@ kCanDelete
if object in a list can be deleted
Definition: TObject.h:58
void
typedef void((*Func_t)())
TF1::SetNumberFitPoints
virtual void SetNumberFitPoints(Int_t npfits)
Definition: TF1.h:624
TF1::fBeta
std::vector< Double_t > fBeta
! Array beta. is approximated by x = alpha +beta*r *gamma*r**2
Definition: TF1.h:260
TF1::SetRange
virtual void SetRange(Double_t xmin, Double_t xmax)
Initialize the upper and lower bounds to draw the function.
Definition: TF1.cxx:3539
kHand
@ kHand
Definition: GuiTypes.h:374
TF1::GetSave
virtual Double_t GetSave(const Double_t *x)
Get value corresponding to X in array of fSave values.
Definition: TF1.cxx:2338
unsigned int
TF1::EvalPar
virtual Double_t EvalPar(const Double_t *x, const Double_t *params=0)
Evaluate function with given coordinates and parameters.
Definition: TF1.cxx:1469
TF1Parameters::SetParNames
void SetParNames(const char *name0="p0", const char *name1="p1", const char *name2="p2", const char *name3="p3", const char *name4="p4", const char *name5="p5", const char *name6="p6", const char *name7="p7", const char *name8="p8", const char *name9="p9", const char *name10="p10")
Set parameter names.
Definition: TF1.cxx:3860
TF1::fChisquare
Double_t fChisquare
Function fit chisquare.
Definition: TF1.h:251
ROOT::Math::AdaptiveIntegratorMultiDim::RelError
double RelError() const
return relative error
Definition: AdaptiveIntegratorMultiDim.h:137
ymin
float ymin
Definition: THbookFile.cxx:95
TMath::BinarySearch
Long64_t BinarySearch(Long64_t n, const T *array, T value)
Definition: TMathBase.h:278
ROOT::v5::TF1Data::fXmax
Double_t fXmax
Definition: TF1Data.h:40
ROOT::Math::GaussLegendreIntegrator
User class for performing function integration.
Definition: GaussLegendreIntegrator.h:37
TF1::fParMin
std::vector< Double_t > fParMin
Array of lower limits of the fNpar parameters.
Definition: TF1.h:255
ROOT::Math::IntegratorMultiDimOptions::DefaultIntegratorType
static IntegrationMultiDim::Type DefaultIntegratorType()
Definition: IntegratorOptions.cxx:343
TF1::EAddToList
EAddToList
Add to list behavior.
Definition: TF1.h:220
AnalyticalIntegral
Double_t AnalyticalIntegral(TF1 *f, Double_t a, Double_t b)
Definition: AnalyticalIntegrals.cxx:30
ROOT::Math::IntegratorOneDimOptions::DefaultRelTolerance
static double DefaultRelTolerance()
Definition: IntegratorOptions.cxx:267
TF1Parameters::fParNames
std::vector< std::string > fParNames
Definition: TF1.h:141
TF1::fParams
std::unique_ptr< TF1Parameters > fParams
Pointer to Function parameters object (exists only for not-formula functions)
Definition: TF1.h:269
IntegratorOptions.h
Longptr_t
long Longptr_t
Definition: RtypesCore.h:82
ROOT::Math::BrentMinimizer1D
User class for performing function minimization.
Definition: BrentMinimizer1D.h:73
TAttLine::SetLineWidth
virtual void SetLineWidth(Width_t lwidth)
Set the line width.
Definition: TAttLine.h:43
GaussIntegrator.h
ROOT::Math::IntegratorOneDim::Status
int Status() const
return the Error Status of the last Integral calculation
Definition: Integrator.h:421
ROOT::Math::IBaseFunctionOneDim::Clone
virtual IBaseFunctionOneDim * Clone() const =0
Clone a function.
ROOT::Math::IBaseFunctionOneDim
Interface (abstract class) for generic functions objects of one-dimension Provides a method to evalua...
Definition: IFunction.h:135
ROOT::v5::TF1Data::fParErrors
Double_t * fParErrors
Definition: TF1Data.h:47
TF1::AddToGlobalList
virtual Bool_t AddToGlobalList(Bool_t on=kTRUE)
Add to global list of functions (gROOT->GetListOfFunctions() ) return previous status (true if the fu...
Definition: TF1.cxx:841
f1
TF1 * f1
Definition: legend1.C:11
TF1::SetSavedPoint
virtual void SetSavedPoint(Int_t point, Double_t value)
Restore value of function saved at point.
Definition: TF1.cxx:3553
TString::IsNull
Bool_t IsNull() const
Definition: TString.h:407
ROOT::Math::BrentRootFinder::Solve
bool Solve(int maxIter=100, double absTol=1E-8, double relTol=1E-10)
Returns the X value corresponding to the function value fy for (xmin<x<xmax).
Definition: BrentRootFinder.cxx:63
TF1Convolution::GetParName
const char * GetParName(Int_t ipar) const
Definition: TF1Convolution.h:68
Double_t
double Double_t
Definition: RtypesCore.h:59
TF1::GetParError
virtual Double_t GetParError(Int_t ipar) const
Return value of parameter number ipar.
Definition: TF1.cxx:1926
TF1Data.h
TGraph
A TGraph is an object made of two arrays X and Y with npoints each.
Definition: TGraph.h:41
TVirtualPad
TVirtualPad is an abstract base class for the Pad and Canvas classes.
Definition: TVirtualPad.h:51
TF1::SetTitle
virtual void SetTitle(const char *title="")
Set function title if title has the form "fffffff;xxxx;yyyy", it is assumed that the function title i...
Definition: TF1.cxx:3569
TF1::TF1FunctorPointerImpl
Definition: TF1.h:293
TPluginManager.h
R__ASSERT
#define R__ASSERT(e)
Definition: TError.h:118
ROOT::Math::BrentRootFinder::Root
double Root() const
Returns root value.
Definition: BrentRootFinder.h:109
ROOT::Math::Minimizer
Abstract Minimizer class, defining the interface for the various minimizer (like Minuit2,...
Definition: Minimizer.h:75
BrentMethods.h
TF1.h
TF1::DrawCopy
virtual TF1 * DrawCopy(Option_t *option="") const
Draw a copy of this function with its current attributes.
Definition: TF1.cxx:1358
TF1Updater_t
void(*)(Int_t nobjects, TObject **from, TObject **to) TF1Updater_t
Definition: TF1.cxx:62
ROOT::Math::BrentRootFinder::SetFunction
bool SetFunction(const ROOT::Math::IGenFunction &f, double xlow, double xup)
Sets the function for the rest of the algorithms.
Definition: BrentRootFinder.cxx:39
TF1::TF1
TF1()
TF1 default constructor.
Definition: TF1.cxx:500
TF1::RejectedPoint
static Bool_t RejectedPoint()
See TF1::RejectPoint above.
Definition: TF1.cxx:3674
TF1::Eval
virtual Double_t Eval(Double_t x, Double_t y=0, Double_t z=0, Double_t t=0) const
Evaluate this function.
Definition: TF1.cxx:1440
ROOT::Math::MinimizerOptions::DefaultMinimizerAlgo
static const std::string & DefaultMinimizerAlgo()
Definition: MinimizerOptions.cxx:82
ROOT::Math::GaussIntegrator::Error
double Error() const
Return the estimate of the absolute Error of the last Integral calculation.
Definition: GaussIntegrator.cxx:176
TInterpreter.h
TF1::GetMaximumX
virtual Double_t GetMaximumX(Double_t xmin=0, Double_t xmax=0, Double_t epsilon=1.E-10, Int_t maxiter=100, Bool_t logx=false) const
Returns the X value corresponding to the maximum value of the function.
Definition: TF1.cxx:1651
TF1::Draw
virtual void Draw(Option_t *option="")
Draw this function with its current attributes.
Definition: TF1.cxx:1328
TF1NormSum::GetNpar
Int_t GetNpar() const
Return the number of (non constant) parameters including the coefficients: for 2 functions: c1,...
Definition: TF1NormSum.cxx:363
ROOT::Math::IntegratorMultiDimOptions::DefaultRelTolerance
static double DefaultRelTolerance()
Definition: IntegratorOptions.cxx:370
TAttFill::SetFillColor
virtual void SetFillColor(Color_t fcolor)
Set the fill area color.
Definition: TAttFill.h:37
ROOT::Math::IntegrationOneDim::kGAUSS
@ kGAUSS
simple Gauss integration method with fixed rule
Definition: AllIntegrationTypes.h:34
ROOT::Math::Minimizer::SetVariable
virtual bool SetVariable(unsigned int ivar, const std::string &name, double val, double step)=0
set a new free variable
TF1::GetMinimum
virtual Double_t GetMinimum(Double_t xmin=0, Double_t xmax=0, Double_t epsilon=1.E-10, Int_t maxiter=100, Bool_t logx=false) const
Returns the minimum value of the function on the (xmin, xmax) interval.
Definition: TF1.cxx:1692
ROOT::v5::TF1Data::fNpfits
Int_t fNpfits
Definition: TF1Data.h:43
TObject
Mother of all ROOT objects.
Definition: TObject.h:37
TF1::fFormula
std::unique_ptr< TFormula > fFormula
Pointer to TFormula in case when user define formula.
Definition: TF1.h:268
TF1::fgAddToGlobList
static std::atomic< Bool_t > fgAddToGlobList
Definition: TF1.h:306
TF1::AbsValue
static void AbsValue(Bool_t reject=kTRUE)
Static function: set the fgAbsValue flag.
Definition: TF1.cxx:979
TH1::kIsZoomed
@ kIsZoomed
Bit set when zooming on Y axis.
Definition: TH1.h:168
TH1
TH1 is the base class of all histogram classes in ROOT.
Definition: TH1.h:58
TF1::Derivative
virtual Double_t Derivative(Double_t x, Double_t *params=0, Double_t epsilon=0.001) const
Returns the first derivative of the function at point x, computed by Richardson's extrapolation metho...
Definition: TF1.cxx:1108
TF1Parameters
TF1 Parameters class.
Definition: TF1.h:50
ROOT::Fit::FitResult::Chi2
double Chi2() const
Chi2 fit value in case of likelihood must be computed ?
Definition: FitResult.h:160
TStyle::GetFuncWidth
Width_t GetFuncWidth() const
Definition: TStyle.h:212
ROOT::Math::IBaseFunctionOneDim::DoEval
virtual double DoEval(double x) const =0
implementation of the evaluation function. Must be implemented by derived classes
TF1::fParent
TObject * fParent
! Parent object hooking this function (if one)
Definition: TF1.h:262
TF1Convolution.h
ROOT::Math::GaussIntegrator::SetRelTolerance
virtual void SetRelTolerance(double eps)
Set the desired relative Error.
Definition: GaussIntegrator.h:65
name
char name[80]
Definition: TGX11.cxx:110
TF1Convolution::GetNpar
Int_t GetNpar() const
Definition: TF1Convolution.h:65
TF1::SetParName
virtual void SetParName(Int_t ipar, const char *name)
Set name of parameter number ipar.
Definition: TF1.cxx:3470
TAxis::FindBin
virtual Int_t FindBin(Double_t x)
Find bin number corresponding to abscissa x.
Definition: TAxis.cxx:293
TF1::operator=
TF1 & operator=(const TF1 &rhs)
Operator =.
Definition: TF1.cxx:936
ROOT::Math::IntegratorMultiDimOptions::DefaultNCalls
static unsigned int DefaultNCalls()
Definition: IntegratorOptions.cxx:372
TF1::GetNDF
virtual Int_t GetNDF() const
Return the number of degrees of freedom in the fit the fNDF parameter has been previously computed du...
Definition: TF1.cxx:1885
ROOT::Math::ParamFunctor
ParamFunctorTempl< double > ParamFunctor
Definition: ParamFunctor.h:387
TF1Parameters::fParameters
std::vector< Double_t > fParameters
Definition: TF1.h:140
TF1::DoInitialize
void DoInitialize(EAddToList addToGlobList)
Common initialization of the TF1.
Definition: TF1.cxx:796
ROOT::Math::IntegratorOneDimOptions::DefaultAbsTolerance
static double DefaultAbsTolerance()
Definition: IntegratorOptions.cxx:266
x2
static const double x2[5]
Definition: RooGaussKronrodIntegrator1D.cxx:364
R__SetClonesArrayTF1Updater
bool R__SetClonesArrayTF1Updater(TF1Updater_t func)
Definition: TClonesArray.cxx:146
gPad
#define gPad
Definition: TVirtualPad.h:287
TAttFill::GetFillColor
virtual Color_t GetFillColor() const
Return the fill area color.
Definition: TAttFill.h:30
ROOT::v5::TFormula::GetNdim
virtual Int_t GetNdim() const
Definition: TFormula.h:237
TF1::DefaultAddToGlobalList
static Bool_t DefaultAddToGlobalList(Bool_t on=kTRUE)
Static method to add/avoid to add automatically functions to the global list (gROOT->GetListOfFunctio...
Definition: TF1.cxx:832
ROOT::Math::IntegratorOneDim
User Class for performing numerical integration of a function in one dimension.
Definition: Integrator.h:98
ROOT::Math::IntegratorMultiDimOptions::DefaultAbsTolerance
static double DefaultAbsTolerance()
Definition: IntegratorOptions.cxx:369
TH1::kNoStats
@ kNoStats
Don't draw stats box.
Definition: TH1.h:164
TF1::fGamma
std::vector< Double_t > fGamma
! Array gamma.
Definition: TF1.h:261
GetParameters
void GetParameters(TFitEditor::FuncParams_t &pars, TF1 *func)
Stores the parameters of the given function into pars.
Definition: TFitEditor.cxx:256
WrappedFunction.h
TF1::GetNumberFreeParameters
virtual Int_t GetNumberFreeParameters() const
Return the number of free parameters.
Definition: TF1.cxx:1896
TMethodCall
Method or function calling interface.
Definition: TMethodCall.h:37
IntegratorMultiDim.h
TAttFill
Fill Area Attributes class.
Definition: TAttFill.h:19
TAttLine::GetLineWidth
virtual Width_t GetLineWidth() const
Return the line width.
Definition: TAttLine.h:35
TF1::SetParLimits
virtual void SetParLimits(Int_t ipar, Double_t parmin, Double_t parmax)
Set limits for parameter ipar.
Definition: TF1.cxx:3518
ROOT::Math::BrentRootFinder
Class for finding the root of a one dimensional function using the Brent algorithm.
Definition: BrentRootFinder.h:62
TAttMarker::SetMarkerStyle
virtual void SetMarkerStyle(Style_t mstyle=1)
Set the marker style.
Definition: TAttMarker.h:40
FitResult.h
TF1::IntegralMultiple
virtual Double_t IntegralMultiple(Int_t n, const Double_t *a, const Double_t *b, Int_t maxpts, Double_t epsrel, Double_t epsabs, Double_t &relerr, Int_t &nfnevl, Int_t &ifail)
This function computes, to an attempted specified accuracy, the value of the integral.
Definition: TF1.cxx:2841
TNamed::GetName
virtual const char * GetName() const
Returns name of object.
Definition: TNamed.h:47
ROOT::Math::IntegratorOneDim::IntegralUp
double IntegralUp(const IGenFunction &f, double a)
evaluate the Integral of a function f over the semi-infinite interval (a,+inf)
Definition: Integrator.h:278
TAxis::GetXmax
Double_t GetXmax() const
Definition: TAxis.h:134
ROOT::Fit::FitResult::Error
double Error(unsigned int i) const
parameter error by index
Definition: FitResult.h:186
TF1
1-Dim function class
Definition: TF1.h:213
TArrayD
Array of doubles (64 bits per element).
Definition: TArrayD.h:27
TF1::TermCoeffLength
int TermCoeffLength(TString &term)
Definition: TF1.cxx:918
TF1::GetQuantiles
virtual Int_t GetQuantiles(Int_t nprobSum, Double_t *q, const Double_t *probSum)
Compute Quantiles for density distribution of this function.
Definition: TF1.cxx:1988
Class
void Class()
Definition: Class.C:29
TString::ToLower
void ToLower()
Change string to lower-case.
Definition: TString.cxx:1147
TF1::DrawIntegral
virtual TObject * DrawIntegral(Option_t *option="al")
Draw integral of this function.
Definition: TF1.cxx:1405
TH1::GetXaxis
TAxis * GetXaxis()
Get the behaviour adopted by the object about the statoverflows. See EStatOverflows for more informat...
Definition: TH1.h:320
ROOT::Math::ParamFunctorTempl
Param Functor class for Multidimensional functions.
Definition: ParamFunctor.h:273
TF1::GetParameter
virtual Double_t GetParameter(Int_t ipar) const
Definition: TF1.h:512
TAttLine::SetLineStyle
virtual void SetLineStyle(Style_t lstyle)
Set the line style.
Definition: TAttLine.h:42
TH1::GetMaximum
virtual Double_t GetMaximum(Double_t maxval=FLT_MAX) const
Return maximum value smaller than maxval of bins in the range, unless the value has been overridden b...
Definition: TH1.cxx:8383
ROOT::Fit::FitResult::Errors
const std::vector< double > & Errors() const
parameter errors (return st::vector)
Definition: FitResult.h:169
ROOT::v5::TF1Data
Definition: TF1Data.h:37
TF1::Save
virtual void Save(Double_t xmin, Double_t xmax, Double_t ymin, Double_t ymax, Double_t zmin, Double_t zmax)
Save values of function in array fSave.
Definition: TF1.cxx:3154
TF1::fNpx
Int_t fNpx
Number of points used for the graphical representation.
Definition: TF1.h:247
TH1.h
TF1::fComposition
std::unique_ptr< TF1AbsComposition > fComposition
Pointer to composition (NSUM or CONV)
Definition: TF1.h:270
ROOT::Math::RichardsonDerivator::Derivative3
double Derivative3(double x)
Returns the third derivative of the function at point x, computed by Richardson's extrapolation metho...
Definition: RichardsonDerivator.h:211
TF1::GetChisquare
Double_t GetChisquare() const
Definition: TF1.h:444
ROOT::Math::BrentMinimizer1D::FValMinimum
virtual double FValMinimum() const
Return function value at current estimate of the minimum.
Definition: BrentMinimizer1D.cxx:78
ROOT
tbb::task_arena is an alias of tbb::interface7::task_arena, which doesn't allow to forward declare tb...
Definition: EExecutionPolicy.hxx:4
TMath::E
constexpr Double_t E()
Base of natural log:
Definition: TMath.h:96
ROOT::Math::GaussIntegrator
User class for performing function integration.
Definition: GaussIntegrator.h:40
TF1::FixParameter
virtual void FixParameter(Int_t ipar, Double_t value)
Fix the value of a parameter The specified value will be used in a fit operation.
Definition: TF1.cxx:1553
Math
Namespace for new Math classes and functions.
TF1::IntegralError
virtual Double_t IntegralError(Double_t a, Double_t b, const Double_t *params=0, const Double_t *covmat=0, Double_t epsilon=1.E-2)
Return Error on Integral of a parametric function between a and b due to the parameter uncertainties ...
Definition: TF1.cxx:2698
TF1NormSum::GetParameters
std::vector< double > GetParameters() const
Return array of parameters.
Definition: TF1NormSum.cxx:291
TH1::Paint
virtual void Paint(Option_t *option="")
Control routine to paint any kind of histograms.
Definition: TH1.cxx:6155
TMath.h
fw3dlego::xbins
const double xbins[xbins_n]
Definition: collection_proxies.C:48
ROOT::Math::RichardsonDerivator::Error
double Error() const
Returns the estimate of the absolute Error of the last derivative calculation.
Definition: RichardsonDerivator.h:83
WrappedTF1.h
ROOT::Math::GaussIntegrator::Status
int Status() const
return the status of the last integration - 0 in case of success
Definition: GaussIntegrator.cxx:179
gROOT
#define gROOT
Definition: TROOT.h:406
int
TF1::Print
virtual void Print(Option_t *option="") const
Print TNamed name and title.
Definition: TF1.cxx:2887
TF1::fParMax
std::vector< Double_t > fParMax
Array of upper limits of the fNpar parameters.
Definition: TF1.h:256
TF1::GetXmin
virtual Double_t GetXmin() const
Definition: TF1.h:552
TF1::ReleaseParameter
virtual void ReleaseParameter(Int_t ipar)
Release parameter number ipar If used in a fit, the parameter can vary freely.
Definition: TF1.cxx:3144
TMethodCall.h
g
#define g(i)
Definition: RSha256.hxx:105