// @(#)root/mathcore:$Id$
// Authors: David Gonzalez Maline    01/2008

/**********************************************************************
 *                                                                    *
 * Copyright (c) 2006 , LCG ROOT MathLib Team                         *
 *                                                                    *
 * This library is free software; you can redistribute it and/or      *
 * modify it under the terms of the GNU General Public License        *
 * as published by the Free Software Foundation; either version 2     *
 * of the License, or (at your option) any later version.             *
 *                                                                    *
 * This library is distributed in the hope that it will be useful,    *
 * but WITHOUT ANY WARRANTY; without even the implied warranty of     *
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU   *
 * General Public License for more details.                           *
 *                                                                    *
 * You should have received a copy of the GNU General Public License  *
 * along with this library (see file COPYING); if not, write          *
 * to the Free Software Foundation, Inc., 59 Temple Place, Suite      *
 * 330, Boston, MA 02111-1307 USA, or contact the author.             *
 *                                                                    *
 **********************************************************************/

// Header for the RootFinder
//
// Created by: David Gonzalez Maline  : Wed Jan 21 2008
//

#ifndef ROOT_Math_BrentRootFinder
#define ROOT_Math_BrentRootFinder

#ifndef ROOT_Math_IFunctionfwd
#include "Math/IFunctionfwd.h"
#endif

#ifndef ROOT_Math_IRootFinderMethod
#include "Math/IRootFinderMethod.h"
#endif

namespace ROOT {
namespace Math {

//___________________________________________________________________________________________
/**
   Class for finding the root of a one dimensional function using the Brent algorithm.
   It will use the Brent Method for finding function roots in a given interval.
   First, a grid search is used to bracket the root value
   with the a step size = (xmax-xmin)/npx. The step size
   can be controlled via the SetNpx() function. A default value of npx = 100 is used.
   The default value con be changed using the static method SetDefaultNpx.
   If the function is unimodal or if its extrema are far apart, setting the fNpx to
   a small value speeds the algorithm up many times.
   Then, Brent's method is applied on the bracketed interval.
   It will use the Brent Method for finding function roots in a given interval.
   If the Brent method fails to converge the bracketing is repeted on the latest best estimate of the
   interval. The procedure is repeted with a maximum value (default =10) which can be set for all
   BrentRootFinder classes with the method SetDefaultNSearch

   This class is implemented from TF1::GetX() method.

   @ingroup RootFinders

 */

   class BrentRootFinder: public IRootFinderMethod {
   public:


      /** Default Constructor. */
      BrentRootFinder();


      /** Default Destructor. */
      virtual ~BrentRootFinder() {}


      /** Set function to solve and the interval in where to look for the root.

          \@param f Function to be minimized.
          \@param xlow Lower bound of the search interval.
          \@param xup Upper bound of the search interval.
      */
      using IRootFinderMethod::SetFunction;
      bool SetFunction(const ROOT::Math::IGenFunction& f, double xlow, double xup);


      /** Returns the X value corresponding to the function value fy for (xmin<x<xmax).
          Method:
          First, the grid search is used to bracket the maximum
          with the step size = (xmax-xmin)/fNpx. This way, the step size
          can be controlled via the SetNpx() function. If the function is
          unimodal or if its extrema are far apart, setting the fNpx to
          a small value speeds the algorithm up many times.
          Then, Brent's method is applied on the bracketed interval.

          \@param maxIter maximum number of iterations.
          \@param absTol desired absolute error in the minimum position.
          \@param absTol desired relative error in the minimum position.
      */
      bool Solve(int maxIter = 100, double absTol = 1E-8, double relTol = 1E-10);

      /** Set the number of point used to bracket root using a grid */
      void SetNpx(int npx) { fNpx = npx; }

      /**
          Set a log grid scan (default is equidistant bins)
          will work only if xlow > 0
      */
      void SetLogScan(bool on) { fLogScan = on; }

      /** Returns root value. Need to call first Solve(). */
      double Root() const { return fRoot; }

      /** Returns status of last estimate. If = 0 is OK */
      int Status() const { return fStatus; }

      /** Return number of iteration used to find minimum */
      int Iterations() const { return fNIter; }

      /** Return name of root finder algorithm ("BrentRootFinder"). */
      const char* Name() const;

      // static function used to modify the default parameters

      /** set number of default Npx used at construction time (when SetNpx is not called)
          Default value is 100
       */
      static void SetDefaultNpx(int npx);

      /** set number of  times the bracketing search in combination with is done to find a good interval
          Default value is 10
       */
      static void SetDefaultNSearch(int n);


   private:

      const IGenFunction* fFunction; // Pointer to the function.
      bool fLogScan;                 // flag to control usage of a log scan
      int fNIter;                    // Number of iterations needed for the last estimation.
      int fNpx;                      // Number of points to bracket root with initial grid (def is 100)
      int fStatus;                   // Status of code of the last estimate
      double fXMin;                  // Lower bound of the search interval.
      double fXMax;                  // Upper bound of the search interval
      double fRoot;                  // Current stimation of the function root.
   };

} // namespace Math
} // namespace ROOT

#endif /* ROOT_Math_BrentRootFinder */
 BrentRootFinder.h:1
 BrentRootFinder.h:2
 BrentRootFinder.h:3
 BrentRootFinder.h:4
 BrentRootFinder.h:5
 BrentRootFinder.h:6
 BrentRootFinder.h:7
 BrentRootFinder.h:8
 BrentRootFinder.h:9
 BrentRootFinder.h:10
 BrentRootFinder.h:11
 BrentRootFinder.h:12
 BrentRootFinder.h:13
 BrentRootFinder.h:14
 BrentRootFinder.h:15
 BrentRootFinder.h:16
 BrentRootFinder.h:17
 BrentRootFinder.h:18
 BrentRootFinder.h:19
 BrentRootFinder.h:20
 BrentRootFinder.h:21
 BrentRootFinder.h:22
 BrentRootFinder.h:23
 BrentRootFinder.h:24
 BrentRootFinder.h:25
 BrentRootFinder.h:26
 BrentRootFinder.h:27
 BrentRootFinder.h:28
 BrentRootFinder.h:29
 BrentRootFinder.h:30
 BrentRootFinder.h:31
 BrentRootFinder.h:32
 BrentRootFinder.h:33
 BrentRootFinder.h:34
 BrentRootFinder.h:35
 BrentRootFinder.h:36
 BrentRootFinder.h:37
 BrentRootFinder.h:38
 BrentRootFinder.h:39
 BrentRootFinder.h:40
 BrentRootFinder.h:41
 BrentRootFinder.h:42
 BrentRootFinder.h:43
 BrentRootFinder.h:44
 BrentRootFinder.h:45
 BrentRootFinder.h:46
 BrentRootFinder.h:47
 BrentRootFinder.h:48
 BrentRootFinder.h:49
 BrentRootFinder.h:50
 BrentRootFinder.h:51
 BrentRootFinder.h:52
 BrentRootFinder.h:53
 BrentRootFinder.h:54
 BrentRootFinder.h:55
 BrentRootFinder.h:56
 BrentRootFinder.h:57
 BrentRootFinder.h:58
 BrentRootFinder.h:59
 BrentRootFinder.h:60
 BrentRootFinder.h:61
 BrentRootFinder.h:62
 BrentRootFinder.h:63
 BrentRootFinder.h:64
 BrentRootFinder.h:65
 BrentRootFinder.h:66
 BrentRootFinder.h:67
 BrentRootFinder.h:68
 BrentRootFinder.h:69
 BrentRootFinder.h:70
 BrentRootFinder.h:71
 BrentRootFinder.h:72
 BrentRootFinder.h:73
 BrentRootFinder.h:74
 BrentRootFinder.h:75
 BrentRootFinder.h:76
 BrentRootFinder.h:77
 BrentRootFinder.h:78
 BrentRootFinder.h:79
 BrentRootFinder.h:80
 BrentRootFinder.h:81
 BrentRootFinder.h:82
 BrentRootFinder.h:83
 BrentRootFinder.h:84
 BrentRootFinder.h:85
 BrentRootFinder.h:86
 BrentRootFinder.h:87
 BrentRootFinder.h:88
 BrentRootFinder.h:89
 BrentRootFinder.h:90
 BrentRootFinder.h:91
 BrentRootFinder.h:92
 BrentRootFinder.h:93
 BrentRootFinder.h:94
 BrentRootFinder.h:95
 BrentRootFinder.h:96
 BrentRootFinder.h:97
 BrentRootFinder.h:98
 BrentRootFinder.h:99
 BrentRootFinder.h:100
 BrentRootFinder.h:101
 BrentRootFinder.h:102
 BrentRootFinder.h:103
 BrentRootFinder.h:104
 BrentRootFinder.h:105
 BrentRootFinder.h:106
 BrentRootFinder.h:107
 BrentRootFinder.h:108
 BrentRootFinder.h:109
 BrentRootFinder.h:110
 BrentRootFinder.h:111
 BrentRootFinder.h:112
 BrentRootFinder.h:113
 BrentRootFinder.h:114
 BrentRootFinder.h:115
 BrentRootFinder.h:116
 BrentRootFinder.h:117
 BrentRootFinder.h:118
 BrentRootFinder.h:119
 BrentRootFinder.h:120
 BrentRootFinder.h:121
 BrentRootFinder.h:122
 BrentRootFinder.h:123
 BrentRootFinder.h:124
 BrentRootFinder.h:125
 BrentRootFinder.h:126
 BrentRootFinder.h:127
 BrentRootFinder.h:128
 BrentRootFinder.h:129
 BrentRootFinder.h:130
 BrentRootFinder.h:131
 BrentRootFinder.h:132
 BrentRootFinder.h:133
 BrentRootFinder.h:134
 BrentRootFinder.h:135
 BrentRootFinder.h:136
 BrentRootFinder.h:137
 BrentRootFinder.h:138
 BrentRootFinder.h:139
 BrentRootFinder.h:140
 BrentRootFinder.h:141
 BrentRootFinder.h:142
 BrentRootFinder.h:143
 BrentRootFinder.h:144
 BrentRootFinder.h:145
 BrentRootFinder.h:146
 BrentRootFinder.h:147
 BrentRootFinder.h:148
 BrentRootFinder.h:149
 BrentRootFinder.h:150
 BrentRootFinder.h:151
 BrentRootFinder.h:152