G4INCL::RootFinder Class Reference

#include <G4INCLRootFinder.hh>


Static Public Member Functions

static G4bool solve (RootFunctor const *const f, const G4double x0)
 Numerically solve a one-dimensional equation.
static std::pair< G4double,
G4double > const & 
getSolution ()
 Get the solution of the last call to solve().

Protected Member Functions

 RootFinder ()
 ~RootFinder ()


Detailed Description

Definition at line 64 of file G4INCLRootFinder.hh.


Constructor & Destructor Documentation

G4INCL::RootFinder::RootFinder (  )  [inline, protected]

Definition at line 108 of file G4INCLRootFinder.hh.

00108 {};

G4INCL::RootFinder::~RootFinder (  )  [inline, protected]

Definition at line 109 of file G4INCLRootFinder.hh.

00109 {};


Member Function Documentation

static std::pair<G4double,G4double> const& G4INCL::RootFinder::getSolution (  )  [inline, static]

Get the solution of the last call to solve().

Returns:
the solution, as an (x,y) pair

Definition at line 83 of file G4INCLRootFinder.hh.

Referenced by G4INCL::InteractionAvatar::enforceEnergyConservation().

00083 { return RootFinder::solution; }

G4bool G4INCL::RootFinder::solve ( RootFunctor const *const   f,
const G4double  x0 
) [static]

Numerically solve a one-dimensional equation.

Numerically solves the equation f(x)==0. This implementation uses the false-position method.

If a root is found, it can be retrieved using the getSolution() method,

Parameters:
f pointer to a RootFunctor
x0 initial value of the function argument
Returns:
true if a root was found

Definition at line 58 of file G4INCLRootFinder.cc.

References G4INCL::RootFunctor::cleanUp(), G4INCL::Math::sign(), and WARN.

Referenced by G4INCL::InteractionAvatar::enforceEnergyConservation().

00058                                                                          {
00059     // If we already have the solution, do nothing
00060     const G4double y0 = (*f)(x0);
00061     if( std::abs(y0) < toleranceY ) {
00062       solution = std::make_pair(x0,y0);
00063       return true;
00064     }
00065 
00066     // Bracket the root and set the initial values
00067     std::pair<G4double,G4double> bracket = bracketRoot(f,x0);
00068     G4double x1 = bracket.first;
00069     G4double x2 = bracket.second;
00070     // If x1>x2, it means that we could not bracket the root. Return false.
00071     if(x1>x2) {
00072       // Maybe zero is a good solution?
00073       G4double y_at_zero = (*f)(0.);
00074       if(std::abs(y_at_zero)<=toleranceY) {
00075         f->cleanUp(true);
00076         solution = std::make_pair(0.,y_at_zero);
00077         return true;
00078       } else {
00079         WARN("Root-finding algorithm could not bracket the root." << std::endl);
00080         f->cleanUp(false);
00081         return false;
00082       }
00083     }
00084 
00085     G4double y1 = (*f)(x1);
00086     G4double y2 = (*f)(x2);
00087     G4double x = x1;
00088     G4double y = y1;
00089 
00090     /* ********************************
00091      * Start of the false-position loop
00092      * ********************************/
00093 
00094     // Keep track of the last updated interval end (-1=left, 1=right)
00095     G4int lastUpdated = 0;
00096 
00097     for(G4int iterations=0; std::abs(y) > toleranceY; iterations++) {
00098 
00099       if(iterations > maxIterations) {
00100         WARN("Root-finding algorithm did not converge." << std::endl);
00101         f->cleanUp(false);
00102         return false;
00103       }
00104 
00105       // Estimate the root position by linear interpolation
00106       x = (y1*x2-y2*x1)/(y1-y2);
00107 
00108       // Update the value of the function
00109       y = (*f)(x);
00110 
00111       // Update the bracketing interval
00112       if(Math::sign(y) == Math::sign(y1)) {
00113         x1=x;
00114         y1=y;
00115         if(lastUpdated==-1) y2 *= 0.5;
00116         lastUpdated = -1;
00117       } else {
00118         x2=x;
00119         y2=y;
00120         if(lastUpdated==1) y1 *= 0.5;
00121         lastUpdated = 1;
00122       }
00123     }
00124 
00125     /* ******************************
00126      * End of the false-position loop
00127      * ******************************/
00128 
00129     solution = std::make_pair(x,y);
00130     f->cleanUp(true);
00131     return true;
00132   }


The documentation for this class was generated from the following files:
Generated on Mon May 27 17:54:09 2013 for Geant4 by  doxygen 1.4.7