Import Geant4 10.7.0.beta source tree

This commit is contained in:
Gabriele Cosmo
2020-06-26 10:23:25 +02:00
parent c02c370437
commit 67ba86d073
1871 changed files with 174422 additions and 131884 deletions
@@ -23,7 +23,7 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4AnalyticalPolSolver
//
// Class description:
//
@@ -50,27 +50,23 @@
// sum_{k=0:n} p[k] x^(n-k) = 0
// Assumes p[0] != 0. (< or > 0) (overflows otherwise)
// --------------------------- HISTORY --------------------------------------
//
// 13.05.05 V.Grichine ( Vladimir.Grichine@cern.ch )
// First implementation in C++
// Author: V.Grichine, 13.05.2005
// --------------------------------------------------------------------
#ifndef G4AN_POL_SOLVER_HH
#define G4AN_POL_SOLVER_HH
#define G4AN_POL_SOLVER_HH 1
#include "G4Types.hh"
#include "G4Types.hh"
class G4AnalyticalPolSolver
class G4AnalyticalPolSolver
{
public: // with description
public:
G4AnalyticalPolSolver();
~G4AnalyticalPolSolver();
G4AnalyticalPolSolver();
~G4AnalyticalPolSolver();
G4int QuadRoots( G4double p[5], G4double r[3][5]);
G4int CubicRoots( G4double p[5], G4double r[3][5]);
G4int BiquadRoots( G4double p[5], G4double r[3][5]);
G4int QuarticRoots( G4double p[5], G4double r[3][5]);
G4int QuadRoots(G4double p[5], G4double r[3][5]);
G4int CubicRoots(G4double p[5], G4double r[3][5]);
G4int BiquadRoots(G4double p[5], G4double r[3][5]);
G4int QuarticRoots(G4double p[5], G4double r[3][5]);
};
#endif
@@ -23,158 +23,81 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4ChebyshevApproximation
//
// Class description:
//
// Class creating the Chebyshev approximation for a function pointed by fFunction
// data member. The Chebyshev polinom approximation provides an efficient evaluation
// of minimax polynomial, which (among all polynomials of the same degree) has the
// smallest maximum deviation from the true function.
// The methods based mainly on recommendations given in the book : An introduction to
// NUMERICAL METHODS IN C++, B.H. Flowers, Claredon Press, Oxford, 1995
//
// ------------------------- MEMBER DATA ------------------------------------
//
// function fFunction - pointer to a function considered
// G4int fNumber - number of Chebyshev coefficients
// G4double* fChebyshevCof - array of Chebyshev coefficients
// G4double fMean = (a+b)/2 - mean point of interval
// G4double fDiff = (b-a)/2 - half of the interval value
//
// ------------------------ CONSTRUCTORS ----------------------------------
//
// Constructor for initialisation of the class data members. It creates the array
// fChebyshevCof[0,...,fNumber-1], fNumber = n ; which consists of Chebyshev
// coefficients describing the function pointed by pFunction. The values a and b
// fixe the interval of validity of Chebyshev approximation.
//
// G4ChebyshevApproximation( function pFunction,
// G4int n,
// G4double a,
// G4double b )
//
// Class creating the Chebyshev approximation for a function pointed by
// fFunction data member. The Chebyshev polinom approximation provides an
// efficient evaluation of minimax polynomial, which (among all polynomials of
// the same degree) has the smallest maximum deviation from the true function.
// The methods based mainly on recommendations given in the book : An
// introduction to NUMERICAL METHODS IN C++, B.H. Flowers, Claredon Press,
// Oxford, 1995
// Author: V.Grichine, 24.04.1997
// --------------------------------------------------------------------
//
// Constructor for creation of Chebyshev coefficients for m-derivative
// from pFunction. The value of m ! MUST BE ! < n , because the result
// array of fChebyshevCof will be of (n-m) size. There is a definite dependence
// between the proper selection of n, m, a and b values to get better accuracy
// of the derivative value.
//
// G4ChebyshevApproximation( function pFunction,
// G4int n,
// G4int m,
// G4double a,
// G4double b )
//
// ------------------------------------------------------
//
// Constructor for creation of Chebyshev coefficients for integral
// from pFunction.
//
// G4ChebyshevApproximation( function pFunction,
// G4double a,
// G4double b,
// G4int n )
//
// ---------------------------------------------------------------
//
// Destructor deletes the array of Chebyshev coefficients
//
// ~G4ChebyshevApproximation()
//
// ----------------------------- METHODS ----------------------------------
//
// Access function for Chebyshev coefficients
//
// G4double GetChebyshevCof(G4int number) const
//
// --------------------------------------------------------------
//
// Evaluate the value of fFunction at the point x via the Chebyshev coefficients
// fChebyshevCof[0,...,fNumber-1]
//
// G4double ChebyshevEvaluation(G4double x) const
//
// ------------------------------------------------------------------
//
// Returns the array derCof[0,...,fNumber-2], the Chebyshev coefficients of the
// derivative of the function whose coefficients are fChebyshevCof
//
// void DerivativeChebyshevCof(G4double derCof[]) const
//
// ------------------------------------------------------------------------
//
// This function produces the array integralCof[0,...,fNumber-1] , the Chebyshev
// coefficients of the integral of the function whose coefficients are
// fChebyshevCof. The constant of integration is set so that the integral vanishes
// at the point (fMean - fDiff)
//
// void IntegralChebyshevCof(G4double integralCof[]) const
// --------------------------- HISTORY --------------------------------------
//
// 24.04.97 V.Grichine ( Vladimir.Grichine@cern.ch )
#ifndef G4CHEBYSHEVAPPROXIMATION_HH
#define G4CHEBYSHEVAPPROXIMATION_HH
#define G4CHEBYSHEVAPPROXIMATION_HH 1
#include "globals.hh"
typedef G4double (*function)(G4double) ;
typedef G4double (*function)(G4double);
class G4ChebyshevApproximation
{
public: // with description
public:
G4ChebyshevApproximation(function pFunction, G4int n, G4double a, G4double b);
// Constructor for creation of Chebyshev coefficients for m-derivative
// from pFunction. The value of m ! MUST BE ! < n , because the result
// array of fChebyshevCof will be of (n-m) size.
// It creates the array fChebyshevCof[0,...,fNumber-1], fNumber = n ;
// which consists of Chebyshev coefficients describing the function pointed
// by pFunction. The values a and b fixe the interval of validity of
// Chebyshev approximation.
G4ChebyshevApproximation( function pFunction,
G4int n,
G4double a,
G4double b ) ;
//
// Constructor for creation of Chebyshev coefficients for m-derivative
// from pFunction. The value of m ! MUST BE ! < n , because the result
// array of fChebyshevCof will be of (n-m) size.
G4ChebyshevApproximation(function pFunction, G4int n, G4int m, G4double a,
G4double b);
// Constructor for creation of Chebyshev coefficients for m-derivative
// from pFunction. The value of m ! MUST BE ! < n , because the result
// array of fChebyshevCof will be of (n-m) size. There is a definite
// dependence between the proper selection of n, m, a and b values to get
// better accuracy of the derivative value.
G4ChebyshevApproximation( function pFunction,
G4int n,
G4int m,
G4double a,
G4double b ) ;
//
// Constructor for creation of Chebyshev coefficients for integral
// from pFunction.
G4ChebyshevApproximation(function pFunction, G4double a, G4double b, G4int n);
// Constructor for creation of Chebyshev coefficients for integral
// from pFunction.
G4ChebyshevApproximation( function pFunction,
G4double a,
G4double b,
G4int n ) ;
~G4ChebyshevApproximation();
// Destructor deletes the array of Chebyshev coefficients
~G4ChebyshevApproximation() ;
// Access functions
G4double GetChebyshevCof(G4int number) const ;
// Methods
G4ChebyshevApproximation(const G4ChebyshevApproximation&) = delete;
G4ChebyshevApproximation& operator=(const G4ChebyshevApproximation&) = delete;
// Copy constructor and assignment operator not allowed.
G4double ChebyshevEvaluation(G4double x) const ;
void DerivativeChebyshevCof(G4double derCof[]) const ;
void IntegralChebyshevCof(G4double integralCof[]) const ;
private:
G4double GetChebyshevCof(G4int number) const;
// Access function for Chebyshev coefficients
G4ChebyshevApproximation(const G4ChebyshevApproximation&);
G4ChebyshevApproximation& operator=(const G4ChebyshevApproximation&);
G4double ChebyshevEvaluation(G4double x) const;
// Evaluate the value of fFunction at the point x via the Chebyshev
// coefficients fChebyshevCof[0,...,fNumber-1]
private:
void DerivativeChebyshevCof(G4double derCof[]) const;
// Returns the array derCof[0,...,fNumber-2], the Chebyshev coefficients
// of the derivative of the function whose coefficients are fChebyshevCof
function fFunction ;
G4int fNumber ;
G4double* fChebyshevCof ;
G4double fMean ;
G4double fDiff ;
void IntegralChebyshevCof(G4double integralCof[]) const;
// This function produces the array integralCof[0,...,fNumber-1] , the
// Chebyshev coefficients of the integral of the function whose coefficients
// are fChebyshevCof. The constant of integration is set so that the integral
// vanishes at the point (fMean - fDiff)
private:
function fFunction; // pointer to a function considered
G4int fNumber; // number of Chebyshev coefficients
G4double* fChebyshevCof; // array of Chebyshev coefficients
G4double fMean; // (a+b)/2 - mean point of interval
G4double fDiff; // (b-a)/2 - half of the interval value
};
#endif
@@ -23,7 +23,7 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4ConvergenceTester
//
// Class description:
//
@@ -37,141 +37,183 @@
// CHAPTER 2. GEOMETRY, DATA, PHYSICS, AND MATHEMATICS
// VI. ESTIMATION OF THE MONTE CARLO PRECISION
//
// Positives numbers are assumed for input values
// Positive numbers are assumed for input values
// Author: Tatsumi Koi (SLAC/SCCS)
//
// --------------------------------------------------------------------
#ifndef G4ConvergenceTester
#define G4ConvergenceTester_h 1
#ifndef G4ConvergenceTester_hh
#define G4ConvergenceTester_hh 1
#include "G4SimplexDownhill.hh"
#include "G4Timer.hh"
#include "globals.hh"
#include <map>
#include <vector>
class G4ConvergenceTester
class G4ConvergenceTester
{
public:
public:
G4ConvergenceTester(G4String theName = "NONAME");
~G4ConvergenceTester();
G4ConvergenceTester(G4double);
G4ConvergenceTester( G4String theName="NONAME" );
~G4ConvergenceTester();
G4ConvergenceTester( G4double );
void AddScore(G4double);
public:
inline G4ConvergenceTester& operator+=(G4double val)
{
this->AddScore(val);
return *this;
}
void AddScore( G4double );
// default to G4cout but can redirected to another ostream
void ShowHistory(std::ostream& out = G4cout);
void ShowResult(std::ostream& out = G4cout);
G4ConvergenceTester& operator+=(G4double val)
{ this->AddScore(val); return *this; }
inline G4double GetValueOfMinimizingFunction(std::vector<G4double> x)
{
return slope_fitting_function(x);
}
// default to G4cout but can redirected to another ostream
void ShowHistory(std::ostream& out = G4cout);
void ShowResult(std::ostream& out = G4cout);
public:
void ComputeStatistics() { calStat(); }
// Public function to explicitly calculate statistics
inline G4double GetValueOfMinimizingFunction( std::vector<G4double> x )
{ return slope_fitting_function( x ); }
// All accessors check to make sure value is current before returning
private:
inline G4double GetMean()
{
CheckIsUpdated();
return mean;
}
inline G4double GetStandardDeviation()
{
CheckIsUpdated();
return sd;
}
inline G4double GetVariance()
{
CheckIsUpdated();
return var;
}
inline G4double GetR()
{
CheckIsUpdated();
return r;
}
inline G4double GetEfficiency()
{
CheckIsUpdated();
return efficiency;
}
inline G4double GetR2eff()
{
CheckIsUpdated();
return r2eff;
}
inline G4double GetR2int()
{
CheckIsUpdated();
return r2int;
}
inline G4double GetShift()
{
CheckIsUpdated();
return shift;
}
inline G4double GetVOV()
{
CheckIsUpdated();
return vov;
}
inline G4double GetFOM()
{
CheckIsUpdated();
return fom;
}
void calStat();
// boolean value of “statsAreUpdated” is set to TRUE at end of calStat
// and set to FALSE at end of AddScore
// NOTE : A thread lock for Geant4-MT needs to be put in AddScore so calStat is not
// executed in one thread while AddScore is modifying/adding data
void CheckIsUpdated() { if(!statsAreUpdated) { calStat(); } }
public:
// Public function to explicitly calculate statistics
void ComputeStatistics() { calStat(); }
// All “Get” functions check to make sure value is current before returning
G4double GetMean() { CheckIsUpdated(); return mean; }
G4double GetStandardDeviation() { CheckIsUpdated(); return sd; }
G4double GetVariance() { CheckIsUpdated(); return var; }
G4double GetR() { CheckIsUpdated(); return r; }
G4double GetEfficiency() { CheckIsUpdated(); return efficiency; }
G4double GetR2eff() { CheckIsUpdated(); return r2eff; }
G4double GetR2int() { CheckIsUpdated(); return r2int; }
G4double GetShift() { CheckIsUpdated(); return shift; }
G4double GetVOV() { CheckIsUpdated(); return vov; }
G4double GetFOM() { CheckIsUpdated(); return fom; }
private:
void calStat();
// Boolean value of 'statsAreUpdated' is set to TRUE at end of calStat
// and set to FALSE at end of AddScore
// NOTE : A thread lock for Geant4-MT needs to be put in AddScore so calStat
// is not executed in one thread while AddScore is modifying/adding data
private:
void calc_grid_point_of_history();
void calc_stat_history();
void check_stat_history(std::ostream& out = G4cout);
G4double calc_Pearson_r( G4int, std::vector<G4double>,
std::vector<G4double> );
G4bool is_monotonically_decrease( std::vector<G4double> );
void calc_slope_fit( std::vector< G4double > );
G4double slope_fitting_function( std::vector< G4double > );
inline void CheckIsUpdated()
{
if(!statsAreUpdated)
{
calStat();
}
}
private:
void calc_grid_point_of_history();
void calc_stat_history();
void check_stat_history(std::ostream& out = G4cout);
G4double calc_Pearson_r(G4int, std::vector<G4double>, std::vector<G4double>);
G4bool is_monotonically_decrease(std::vector<G4double>);
void calc_slope_fit(std::vector<G4double>);
G4double slope_fitting_function(std::vector<G4double>);
G4String name;
std::map< G4int , G4double > nonzero_histories;
// (ith-history , score value)
G4int n;
// number of history
G4double sum; // sum of scores;
private:
G4String name;
std::map<G4int, G4double> nonzero_histories;
// (ith-history , score value)
G4int n = 0;
// number of history
G4double sum = 0.0; // sum of scores;
G4Timer* timer;
std::vector<G4double> cpu_time;
G4Timer* timer = nullptr;
std::vector<G4double> cpu_time;
G4double mean;
G4double var;
G4double sd;
G4double r; // relative err sd/mean/sqrt(n)
G4double efficiency; // rate of non zero score
G4double r2eff;
G4double r2int;
G4double shift;
G4double vov;
G4double fom;
G4double mean = 0.0;
G4double var = 0.0;
G4double sd = 0.0;
G4double r = 0.0; // relative err sd/mean/sqrt(n)
G4double efficiency = 0.0; // rate of non zero score
G4double r2eff = 0.0;
G4double r2int = 0.0;
G4double shift = 0.0;
G4double vov = 0.0;
G4double fom = 0.0;
G4double largest;
G4int largest_score_happened;
G4double mean_1;
G4double var_1;
G4double sd_1;
G4double r_1; // relative err sd/mean/sqrt(n)
G4double shift_1;
G4double vov_1;
G4double fom_1;
G4double largest = 0.0;
G4int largest_score_happened = 0;
G4int noBinOfHistory;
std::vector< G4int > history_grid;
std::vector< G4double > mean_history;
std::vector< G4double > var_history;
std::vector< G4double > sd_history;
std::vector< G4double > r_history;
std::vector< G4double > vov_history;
std::vector< G4double > fom_history;
std::vector< G4double > shift_history;
std::vector< G4double > e_history;
std::vector< G4double > r2eff_history;
std::vector< G4double > r2int_history;
G4double mean_1 = 0.0;
G4double var_1 = 0.0;
G4double sd_1 = 0.0;
G4double r_1 = 0.0; // relative err sd/mean/sqrt(n)
G4double shift_1 = 0.0;
G4double vov_1 = 0.0;
G4double fom_1 = 0.0;
G4double slope;
std::vector< G4double > largest_scores;
std::vector< G4double > f_xi;
std::vector< G4double > f_yi;
G4int noBinOfPDF;
G4SimplexDownhill<G4ConvergenceTester>* minimizer;
G4int noBinOfHistory = 16;
std::vector<G4int> history_grid;
std::vector<G4double> mean_history;
std::vector<G4double> var_history;
std::vector<G4double> sd_history;
std::vector<G4double> r_history;
std::vector<G4double> vov_history;
std::vector<G4double> fom_history;
std::vector<G4double> shift_history;
std::vector<G4double> e_history;
std::vector<G4double> r2eff_history;
std::vector<G4double> r2int_history;
G4int noPass;
G4int noTotal; // Total number of tests
G4double slope = 0.0;
std::vector<G4double> largest_scores;
std::vector<G4double> f_xi;
std::vector<G4double> f_yi;
G4int noBinOfPDF = 10;
G4SimplexDownhill<G4ConvergenceTester>* minimizer = nullptr;
G4bool statsAreUpdated;
G4int noPass = 0;
G4int noTotal = 8; // Total number of tests
G4bool showHistory;
G4bool calcSLOPE;
G4bool statsAreUpdated = true;
G4bool showHistory = true;
G4bool calcSLOPE = true;
};
#endif
#endif
@@ -23,141 +23,89 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4DataInterpolation
//
// Class description:
//
// The class consists of some methods for data interpolations and extrapolations.
// The methods based mainly on recommendations given in the book : An introduction to
// NUMERICAL METHODS IN C++, B.H. Flowers, Claredon Press, Oxford, 1995
//
// ------------------------------ Data members: ---------------------------------
//
// fArgument and fFunction - pointers to data table to be interpolated
// for y[i] and x[i] respectively
// fNumber - the corresponding table size
// ......
// G4DataInterpolation( G4double pX[], G4double pY[], G4int number )
//
// Constructor for initializing of fArgument, fFunction and fNumber data members:
// ......
// G4DataInterpolation( G4double pX[], G4double pY[], G4int number,
// G4double pFirstDerStart, G4double pFirstDerFinish )
//
// Constructor for cubic spline interpolation. It creates the array
// fSecondDerivative[0,...fNumber-1] which is used in this interpolation by
// the function:
// ....
// ~G4DataInterpolation()
//
// Destructor deletes dynamically created arrays for data members: fArgument,
// fFunction and fSecondDerivative, all have dimension of fNumber
//
// ------------------------------ Methods: ----------------------------------------
//
// G4double PolynomInterpolation(G4double pX, G4double& deltaY ) const
//
// This function returns the value P(pX), where P(x) is polynom of fNumber-1 degree
// such that P(fArgument[i]) = fFunction[i], for i = 0, ..., fNumber-1 .
// ........
// void PolIntCoefficient( G4double cof[]) const
//
// Given arrays fArgument[0,..,fNumber-1] and fFunction[0,..,fNumber-1] , this
// function calculates an array of coefficients. The coefficients don't provide
// usually (fNumber>10) better accuracy for polynom interpolation, as compared with
// PolynomInterpolation function. They could be used instead for derivate
// calculations and some other applications.
// .........
// G4double RationalPolInterpolation(G4double pX, G4double& deltaY ) const
//
// The function returns diagonal rational function (Bulirsch and Stoer algorithm
// of Neville type) Pn(x)/Qm(x) where P and Q are polynoms.
// Tests showed the method is not stable and hasn't advantage if compared with
// polynomial interpolation
// ................
// G4double CubicSplineInterpolation(G4double pX) const
//
// Cubic spline interpolation in point pX for function given by the table:
// fArgument, fFunction. The constructor, which creates fSecondDerivative, must be
// called before. The function works optimal, if sequential calls are in random
// values of pX.
// ..................
// G4double FastCubicSpline(G4double pX, G4int index) const
//
// Return cubic spline interpolation in the point pX which is located between
// fArgument[index] and fArgument[index+1]. It is usually called in sequence of
// known from external analysis values of index.
// .........
// G4int LocateArgument(G4double pX) const
//
// Given argument pX, returns index k, so that pX bracketed by fArgument[k] and
// fArgument[k+1]
// ......................
// void CorrelatedSearch( G4double pX, G4int& index ) const
//
// Given a value pX, returns a value 'index' such that pX is between fArgument[index]
// and fArgument[index+1]. fArgument MUST BE MONOTONIC, either increasing or
// decreasing. If index = -1 or fNumber, this indicates that pX is out of range.
// The value index on input is taken as the initial approximation for index on
// output.
// --------------------------------- History: --------------------------------------
//
// 3.4.97 V.Grichine (Vladimir.Grichine@cern.ch)
//
// The class consists of some methods for data interpolations and
// extrapolations. The methods based mainly on recommendations given in the
// book: An introduction to NUMERICAL METHODS IN C++, B.H. Flowers,
// Claredon Press, Oxford, 1995.
// Author: V.Grichine, 03.04.1997
// --------------------------------------------------------------------
#ifndef G4DATAINTERPOLATION_HH
#define G4DATAINTERPOLATION_HH
#define G4DATAINTERPOLATION_HH 1
#include "globals.hh"
class G4DataInterpolation
{
public:
G4DataInterpolation( G4double pX[],
G4double pY[],
G4int number );
public:
G4DataInterpolation(G4double pX[], G4double pY[], G4int number);
// Constructor for initializing data members.
// Constructor for cubic spline interpolation. It creates fSecond Deivative array
// as well as fArgument and fFunction
G4DataInterpolation( G4double pX[],
G4double pY[],
G4int number,
G4double pFirstDerStart,
G4double pFirstDerFinish ) ;
G4DataInterpolation(G4double pX[], G4double pY[], G4int number,
G4double pFirstDerStart, G4double pFirstDerFinish);
// Constructor for cubic spline interpolation. It creates fSecond Deivative
// array as well as fArgument and fFunction.
~G4DataInterpolation() ;
G4double PolynomInterpolation( G4double pX,
G4double& deltaY ) const ;
void PolIntCoefficient( G4double cof[]) const ;
~G4DataInterpolation();
// Destructor deletes dynamically created arrays for data members: fArgument,
// fFunction and fSecondDerivative, all have dimension of fNumber.
G4double RationalPolInterpolation( G4double pX,
G4double& deltaY ) const ;
G4DataInterpolation(const G4DataInterpolation&) = delete;
G4DataInterpolation& operator=(const G4DataInterpolation&) = delete;
// Copy constructor and assignement operator not allowed.
G4double CubicSplineInterpolation( G4double pX ) const ;
G4double PolynomInterpolation(G4double pX, G4double& deltaY) const;
// This function returns the value P(pX), where P(x) is polynom of fNumber-1
// degree such that P(fArgument[i]) = fFunction[i], for i = 0, ..., fNumber-1.
G4double FastCubicSpline( G4double pX,
G4int index ) const ;
void PolIntCoefficient(G4double cof[]) const;
// Given arrays fArgument[0,..,fNumber-1] and fFunction[0,..,fNumber-1], this
// function calculates an array of coefficients.
// The coefficients don't provide usually (fNumber>10) better accuracy for
// polynom interpolation, as compared with PolynomInterpolation() function.
// They could be used instead for derivate calculations and some other
// applications.
G4int LocateArgument( G4double pX ) const ;
void CorrelatedSearch( G4double pX,
G4int& index ) const ;
private:
G4double RationalPolInterpolation(G4double pX, G4double& deltaY) const;
// The function returns diagonal rational function (Bulirsch and Stoer
// algorithm of Neville type) Pn(x)/Qm(x) where P and Q are polynoms.
// Tests showed the method is not stable and hasn't advantage if compared
// with polynomial interpolation.
G4DataInterpolation(const G4DataInterpolation&);
G4DataInterpolation& operator=(const G4DataInterpolation&);
G4double CubicSplineInterpolation(G4double pX) const;
// Cubic spline interpolation in point pX for function given by the table:
// fArgument, fFunction. The constructor, which creates fSecondDerivative,
// must be called before. The function works optimal, if sequential calls
// are in random values of pX.
private:
G4double* fArgument ;
G4double* fFunction ;
G4double* fSecondDerivative ;
G4int fNumber ;
} ;
G4double FastCubicSpline(G4double pX, G4int index) const;
// Return cubic spline interpolation in the point pX which is located between
// fArgument[index] and fArgument[index+1]. It is usually called in sequence
// of known from external analysis values of index.
G4int LocateArgument(G4double pX) const;
// Given argument pX, returns index k, so that pX bracketed by fArgument[k]
// and fArgument[k+1].
void CorrelatedSearch(G4double pX, G4int& index) const;
// Given a value pX, returns a value 'index' such that pX is between
// fArgument[index] and fArgument[index+1]. fArgument MUST BE MONOTONIC,
// either increasing or decreasing. If index = -1 or fNumber, this indicates
// that pX is out of range. The value index on input is taken as the initial
// approximation for index on output.
private:
// pointers to data table to be interpolated for y[i] and x[i] respectively
G4double* fArgument = nullptr;
G4double* fFunction = nullptr;
G4double* fSecondDerivative = nullptr;
G4int fNumber = 0; // the corresponding table size
};
#endif
@@ -23,62 +23,38 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4GaussChebyshevQ
//
// Class description:
//
// Class for Gauss-Chebyshev quadrature method
// Roots of ortogonal polynoms and corresponding weights are calculated based on
// iteration method (by bisection Newton algorithm). Constant values for initial
// approximations were derived from the book: M. Abramowitz, I. Stegun, Handbook
// of mathematical functions, DOVER Publications INC, New York 1965 ; chapters 9,
// 10, and 22 .
//
// ------------------------------ CONSTRUCTORS ----------------------------
//
// Constructor for Gauss-Chebyshev quadrature method
//
// G4GaussChebyshevQuadrature( function pFunction,
// G4int nChebyshev )
//
//
//
// ------------------------------- METHODS -----------------------------------
//
// Integrates function pointed by fFunction from a to b by Gauss-Chebyshev quadrature
// method
//
// G4double Integral(G4double a, G4double b) const
// ------------------------------- HISTORY --------------------------------
//
// 13.05.97 V.Grichine (Vladimir.Grichine@cern.ch)
// approximations were derived from the book:
// M. Abramowitz, I. Stegun, Handbook of mathematical functions,
// DOVER Publications INC, New York 1965 ; chapters 9, 10, and 22.
// Author: V.Grichine, 13.05.1997
// --------------------------------------------------------------------
#ifndef G4GAUSSCHEBYSHEVQ_HH
#define G4GAUSSCHEBYSHEVQ_HH
#define G4GAUSSCHEBYSHEVQ_HH 1
#include "G4VGaussianQuadrature.hh"
class G4GaussChebyshevQ : public G4VGaussianQuadrature
{
public:
// Constructor/destructor
public:
G4GaussChebyshevQ(function pFunction, G4int nChebyshev);
// Constructor for Gauss-Chebyshev quadrature method
G4GaussChebyshevQ( function pFunction,
G4int nChebyshev ) ;
~G4GaussChebyshevQ() ;
// Methods
G4double Integral(G4double a, G4double b) const ;
~G4GaussChebyshevQ();
G4GaussChebyshevQ(const G4GaussChebyshevQ&) = delete;
G4GaussChebyshevQ& operator=(const G4GaussChebyshevQ&) = delete;
private:
G4GaussChebyshevQ(const G4GaussChebyshevQ&);
G4GaussChebyshevQ& operator=(const G4GaussChebyshevQ&);
G4double Integral(G4double a, G4double b) const;
// Integrates function pointed by fFunction from a to b by Gauss-Chebyshev
// quadrature method
};
#endif
@@ -23,56 +23,38 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4GaussHermiteQ
//
// Class description:
//
// Roots of ortogonal polynoms and corresponding weights are calculated based on
// iteration method (by bisection Newton algorithm). Constant values for initial
// approximations were derived from the book: M. Abramowitz, I. Stegun, Handbook
// of mathematical functions, DOVER Publications INC, New York 1965 ; chapters 9,
// 10, and 22 .
//
// --------------------------------------------------------------------------
//
// Constructor for Gauss-Hermite quadrature method . The function GaussHermite
// should be called then
//
// G4GaussHermiteQ( function pFunction, G4int nHermite )
//
// ----------------------------------------------------------------------------
//
// Gauss-Hermite method for integration of std::exp(-x*x)*nFunction(x) from minus infinity
// to plus infinity .
//
// G4double Integral() const
// ------------------------------- HISTORY -------------------------------------
//
// 13.05.97 V.Grichine (Vladimir.Grichine@cern.chz0
// approximations were derived from the book:
// M. Abramowitz, I. Stegun, Handbook of mathematical functions,
// DOVER Publications INC, New York 1965 ; chapters 9, 10, and 22.
// Author: V.Grichine, 13.05.1997 V.Grichine
// --------------------------------------------------------------------
#ifndef G4GAUSSHERMITEQ_HH
#define G4GAUSSHERMITEQ_HH
#define G4GAUSSHERMITEQ_HH 1
#include "G4VGaussianQuadrature.hh"
class G4GaussHermiteQ : public G4VGaussianQuadrature
{
public:
// Constructor
public:
// Constructor
G4GaussHermiteQ( function pFunction, G4int nHermite ) ;
// Methods
G4double Integral() const ;
G4GaussHermiteQ(function pFunction, G4int nHermite);
// Constructor for Gauss-Hermite quadrature method.
// The function GaussHermite should be called then.
G4GaussHermiteQ(const G4GaussHermiteQ&) = delete;
G4GaussHermiteQ& operator=(const G4GaussHermiteQ&) = delete;
private:
G4GaussHermiteQ(const G4GaussHermiteQ&);
G4GaussHermiteQ& operator=(const G4GaussHermiteQ&);
G4double Integral() const;
// Gauss-Hermite method for integration of std::exp(-x*x)*nFunction(x) from
// minus infinity to plus infinity.
};
#endif
@@ -23,59 +23,36 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4GaussJacobiQ
//
// Class description:
//
// Roots of ortogonal polynoms and corresponding weights are calculated based on
// iteration method (by bisection Newton algorithm). Constant values for initial
// approximations were derived from the book: M. Abramowitz, I. Stegun, Handbook
// of mathematical functions, DOVER Publications INC, New York 1965 ; chapters 9,
// 10, and 22 .
//
// ---------------------------------------------------------------------------
//
// Constructor for Gauss-Jacobi integration method.
//
// G4GaussJacobiQ( function pFunction,
// G4double alpha,
// G4double beta,
// G4int nJacobi )
//
// ----------------------------------------------------------------------------
//
// Gauss-Jacobi method for integration of ((1-x)^alpha)*((1+x)^beta)*pFunction(x)
// from minus unit to plus unit .
//
// G4double Integral() const
// ------------------------------- HISTORY -------------------------------------
//
// 13.05.97 V.Grichine (Vladimir.Grichine@cern.chz0
// approximations were derived from the book:
// M. Abramowitz, I. Stegun, Handbook of mathematical functions,
// DOVER Publications INC, New York 1965 ; chapters 9, 10, and 22.
// Author: V.Grichine, 13.05.1997
// --------------------------------------------------------------------
#ifndef G4GAUSSJACOBIQ_HH
#define G4GAUSSJACOBIQ_HH
#define G4GAUSSJACOBIQ_HH 1
#include "G4VGaussianQuadrature.hh"
class G4GaussJacobiQ : public G4VGaussianQuadrature
{
public:
// Constructor
public:
G4GaussJacobiQ(function pFunction, G4double alpha, G4double beta,
G4int nJacobi);
// Constructor for Gauss-Jacobi integration method.
G4GaussJacobiQ( function pFunction,
G4double alpha,
G4double beta,
G4int nJacobi ) ;
// Methods
G4double Integral() const ;
G4GaussJacobiQ(const G4GaussJacobiQ&) = delete;
G4GaussJacobiQ& operator=(const G4GaussJacobiQ&) = delete;
private:
G4GaussJacobiQ(const G4GaussJacobiQ&);
G4GaussJacobiQ& operator=(const G4GaussJacobiQ&);
G4double Integral() const;
// Gauss-Jacobi method for integration of
// ((1-x)^alpha)*((1+x)^beta)*pFunction(x) from minus unit to plus unit.
};
#endif
@@ -30,55 +30,36 @@
// Class for realization of Gauss-Laguerre quadrature method
// Roots of ortogonal polynoms and corresponding weights are calculated based on
// iteration method (by bisection Newton algorithm). Constant values for initial
// approximations were derived from the book: M. Abramowitz, I. Stegun, Handbook
// of mathematical functions, DOVER Publications INC, New York 1965 ; chapters 9,
// 10, and 22 .
//
// ---------------------------------------------------------------------------
//
// Constructor for Gauss-Laguerre quadrature method: integral from zero to
// infinity of std::pow(x,alpha)*std::exp(-x)*f(x). The value of nLaguerre sets the accuracy.
// The constructor creates arrays fAbscissa[0,..,nLaguerre-1] and
// fWeight[0,..,nLaguerre-1] . The function GaussLaguerre(f) should be called
// then with any f .
//
// G4GaussLaguerreQ( function pFunction,
// G4double alpha,
// G4int nLaguerre )
//
//
// -------------------------------------------------------------------------
//
// Gauss-Laguerre method for integration of std::pow(x,alpha)*std::exp(-x)*pFunction(x)
// from zero up to infinity. pFunction is evaluated in fNumber points for which
// fAbscissa[i] and fWeight[i] arrays were created in constructor
//
// G4double Integral() const
// ------------------------------- HISTORY --------------------------------
//
// 13.05.97 V.Grichine (Vladimir.Grichine@cern.chz0
// approximations were derived from the book:
// M. Abramowitz, I. Stegun, Handbook of mathematical functions,
// DOVER Publications INC, New York 1965 ; chapters 9, 10, and 22.
// Author: V.Grichine, 13.05.1997
// --------------------------------------------------------------------
#ifndef G4GAUSSLAGUERREQ_HH
#define G4GAUSSLAGUERREQ_HH
#define G4GAUSSLAGUERREQ_HH 1
#include "G4VGaussianQuadrature.hh"
class G4GaussLaguerreQ : public G4VGaussianQuadrature
{
public:
G4GaussLaguerreQ( function pFunction,
G4double alpha,
G4int nLaguerre ) ;
// Methods
G4double Integral() const ;
public:
G4GaussLaguerreQ(function pFunction, G4double alpha, G4int nLaguerre);
// Constructor for Gauss-Laguerre quadrature method: integral from zero to
// infinity of std::pow(x,alpha)*std::exp(-x)*f(x). The value of nLaguerre
// sets the accuracy.
// The constructor creates arrays fAbscissa[0,..,nLaguerre-1] and
// fWeight[0,..,nLaguerre-1] . The function GaussLaguerre(f) should be
// called then with any f.
private:
G4GaussLaguerreQ(const G4GaussLaguerreQ&) = delete;
G4GaussLaguerreQ& operator=(const G4GaussLaguerreQ&) = delete;
G4GaussLaguerreQ(const G4GaussLaguerreQ&);
G4GaussLaguerreQ& operator=(const G4GaussLaguerreQ&);
G4double Integral() const;
// Gauss-Laguerre method for integration of
// std::pow(x,alpha)*std::exp(-x)*pFunction(x) from zero up to infinity.
// pFunction is evaluated in fNumber points for which fAbscissa[i] and
// fWeight[i] arrays were created in constructor.
};
#endif
@@ -23,90 +23,63 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4GaussLegendreQ
//
// Class description:
//
// Class for Gauss-Legendre integration method
// Roots of ortogonal polynoms and corresponding weights are calculated based on
// iteration method (by bisection Newton algorithm). Constant values for initial
// approximations were derived from the book: M. Abramowitz, I. Stegun, Handbook
// of mathematical functions, DOVER Publications INC, New York 1965 ; chapters 9,
// 10, and 22 .
//
// ------------------------- CONSTRUCTORS: -------------------------------
//
// Constructor for GaussLegendre quadrature method. The value nLegendre set the
// accuracy required, i.e the number of points where the function pFunction will
// be evaluated during integration. The constructor creates the arrays for
// abscissas and weights that used in Gauss-Legendre quadrature method.
// The values a and b are the limits of integration of the pFunction.
//
// G4GaussLegendreQ( function pFunction,
// G4int nLegendre )
//
// -------------------------- METHODS: ---------------------------------------
//
// Returns the integral of the function to be pointed by fFunction between a and b,
// by 2*fNumber point Gauss-Legendre integration: the function is evaluated exactly
// 2*fNumber Times at interior points in the range of integration. Since the weights
// and abscissas are, in this case, symmetric around the midpoint of the range of
// integration, there are actually only fNumber distinct values of each.
//
// G4double Integral(G4double a, G4double b) const
//
// -----------------------------------------------------------------------
//
// Returns the integral of the function to be pointed by fFunction between a and b,
// by ten point Gauss-Legendre integration: the function is evaluated exactly
// ten Times at interior points in the range of integration. Since the weights
// and abscissas are, in this case, symmetric around the midpoint of the range of
// integration, there are actually only five distinct values of each
//
// G4double
// QuickIntegral(G4double a, G4double b) const
//
// ---------------------------------------------------------------------
//
// Returns the integral of the function to be pointed by fFunction between a and b,
// by 96 point Gauss-Legendre integration: the function is evaluated exactly
// ten Times at interior points in the range of integration. Since the weights
// and abscissas are, in this case, symmetric around the midpoint of the range of
// integration, there are actually only five distinct values of each
//
// G4double
// AccurateIntegral(G4double a, G4double b) const
// ------------------------------- HISTORY --------------------------------
//
// 13.05.97 V.Grichine (Vladimir.Grichine@cern.chz0
// approximations were derived from the book:
// M. Abramowitz, I. Stegun, Handbook of mathematical functions,
// DOVER Publications INC, New York 1965 ; chapters 9, 10, and 22.
// Author: V.Grichine, 13.05.1997
// --------------------------------------------------------------------
#ifndef G4GAUSSLEGENDREQ_HH
#define G4GAUSSLEGENDREQ_HH
#define G4GAUSSLEGENDREQ_HH 1
#include "G4VGaussianQuadrature.hh"
class G4GaussLegendreQ : public G4VGaussianQuadrature
{
public:
explicit G4GaussLegendreQ( function pFunction ) ;
public:
explicit G4GaussLegendreQ(function pFunction);
G4GaussLegendreQ( function pFunction,
G4int nLegendre ) ;
// Methods
G4double Integral(G4double a, G4double b) const ;
G4GaussLegendreQ(function pFunction, G4int nLegendre);
// Constructor for GaussLegendre quadrature method. The value nLegendre set
// the accuracy required, i.e the number of points where the function
// pFunction will be evaluated during integration. The constructor creates
// the arrays for abscissas and weights that used in Gauss-Legendre
// quadrature method.
// The values a and b are the limits of integration of the pFunction.
G4double QuickIntegral(G4double a, G4double b) const ;
G4double AccurateIntegral(G4double a, G4double b) const ;
G4GaussLegendreQ(const G4GaussLegendreQ&) = delete;
G4GaussLegendreQ& operator=(const G4GaussLegendreQ&) = delete;
private:
G4double Integral(G4double a, G4double b) const;
// Returns the integral of the function to be pointed by fFunction between a
// and b, by 2*fNumber point Gauss-Legendre integration: the function is
// evaluated exactly 2*fNumber Times at interior points in the range of
// integration. Since the weights and abscissas are, in this case, symmetric
// around the midpoint of the range of integration, there are actually only
// fNumber distinct values of each.
G4GaussLegendreQ(const G4GaussLegendreQ&);
G4GaussLegendreQ& operator=(const G4GaussLegendreQ&);
G4double QuickIntegral(G4double a, G4double b) const;
// Returns the integral of the function to be pointed by fFunction between a
// and b, by ten point Gauss-Legendre integration: the function is evaluated
// exactly ten Times at interior points in the range of integration. Since
// the weights and abscissas are, in this case, symmetric around the midpoint
// of the range of integration, there are actually only five distinct values
// of each.
G4double AccurateIntegral(G4double a, G4double b) const;
// Returns the integral of the function to be pointed by fFunction between a
// and b, by 96 point Gauss-Legendre integration: the function is evaluated
// exactly ten Times at interior points in the range of integration. Since
// the weights and abscissas are, in this case, symmetric around the midpoint
// of the range of integration, there are actually only five distinct values
// of each.
};
#endif
@@ -23,112 +23,101 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4Integrator
//
// Class description:
//
// Template class collecting integrator methods for generic funtions.
// History:
//
// 04.09.99 V.Grichine, first implementation based on G4SimpleIntegration class
// H.P.Wellisch, G.Cosmo, and E.Cherniaev advises
// 08.09.99 V.Grichine, methods involving orthogonal polynomials
//
// Author: V.Grichine, 04.09.1999 - First implementation based on
// G4SimpleIntegration class with H.P.Wellisch, G.Cosmo, and
// E.TCherniaev advises
// --------------------------------------------------------------------
#ifndef G4INTEGRATOR_HH
#define G4INTEGRATOR_HH 1
#include "G4Types.hh"
#include <cmath>
#include <CLHEP/Units/PhysicalConstants.h>
#include <cmath>
template <class T, class F>
class G4Integrator
{
public: // with description
public:
G4Integrator() { ; }
~G4Integrator() { ; }
G4Integrator(){;}
~G4Integrator(){;}
G4double Simpson( T& typeT, F f, G4double a, G4double b, G4int n ) ;
G4double Simpson( T* ptrT, F f, G4double a, G4double b, G4int n ) ;
G4double Simpson( G4double (*f)(G4double),
G4double a, G4double b, G4int n ) ;
G4double Simpson(T& typeT, F f, G4double a, G4double b, G4int n);
G4double Simpson(T* ptrT, F f, G4double a, G4double b, G4int n);
G4double Simpson(G4double (*f)(G4double), G4double a, G4double b, G4int n);
// Simpson integration method
G4double AdaptiveGauss( T& typeT, F f, G4double a, G4double b, G4double e ) ;
G4double AdaptiveGauss( T* ptrT, F f, G4double a, G4double b, G4double e ) ;
G4double AdaptiveGauss( G4double (*f)(G4double),
G4double a, G4double b, G4double e ) ;
G4double AdaptiveGauss(T& typeT, F f, G4double a, G4double b, G4double e);
G4double AdaptiveGauss(T* ptrT, F f, G4double a, G4double b, G4double e);
G4double AdaptiveGauss(G4double (*f)(G4double), G4double a, G4double b,
G4double e);
// Adaptive Gauss method
// Integration methods involving orthogohol polynomials
G4double Legendre( T& typeT, F f, G4double a, G4double b, G4int n) ;
G4double Legendre( T* ptrT, F f, G4double a, G4double b, G4int n) ;
G4double Legendre( G4double (*f)(G4double), G4double a, G4double b, G4int n) ;
G4double Legendre(T& typeT, F f, G4double a, G4double b, G4int n);
G4double Legendre(T* ptrT, F f, G4double a, G4double b, G4int n);
G4double Legendre(G4double (*f)(G4double), G4double a, G4double b, G4int n);
//
// Methods involving Legendre polynomials
// Methods involving Legendre polynomials
G4double Legendre10( T& typeT, F f,G4double a, G4double b) ;
G4double Legendre10( T* ptrT, F f,G4double a, G4double b) ;
G4double Legendre10( G4double (*f)(G4double), G4double a, G4double b) ;
G4double Legendre10(T& typeT, F f, G4double a, G4double b);
G4double Legendre10(T* ptrT, F f, G4double a, G4double b);
G4double Legendre10(G4double (*f)(G4double), G4double a, G4double b);
//
// Legendre10 is very fast and accurate enough
G4double Legendre96( T& typeT, F f,G4double a, G4double b) ;
G4double Legendre96( T* ptrT, F f,G4double a, G4double b) ;
G4double Legendre96( G4double (*f)(G4double), G4double a, G4double b) ;
G4double Legendre96(T& typeT, F f, G4double a, G4double b);
G4double Legendre96(T* ptrT, F f, G4double a, G4double b);
G4double Legendre96(G4double (*f)(G4double), G4double a, G4double b);
//
// Legendre96 is very accurate and fast enough
G4double Chebyshev( T& typeT, F f, G4double a, G4double b, G4int n) ;
G4double Chebyshev( T* ptrT, F f, G4double a, G4double b, G4int n) ;
G4double Chebyshev( G4double (*f)(G4double), G4double a, G4double b, G4int n) ;
G4double Chebyshev(T& typeT, F f, G4double a, G4double b, G4int n);
G4double Chebyshev(T* ptrT, F f, G4double a, G4double b, G4int n);
G4double Chebyshev(G4double (*f)(G4double), G4double a, G4double b, G4int n);
//
// Methods involving Chebyshev polynomials
G4double Laguerre( T& typeT, F f, G4double alpha, G4int n) ;
G4double Laguerre( T* ptrT, F f, G4double alpha, G4int n) ;
G4double Laguerre( G4double (*f)(G4double), G4double alpha, G4int n) ;
// Methods involving Chebyshev polynomials
G4double Laguerre(T& typeT, F f, G4double alpha, G4int n);
G4double Laguerre(T* ptrT, F f, G4double alpha, G4int n);
G4double Laguerre(G4double (*f)(G4double), G4double alpha, G4int n);
//
// Method involving Laguerre polynomials
G4double Hermite( T& typeT, F f, G4int n) ;
G4double Hermite( T* ptrT, F f, G4int n) ;
G4double Hermite( G4double (*f)(G4double), G4int n) ;
G4double Hermite(T& typeT, F f, G4int n);
G4double Hermite(T* ptrT, F f, G4int n);
G4double Hermite(G4double (*f)(G4double), G4int n);
//
// Method involving Hermite polynomials
G4double Jacobi( T& typeT, F f, G4double alpha, G4double beta, G4int n) ;
G4double Jacobi( T* ptrT, F f, G4double alpha, G4double beta, G4int n) ;
G4double Jacobi( G4double (*f)(G4double), G4double alpha,
G4double beta, G4int n) ;
G4double Jacobi(T& typeT, F f, G4double alpha, G4double beta, G4int n);
G4double Jacobi(T* ptrT, F f, G4double alpha, G4double beta, G4int n);
G4double Jacobi(G4double (*f)(G4double), G4double alpha, G4double beta,
G4int n);
// Method involving Jacobi polynomials
protected:
// Auxiliary functions for adaptive Gauss method
// Auxiliary function for adaptive Gauss method
G4double Gauss(T& typeT, F f, G4double a, G4double b);
G4double Gauss(T* ptrT, F f, G4double a, G4double b);
G4double Gauss(G4double (*f)(G4double), G4double a, G4double b);
G4double Gauss( T& typeT, F f, G4double a, G4double b ) ;
G4double Gauss( T* ptrT, F f, G4double a, G4double b ) ;
G4double Gauss( G4double (*f)(G4double), G4double a, G4double b) ;
void AdaptGauss(T& typeT, F f, G4double a, G4double b, G4double e,
G4double& sum, G4int& n);
void AdaptGauss(T* typeT, F f, G4double a, G4double b, G4double e,
G4double& sum, G4int& n);
void AdaptGauss(G4double (*f)(G4double), G4double a, G4double b, G4double e,
G4double& sum, G4int& n);
void AdaptGauss( T& typeT, F f, G4double a, G4double b,
G4double e, G4double& sum, G4int& n) ;
void AdaptGauss( T* typeT, F f, G4double a, G4double b,
G4double e, G4double& sum, G4int& n ) ;
void AdaptGauss( G4double (*f)(G4double), G4double a, G4double b,
G4double e, G4double& sum, G4int& n ) ;
G4double GammaLogarithm(G4double xx) ;
} ;
G4double GammaLogarithm(G4double xx);
};
#include "G4Integrator.icc"
File diff suppressed because it is too large Load Diff
@@ -23,7 +23,7 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4JTPolynomialSolver
//
// Class description:
//
@@ -37,86 +37,80 @@
// op - double precision vector of coefficients in order of
// decreasing powers
// degree - integer degree of polynomial
//
//
// ----------------------------- OUTPUT -------------------------------
//
// zeror,zeroi - double precision vectors of the
// real and imaginary parts of the zeros
//
//
// ---------------------------- EXAMPLE -------------------------------
//
//
// G4JTPolynomialSolver trapEq ;
// G4double coef[8] ;
// G4double zr[7] , zi[7] ;
// G4int num = trapEq.FindRoots(coef,7,zr,zi);
// ---------------------------- HISTORY -------------------------------
//
// Translated from original TOMS493 Fortran77 routine (ANSI C, by C.Bond).
// Translated to C++ and adapted to use STL vectors,
// by Oliver Link (Oliver.Link@cern.ch)
//
// --------------------------------------------------------------------
// Author: Oliver Link, 15.02.2005
// Translated to C++ and adapted to use STL vectors.
// --------------------------------------------------------------------
#ifndef G4JTPOLYNOMIALSOLVER_HH
#define G4JTPOLYNOMIALSOLVER_HH
#define G4JTPOLYNOMIALSOLVER_HH 1
#include <cmath>
#include <vector>
#include "globals.hh"
class G4JTPolynomialSolver
class G4JTPolynomialSolver
{
public:
G4JTPolynomialSolver();
~G4JTPolynomialSolver();
public:
G4int FindRoots(G4double* op, G4int degree, G4double* zeror, G4double* zeroi);
G4JTPolynomialSolver();
~G4JTPolynomialSolver();
G4int FindRoots(G4double *op, G4int degree,
G4double *zeror, G4double *zeroi);
private:
void Quadratic(G4double a, G4double b1, G4double c, G4double* sr,
G4double* si, G4double* lr, G4double* li);
void ComputeFixedShiftPolynomial(G4int l2, G4int* nz);
void QuadraticPolynomialIteration(G4double* uu, G4double* vv, G4int* nz);
void RealPolynomialIteration(G4double* sss, G4int* nz, G4int* iflag);
void ComputeScalarFactors(G4int* type);
void ComputeNextPolynomial(G4int* type);
void ComputeNewEstimate(G4int type, G4double* uu, G4double* vv);
void QuadraticSyntheticDivision(G4int n, G4double* u, G4double* v,
std::vector<G4double>& p,
std::vector<G4double>& q, G4double* a,
G4double* b);
private:
private:
std::vector<G4double> p;
std::vector<G4double> qp;
std::vector<G4double> k;
std::vector<G4double> qk;
std::vector<G4double> svk;
std::vector<G4double> p;
std::vector<G4double> qp;
std::vector<G4double> k;
std::vector<G4double> qk;
std::vector<G4double> svk;
G4double sr = 0.0;
G4double si = 0.0;
G4double u = 0.0, v = 0.0;
G4double a = 0.0, b = 0.0, c = 0.0, d = 0.0;
G4double a1 = 0.0, a3 = 0.0, a7 = 0.0;
G4double e = 0.0, f = 0.0, g = 0.0, h = 0.0;
G4double szr = 0.0, szi = 0.0;
G4double lzr = 0.0, lzi = 0.0;
G4int n = 0;
G4double sr;
G4double si;
G4double u,v;
G4double a,b,c,d;
G4double a1,a3,a7;
G4double e,f,g,h;
G4double szr,szi;
G4double lzr,lzi;
G4int n;
/* The following statements set machine constants */
/* The following statements set machine constants */
static const G4double base;
static const G4double eta;
static const G4double infin;
static const G4double smalno;
static const G4double are;
static const G4double mre;
static const G4double lo;
void Quadratic(G4double a,G4double b1,G4double c,
G4double *sr,G4double *si, G4double *lr,G4double *li);
void ComputeFixedShiftPolynomial(G4int l2, G4int *nz);
void QuadraticPolynomialIteration(G4double *uu,G4double *vv,G4int *nz);
void RealPolynomialIteration(G4double *sss, G4int *nz, G4int *iflag);
void ComputeScalarFactors(G4int *type);
void ComputeNextPolynomial(G4int *type);
void ComputeNewEstimate(G4int type,G4double *uu,G4double *vv);
void QuadraticSyntheticDivision(G4int n, G4double *u, G4double *v,
std::vector<G4double> &p,
std::vector<G4double> &q,
G4double *a, G4double *b);
static const G4double base;
static const G4double eta;
static const G4double infin;
static const G4double smalno;
static const G4double are;
static const G4double mre;
static const G4double lo;
};
#endif
@@ -23,9 +23,7 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
//
// class G4PolynomialSolver
// G4PolynomialSolver
//
// Class description:
//
@@ -56,80 +54,72 @@
// G4double MyFunctionClass::Function(G4double value)
// {
// G4double Lx,Ly,Lz;
// G4double result;
//
// G4double result;
//
// Lx = x + value*dx;
// Ly = y + value*dy;
// Lz = z + value*dz;
//
//
// result = TorusEquation(Lx,Ly,Lz,Rmax,Rmin);
//
// return result ;
// }
//
//
// return result ;
// }
//
// G4double MyFunctionClass::Derivative(G4double value)
// {
// G4double Lx,Ly,Lz;
// G4double result;
//
// G4double result;
//
// Lx = x + value*dx;
// Ly = y + value*dy;
// Lz = z + value*dz;
//
//
// result = dx*TorusDerivativeX(Lx,Ly,Lz,Rmax,Rmin);
// result += dy*TorusDerivativeY(Lx,Ly,Lz,Rmax,Rmin);
// result += dz*TorusDerivativeZ(Lx,Ly,Lz,Rmax,Rmin);
//
//
// return result;
// }
//
//
// Then to have a root inside an interval [IntervalMin,IntervalMax] do the
// following:
//
// MyRoot = PolySolver.solve(IntervalMin,IntervalMax);
//
// History:
//
// - 19.12.00 E.Medernach, First implementation
//
// Author: E.Medernach, 19.12.2000 - First implementation
// --------------------------------------------------------------------
#ifndef G4POL_SOLVER_HH
#define G4POL_SOLVER_HH
#define G4POL_SOLVER_HH 1
#include "globals.hh"
#include "globals.hh"
template <class T, class F>
class G4PolynomialSolver
class G4PolynomialSolver
{
public: // with description
G4PolynomialSolver(T* typeF, F func, F deriv, G4double precision);
public:
G4PolynomialSolver(T* typeF, F func, F deriv, G4double precision);
~G4PolynomialSolver();
G4double solve (G4double IntervalMin, G4double IntervalMax);
private:
G4double solve(G4double IntervalMin, G4double IntervalMax);
G4double Newton (G4double IntervalMin, G4double IntervalMax);
//General Newton method with Bezier Clipping
private:
G4double Newton(G4double IntervalMin, G4double IntervalMax);
// General Newton method with Bezier Clipping
// Works for polynomial of order less or equal than 4.
// But could be changed to work for polynomial of any order providing
// that we find the bezier control points.
G4int BezierClipping(G4double *IntervalMin, G4double *IntervalMax);
// This is just one iteration of Bezier Clipping
G4int BezierClipping(G4double* IntervalMin, G4double* IntervalMax);
// This is just one iteration of Bezier Clipping
T* FunctionClass;
F Function;
F Derivative;
T* FunctionClass ;
F Function ;
F Derivative ;
G4double Precision;
};
#include "G4PolynomialSolver.icc"
#endif
#endif
@@ -23,40 +23,36 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
// G4PolynomialSolver inline methods implementation
//
//
// class G4PolynomialSolver
//
// 19.12.00 E.Medernach, First implementation
//
// Author: E.Medernach, 19.12.2000 - First implementation
// --------------------------------------------------------------------
#define POLEPSILON 1e-12
#define POLINFINITY 9.0E99
#define ITERATION 12 // 20 But 8 is really enough for Newton with a good guess
#define POLEPSILON 1e-12
#define POLINFINITY 9.0E99
#define ITERATION 12 // 20 But 8 is really enough for Newton with a good guess
template <class T, class F>
G4PolynomialSolver<T,F>::G4PolynomialSolver (T* typeF, F func, F deriv,
G4PolynomialSolver<T, F>::G4PolynomialSolver(T* typeF, F func, F deriv,
G4double precision)
{
Precision = precision ;
FunctionClass = typeF ;
Function = func ;
Derivative = deriv ;
Precision = precision;
FunctionClass = typeF;
Function = func;
Derivative = deriv;
}
template <class T, class F>
G4PolynomialSolver<T,F>::~G4PolynomialSolver ()
{
}
G4PolynomialSolver<T, F>::~G4PolynomialSolver()
{}
template <class T, class F>
G4double G4PolynomialSolver<T,F>::solve(G4double IntervalMin,
G4double IntervalMax)
G4double G4PolynomialSolver<T, F>::solve(G4double IntervalMin,
G4double IntervalMax)
{
return Newton(IntervalMin,IntervalMax);
return Newton(IntervalMin, IntervalMax);
}
/* If we want to be general this could work for any
polynomial of order more that 4 if we find the (ORDER + 1)
control points
@@ -64,155 +60,165 @@ G4double G4PolynomialSolver<T,F>::solve(G4double IntervalMin,
#define NBBEZIER 5
template <class T, class F>
G4int
G4PolynomialSolver<T,F>::BezierClipping(/*T* typeF,F func,F deriv,*/
G4double *IntervalMin,
G4double *IntervalMax)
G4int G4PolynomialSolver<T, F>::BezierClipping(/*T* typeF,F func,F deriv,*/
G4double* IntervalMin,
G4double* IntervalMax)
{
/** BezierClipping is a clipping interval Newton method **/
/** It works by clipping the area where the polynomial is **/
G4double P[NBBEZIER][2],D[2];
G4double NewMin,NewMax;
G4double P[NBBEZIER][2], D[2];
G4double NewMin, NewMax;
G4int IntervalIsVoid = 1;
/*** Calculating Control Points ***/
/* We see the polynomial as a Bezier curve for some control points to find */
/*
For 5 control points (polynomial of degree 4) this is:
0 p0 = F((*IntervalMin))
1/4 p1 = F((*IntervalMin)) + ((*IntervalMax) - (*IntervalMin))/4
* F'((*IntervalMin))
2/4 p2 = 1/6 * (16*F(((*IntervalMax) + (*IntervalMin))/2)
- (p0 + 4*p1 + 4*p3 + p4))
- (p0 + 4*p1 + 4*p3 + p4))
3/4 p3 = F((*IntervalMax)) - ((*IntervalMax) - (*IntervalMin))/4
* F'((*IntervalMax))
1 p4 = F((*IntervalMax))
*/
*/
/* x,y,z,dx,dy,dz are constant during searching */
D[0] = (FunctionClass->*Derivative)(*IntervalMin);
P[0][0] = (*IntervalMin);
P[0][1] = (FunctionClass->*Function)(*IntervalMin);
if (std::fabs(P[0][1]) < Precision) {
return 1;
}
if (((*IntervalMax) - (*IntervalMin)) < POLEPSILON) {
if(std::fabs(P[0][1]) < Precision)
{
return 1;
}
P[1][0] = (*IntervalMin) + ((*IntervalMax) - (*IntervalMin))/4;
P[1][1] = P[0][1] + (((*IntervalMax) - (*IntervalMin))/4.0) * D[0];
if(((*IntervalMax) - (*IntervalMin)) < POLEPSILON)
{
return 1;
}
P[1][0] = (*IntervalMin) + ((*IntervalMax) - (*IntervalMin)) / 4;
P[1][1] = P[0][1] + (((*IntervalMax) - (*IntervalMin)) / 4.0) * D[0];
D[1] = (FunctionClass->*Derivative)(*IntervalMax);
P[4][0] = (*IntervalMax);
P[4][1] = (FunctionClass->*Function)(*IntervalMax);
P[3][0] = (*IntervalMax) - ((*IntervalMax) - (*IntervalMin))/4;
P[3][1] = P[4][1] - ((*IntervalMax) - (*IntervalMin))/4 * D[1];
P[2][0] = ((*IntervalMax) + (*IntervalMin))/2;
P[2][1] = (16*(FunctionClass->*Function)(((*IntervalMax)+(*IntervalMin))/2)
- (P[0][1] + 4*P[1][1] + 4*P[3][1] + P[4][1]))/6 ;
P[3][0] = (*IntervalMax) - ((*IntervalMax) - (*IntervalMin)) / 4;
P[3][1] = P[4][1] - ((*IntervalMax) - (*IntervalMin)) / 4 * D[1];
P[2][0] = ((*IntervalMax) + (*IntervalMin)) / 2;
P[2][1] =
(16 * (FunctionClass->*Function)(((*IntervalMax) + (*IntervalMin)) / 2) -
(P[0][1] + 4 * P[1][1] + 4 * P[3][1] + P[4][1])) /
6;
{
G4double Intersection ;
G4int i,j;
NewMin = (*IntervalMax) ;
NewMax = (*IntervalMin) ;
G4double Intersection;
G4int i, j;
for (i=0;i<5;i++)
for (j=i+1;j<5;j++)
{
/* there is an intersection only if each have different signs */
if (((P[j][1] > -Precision) && (P[i][1] < Precision)) ||
((P[j][1] < Precision) && (P[i][1] > -Precision))) {
IntervalIsVoid = 0;
Intersection = P[j][0] - P[j][1]*((P[i][0] - P[j][0])/
(P[i][1] - P[j][1]));
if (Intersection < NewMin) {
NewMin = Intersection;
}
if (Intersection > NewMax) {
NewMax = Intersection;
}
}
}
NewMin = (*IntervalMax);
NewMax = (*IntervalMin);
if (IntervalIsVoid != 1) {
for(i = 0; i < 5; ++i)
for(j = i + 1; j < 5; ++j)
{
/* there is an intersection only if each have different signs */
if(((P[j][1] > -Precision) && (P[i][1] < Precision)) ||
((P[j][1] < Precision) && (P[i][1] > -Precision)))
{
IntervalIsVoid = 0;
Intersection =
P[j][0] - P[j][1] * ((P[i][0] - P[j][0]) / (P[i][1] - P[j][1]));
if(Intersection < NewMin)
{
NewMin = Intersection;
}
if(Intersection > NewMax)
{
NewMax = Intersection;
}
}
}
if(IntervalIsVoid != 1)
{
(*IntervalMax) = NewMax;
(*IntervalMin) = NewMin;
}
}
if (IntervalIsVoid == 1) {
if(IntervalIsVoid == 1)
{
return -1;
}
return 0;
}
template <class T, class F>
G4double G4PolynomialSolver<T,F>::Newton (G4double IntervalMin,
G4double G4PolynomialSolver<T, F>::Newton(G4double IntervalMin,
G4double IntervalMax)
{
/* So now we have a good guess and an interval where
if there are an intersection the root must be */
G4double Value = 0;
G4double Value = 0;
G4double Gradient = 0;
G4double Lambda ;
G4double Lambda;
G4int i = 0;
G4int j = 0;
G4int i=0;
G4int j=0;
/* Reduce interval before applying Newton Method */
{
G4int NewtonIsSafe ;
G4int NewtonIsSafe;
while ((NewtonIsSafe = BezierClipping(&IntervalMin,&IntervalMax)) == 0) ;
while((NewtonIsSafe = BezierClipping(&IntervalMin, &IntervalMax)) == 0)
;
if (NewtonIsSafe == -1) {
if(NewtonIsSafe == -1)
{
return POLINFINITY;
}
}
Lambda = IntervalMin;
Value = (FunctionClass->*Function)(Lambda);
Value = (FunctionClass->*Function)(Lambda);
// while ((std::fabs(Value) > Precision)) {
while (j != -1) {
while(j != -1)
{
Value = (FunctionClass->*Function)(Lambda);
Gradient = (FunctionClass->*Derivative)(Lambda);
Lambda = Lambda - Value/Gradient ;
Lambda = Lambda - Value / Gradient;
if (std::fabs(Value) <= Precision) {
j ++;
if (j == 2) {
j = -1;
}
} else {
i ++;
if (i > ITERATION)
return POLINFINITY;
}
if(std::fabs(Value) <= Precision)
{
++j;
if(j == 2)
{
j = -1;
}
}
else
{
++i;
if(i > ITERATION)
return POLINFINITY;
}
}
return Lambda ;
return Lambda;
}
@@ -23,97 +23,67 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4SimpleIntegration
//
// Class description:
//
// Class for realisation of simple numerical methodes for integration of
// functions with signature: double f(double). The methods based mainly on
// algorithms given in the book :
// algorithms given in the book:
// An introduction to NUMERICAL METHODS IN C++,
// B.H. Flowers, Claredon Press, Oxford, 1995.
//
// --------------------------- Member data ----------------------------
//
// fFunction - pointer to the function to be integrated
// fTolerance - accuracy of integration in Adaptive Gauss method
// fMaxDepth = 100 - constant maximum iteration depth for
// Adaptive Gauss method
//
// --------------------------- Methods --------------------------------
//
// Trapezoidal, MidPoint, Gauss and Simpson(double a,double b,int n)
// - integrate function pointed by fFunction from a to b by n iterations,
// i.e. with Step (b-a)/n according to the correspondent method.
//
// AdaptGausIntegration(double a, double b)
// - integrate function from a to be with accuracy <= fTolerance
// ----------------------------- History ------------------------------
//
// 26.03.97 V.Grichine ( Vladimir.Grichine@cern.ch )
// Author: V.Grichine, 26.03.1997
// --------------------------------------------------------------------
#ifndef G4SIMPLEINTEGRATION_HH
#define G4SIMPLEINTEGRATION_HH
#define G4SIMPLEINTEGRATION_HH 1
#include "G4Types.hh"
typedef G4double (*function)(G4double) ;
typedef G4double (*function)(G4double);
class G4SimpleIntegration
{
public:
public:
explicit G4SimpleIntegration(function pFunction);
explicit G4SimpleIntegration( function pFunction ) ;
G4SimpleIntegration( function pFunction,
G4double pTolerance ) ;
~G4SimpleIntegration() ;
// Simple integration methods
G4double Trapezoidal(G4double xInitial,
G4double xFinal,
G4int iterationNumber ) ;
G4SimpleIntegration(function pFunction, G4double pTolerance);
G4double MidPoint(G4double xInitial,
G4double xFinal,
G4int iterationNumber ) ;
~G4SimpleIntegration();
G4double Gauss(G4double xInitial,
G4double xFinal,
G4int iterationNumber ) ;
G4SimpleIntegration(const G4SimpleIntegration&) = delete;
G4SimpleIntegration& operator=(const G4SimpleIntegration&) = delete;
// Private copy constructor and assignment operator.
G4double Simpson(G4double xInitial,
G4double xFinal,
G4int iterationNumber ) ;
// Simple integration methods:
// Trapezoidal, MidPoint, Gauss and Simpson(double a,double b,int n)
// - integrate function pointed by fFunction from a to b by n iterations,
// i.e. with Step (b-a)/n according to the correspondent method.
// Adaptive Gauss integration with accuracy ~ fTolerance
G4double Trapezoidal(G4double xInitial, G4double xFinal,
G4int iterationNumber);
G4double AdaptGaussIntegration( G4double xInitial,
G4double xFinal ) ;
protected:
G4double MidPoint(G4double xInitial, G4double xFinal, G4int iterationNumber);
G4double Gauss( G4double xInitial,
G4double xFinal ) ;
G4double Gauss(G4double xInitial, G4double xFinal, G4int iterationNumber);
void AdaptGauss( G4double xInitial,
G4double xFinal,
G4double& sum,
G4int& depth ) ;
private:
G4double Simpson(G4double xInitial, G4double xFinal, G4int iterationNumber);
G4SimpleIntegration(const G4SimpleIntegration&);
G4SimpleIntegration& operator=(const G4SimpleIntegration&);
// Private copy constructor and assignment operator.
// Adaptive Gauss integration with accuracy ~ fTolerance
private:
G4double AdaptGaussIntegration(G4double xInitial, G4double xFinal);
// Integrate function from a to be with accuracy <= fTolerance
function fFunction ;
G4double fTolerance ;
const G4int fMaxDepth ;
protected:
G4double Gauss(G4double xInitial, G4double xFinal);
void AdaptGauss(G4double xInitial, G4double xFinal, G4double& sum,
G4int& depth);
private:
function fFunction; // pointer to the function to be integrated
G4double fTolerance = 0.0001; // accuracy of integration
const G4int fMaxDepth = 100; // constant maximum iteration depth
};
#endif
@@ -23,7 +23,7 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4SimplexDownhill
//
// Class description:
//
@@ -34,75 +34,75 @@
// by William H., Cambridge University Press ISBN 0521437202 (1992)
// Author: Tatsumi Koi (SLAC/SCCS), 2007
// --------------------------------------------------------------------------
// --------------------------------------------------------------------
#ifndef G4SimplexDownhill_hh
#define G4SimplexDownhill_hh
#define G4SimplexDownhill_hh 1
#include "globals.hh"
#include <vector>
#include <algorithm>
#include <algorithm>
#include <vector>
template<class T>
template <class T>
class G4SimplexDownhill
{
public:
G4SimplexDownhill(T* tp, G4int n)
: currentValue(0.)
, target(tp)
, numberOfVariable(n)
{
init();
}
public: // with description
~G4SimplexDownhill();
G4SimplexDownhill( T* tp , G4int n )
: currentValue(0.), target(tp), numberOfVariable(n)
{ init(); }
G4double GetMinimum();
~G4SimplexDownhill();
std::vector<G4double> GetMinimumPoint();
G4double GetMinimum();
private:
G4double getValue(std::vector<G4double> x)
{
return target->GetValueOfMinimizingFunction(x);
}
std::vector< G4double > GetMinimumPoint();
void initialize();
std::vector<std::vector<G4double>> currentSimplex;
void calHeights();
std::vector<G4double> currentHeights;
G4double currentValue;
private:
std::vector<G4double> calCentroid(G4int);
G4double getValue( std::vector< G4double > x )
{ return target->GetValueOfMinimizingFunction( x ); }
G4bool isItGoodEnough();
void initialize();
std::vector< std::vector< G4double > > currentSimplex;
std::vector<G4double> getReflectionPoint(std::vector<G4double>,
std::vector<G4double>);
std::vector<G4double> getExpansionPoint(std::vector<G4double>,
std::vector<G4double>);
std::vector<G4double> getContractionPoint(std::vector<G4double>,
std::vector<G4double>);
void calHeights();
std::vector< G4double > currentHeights;
G4double currentValue;
void doDownhill();
std::vector< G4double > calCentroid( G4int );
void init();
G4bool isItGoodEnough();
private:
T* target;
std::vector< G4double > getReflectionPoint( std::vector< G4double > ,
std::vector< G4double > );
std::vector< G4double > getExpansionPoint( std::vector< G4double > ,
std::vector< G4double > );
std::vector< G4double > getContractionPoint( std::vector< G4double > ,
std::vector< G4double > );
G4int numberOfVariable;
void doDownhill();
G4double alpha;
G4double beta;
G4double gamma;
G4double max_se;
G4double max_ratio;
G4int maximum_no_trial;
G4bool minimized;
void init();
private:
T* target;
G4int numberOfVariable;
G4double alpha;
G4double beta;
G4double gamma;
G4double max_se;
G4double max_ratio;
G4int maximum_no_trial;
G4bool minimized;
std::vector< G4double > minimumPoint;
std::vector<G4double> minimumPoint;
};
#include "G4SimplexDownhill.icc"
@@ -23,419 +23,344 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4SimplexDownhill inline methods implementation
//
// Author: Tatsumi Koi (SLAC/SCCS), 2007
// --------------------------------------------------------------------------
#include <cfloat>
#include <iostream>
#include <numeric>
#include <cfloat>
template<class T> void G4SimplexDownhill<T>::init()
template <class T>
void G4SimplexDownhill<T>::init()
{
alpha = 2.0; // refrection coefficient: 0 < alpha
beta = 0.5; // contraction coefficient: 0 < beta < 1
gamma = 2.0; // expantion coefficient: 1 < gamma
alpha = 2.0; // refrection coefficient: 0 < alpha
beta = 0.5; // contraction coefficient: 0 < beta < 1
gamma = 2.0; // expantion coefficient: 1 < gamma
maximum_no_trial = 10000;
max_se = FLT_MIN;
//max_ratio = FLT_EPSILON/1;
max_ratio = DBL_EPSILON/1;
minimized = false;
maximum_no_trial = 10000;
max_se = FLT_MIN;
// max_ratio = FLT_EPSILON/1;
max_ratio = DBL_EPSILON / 1;
minimized = false;
}
/*
void G4SimplexDownhill<class T>::
SetFunction( G4int n , G4double( *afunc )( std::vector < G4double > ) )
SetFunction( G4int n , G4double( *afunc )( std::vector < G4double > ) )
{
numberOfVariable = n;
numberOfVariable = n;
theFunction = afunc;
minimized = false;
minimized = false;
}
*/
template<class T>
template <class T>
G4double G4SimplexDownhill<T>::GetMinimum()
{
initialize();
initialize();
// First Tryal;
// First Tryal;
//G4cout << "Begin First Trials" << G4endl;
doDownhill();
//G4cout << "End First Trials" << G4endl;
// G4cout << "Begin First Trials" << G4endl;
doDownhill();
// G4cout << "End First Trials" << G4endl;
std::vector< G4double >::iterator it_minh =
std::min_element( currentHeights.begin() , currentHeights.end() );
G4int imin = 0;
G4int i = 0;
for ( std::vector< G4double >::iterator it = currentHeights.begin();
it != currentHeights.end(); it++ )
{
if ( it == it_minh )
{
imin = i;
}
i++;
}
minimumPoint = currentSimplex[ imin ];
std::vector<G4double>::const_iterator it_minh =
std::min_element(currentHeights.cbegin(), currentHeights.cend());
G4int imin = 0;
G4int i = 0;
for(auto it = currentHeights.cbegin(); it != currentHeights.cend(); ++it)
{
if(it == it_minh)
{
imin = i;
}
++i;
}
minimumPoint = currentSimplex[imin];
// Second Trial
// Second Trial
//std::vector< G4double > minimumPoint = currentSimplex[ 0 ];
initialize();
// std::vector< G4double > minimumPoint = currentSimplex[ 0 ];
initialize();
currentSimplex[ numberOfVariable ] = minimumPoint;
currentSimplex[numberOfVariable] = minimumPoint;
//G4cout << "Begin Second Trials" << G4endl;
doDownhill();
//G4cout << "End Second Trials" << G4endl;
G4double sum = std::accumulate( currentHeights.begin() ,
currentHeights.end() , 0.0 );
G4double average = sum/(numberOfVariable+1);
G4double minimum = average;
// G4cout << "Begin Second Trials" << G4endl;
doDownhill();
// G4cout << "End Second Trials" << G4endl;
minimized = true;
G4double sum =
std::accumulate(currentHeights.begin(), currentHeights.end(), 0.0);
G4double average = sum / (numberOfVariable + 1);
G4double minimum = average;
return minimum;
minimized = true;
return minimum;
}
template<class T>
template <class T>
void G4SimplexDownhill<T>::initialize()
{
currentSimplex.resize(numberOfVariable + 1);
currentHeights.resize(numberOfVariable + 1);
currentSimplex.resize( numberOfVariable+1 );
currentHeights.resize( numberOfVariable+1 );
for ( G4int i = 0 ; i < numberOfVariable ; i++ )
{
std::vector< G4double > avec ( numberOfVariable , 0.0 );
avec[ i ] = 1.0;
currentSimplex[ i ] = avec;
}
//std::vector< G4double > avec ( numberOfVariable , 0.0 );
std::vector< G4double > avec ( numberOfVariable , 1 );
currentSimplex[ numberOfVariable ] = avec;
for(G4int i = 0; i < numberOfVariable; ++i)
{
std::vector<G4double> avec(numberOfVariable, 0.0);
avec[i] = 1.0;
currentSimplex[i] = avec;
}
// std::vector< G4double > avec ( numberOfVariable , 0.0 );
std::vector<G4double> avec(numberOfVariable, 1);
currentSimplex[numberOfVariable] = avec;
}
template<class T>
template <class T>
void G4SimplexDownhill<T>::calHeights()
{
for ( G4int i = 0 ; i <= numberOfVariable ; i++ )
{
currentHeights[i] = getValue ( currentSimplex[i] );
}
for(G4int i = 0; i <= numberOfVariable; ++i)
{
currentHeights[i] = getValue(currentSimplex[i]);
}
}
template<class T>
std::vector< G4double > G4SimplexDownhill<T>::calCentroid( G4int ih )
template <class T>
std::vector<G4double> G4SimplexDownhill<T>::calCentroid(G4int ih)
{
std::vector<G4double> centroid(numberOfVariable, 0.0);
std::vector< G4double > centroid ( numberOfVariable , 0.0 );
G4int i = 0;
for ( std::vector< std::vector< G4double > >::iterator
it = currentSimplex.begin(); it != currentSimplex.end() ; it++ )
{
if ( i != ih )
{
for ( G4int j = 0 ; j < numberOfVariable ; j++ )
{
centroid[j] += (*it)[j]/numberOfVariable;
}
}
i++;
G4int i = 0;
for(auto it = currentSimplex.cbegin(); it != currentSimplex.cend(); ++it)
{
if(i != ih)
{
for(G4int j = 0; j < numberOfVariable; ++j)
{
centroid[j] += (*it)[j] / numberOfVariable;
}
}
++i;
}
return centroid;
return centroid;
}
template<class T>
std::vector< G4double > G4SimplexDownhill<T>::
getReflectionPoint( std::vector< G4double > p ,
std::vector< G4double > centroid )
template <class T>
std::vector<G4double> G4SimplexDownhill<T>::getReflectionPoint(
std::vector<G4double> p, std::vector<G4double> centroid)
{
//G4cout << "Reflection" << G4endl;
// G4cout << "Reflection" << G4endl;
std::vector< G4double > reflectionP ( numberOfVariable , 0.0 );
std::vector<G4double> reflectionP(numberOfVariable, 0.0);
for ( G4int i = 0 ; i < numberOfVariable ; i++ )
{
reflectionP[ i ] = ( 1 + alpha ) * centroid[ i ] - alpha * p[ i ];
}
return reflectionP;
for(G4int i = 0; i < numberOfVariable; ++i)
{
reflectionP[i] = (1 + alpha) * centroid[i] - alpha * p[i];
}
return reflectionP;
}
template<class T>
std::vector< G4double > G4SimplexDownhill<T>::
getExpansionPoint( std::vector< G4double > p ,
std::vector< G4double > centroid )
template <class T>
std::vector<G4double> G4SimplexDownhill<T>::getExpansionPoint(
std::vector<G4double> p, std::vector<G4double> centroid)
{
//G4cout << "Expantion" << G4endl;
// G4cout << "Expantion" << G4endl;
std::vector< G4double > expansionP ( numberOfVariable , 0.0 );
std::vector<G4double> expansionP(numberOfVariable, 0.0);
for ( G4int i = 0 ; i < numberOfVariable ; i++ )
{
expansionP[i] = ( 1 - gamma ) * centroid[i] + gamma * p[i];
}
return expansionP;
for(G4int i = 0; i < numberOfVariable; ++i)
{
expansionP[i] = (1 - gamma) * centroid[i] + gamma * p[i];
}
return expansionP;
}
template<class T>
std::vector< G4double > G4SimplexDownhill<T>::
getContractionPoint( std::vector< G4double > p ,
std::vector< G4double > centroid )
template <class T>
std::vector<G4double> G4SimplexDownhill<T>::getContractionPoint(
std::vector<G4double> p, std::vector<G4double> centroid)
{
//G4cout << "Contraction" << G4endl;
std::vector<G4double> contractionP(numberOfVariable, 0.0);
std::vector< G4double > contractionP ( numberOfVariable , 0.0 );
for(G4int i = 0; i < numberOfVariable; ++i)
{
contractionP[i] = (1 - beta) * centroid[i] + beta * p[i];
}
for ( G4int i = 0 ; i < numberOfVariable ; i++ )
{
contractionP[i] = ( 1 - beta ) * centroid[i] + beta * p[i];
}
return contractionP;
return contractionP;
}
template<class T>
template <class T>
G4bool G4SimplexDownhill<T>::isItGoodEnough()
{
G4bool result = false;
G4bool result = false;
G4double sum = std::accumulate( currentHeights.begin() ,
currentHeights.end() , 0.0 );
G4double average = sum/(numberOfVariable+1);
//G4cout << "average " << average << G4endl;
G4double sum =
std::accumulate(currentHeights.begin(), currentHeights.end(), 0.0);
G4double average = sum / (numberOfVariable + 1);
G4double delta = 0.0;
for ( G4int i = 0 ; i <= numberOfVariable ; i++ )
{
delta += std::abs ( currentHeights[ i ] - average );
}
//G4cout << "ratio of delta to average is "
// << delta / (numberOfVariable+1) / average << G4endl;
G4double delta = 0.0;
for(G4int i = 0; i <= numberOfVariable; ++i)
{
delta += std::abs(currentHeights[i] - average);
}
if ( delta/(numberOfVariable+1)/average < max_ratio )
{
result = true;
}
/*
G4double sigma = 0.0;
G4cout << "average " << average << G4endl;
for ( G4int i = 0 ; i <= numberOfVariable ; i++ )
{
sigma += ( currentHeights[ i ] - average )
*( currentHeights[ i ] - average );
}
if(delta / (numberOfVariable + 1) / average < max_ratio)
{
result = true;
}
G4cout << "standard error of hs "
<< std::sqrt ( sigma ) / (numberOfVariable+1) << G4endl;
if ( std::sqrt ( sigma ) / (numberOfVariable+1) < max_se )
{
result = true;
}
*/
return result;
return result;
}
template<class T>
template <class T>
void G4SimplexDownhill<T>::doDownhill()
{
G4int nth_trial = 0;
G4int nth_trial = 0;
while(nth_trial < maximum_no_trial)
{
calHeights();
while ( nth_trial < maximum_no_trial )
{
if(isItGoodEnough())
{
break;
}
/*
G4cout << "Begining " << nth_trial << "th trial " << G4endl;
for ( G4int j = 0 ; j <= numberOfVariable ; j++ )
std::vector<G4double>::const_iterator it_maxh =
std::max_element(currentHeights.cbegin(), currentHeights.cend());
std::vector<G4double>::const_iterator it_minh =
std::min_element(currentHeights.cbegin(), currentHeights.cend());
G4double h_H = *it_maxh;
G4double h_L = *it_minh;
G4int ih = 0;
G4int il = 0;
G4double h_H2 = 0.0;
G4int i = 0;
for(auto it = currentHeights.cbegin(); it != currentHeights.cend(); ++it)
{
if(it == it_maxh)
{
G4cout << "SimplexPoint " << j << ": ";
for ( G4int i = 0 ; i < numberOfVariable ; i++ )
{
G4cout << currentSimplex[j][i]
<< " ";
}
G4cout << G4endl;
ih = i;
}
*/
calHeights();
if ( isItGoodEnough() )
{
break;
else
{
h_H2 = std::max(h_H2, *it);
}
std::vector< G4double >::iterator it_maxh =
std::max_element( currentHeights.begin() , currentHeights.end() );
std::vector< G4double >::iterator it_minh =
std::min_element( currentHeights.begin() , currentHeights.end() );;
G4double h_H = *it_maxh;
G4double h_L = *it_minh;
G4int ih = 0;;
G4int il = 0;
G4double h_H2 =0.0;
G4int i = 0;
for ( std::vector< G4double >::iterator
it = currentHeights.begin(); it != currentHeights.end(); it++ )
if(it == it_minh)
{
if ( it == it_maxh )
{
ih = i;
}
else
{
h_H2 = std::max( h_H2 , *it );
}
if ( it == it_minh )
{
il = i;
}
i++;
il = i;
}
++i;
}
//G4cout << "max " << h_H << " " << ih << G4endl;
//G4cout << "max-dash " << h_H2 << G4endl;
//G4cout << "min " << h_L << " " << il << G4endl;
std::vector<G4double> centroidPoint = calCentroid(ih);
std::vector< G4double > centroidPoint = calCentroid ( ih );
// REFLECTION
std::vector<G4double> reflectionPoint =
getReflectionPoint(currentSimplex[ih], centroidPoint);
// REFLECTION
std::vector< G4double > reflectionPoint =
getReflectionPoint( currentSimplex[ ih ] , centroidPoint );
G4double h = getValue(reflectionPoint);
G4double h = getValue( reflectionPoint );
if ( h <= h_L )
{
if(h <= h_L)
{
// EXPANSION
std::vector< G4double > expansionPoint =
getExpansionPoint( reflectionPoint , centroidPoint );
G4double hh = getValue( expansionPoint );
if ( hh <= h_L )
{
// Replace
currentSimplex[ ih ] = expansionPoint;
//G4cout << "A" << G4endl;
}
else
{
// Replace
currentSimplex[ ih ] = reflectionPoint;
//G4cout << "B1" << G4endl;
}
}
else
std::vector<G4double> expansionPoint =
getExpansionPoint(reflectionPoint, centroidPoint);
G4double hh = getValue(expansionPoint);
if(hh <= h_L)
{
if ( h <= h_H2 )
{
// Replace
currentSimplex[ ih ] = reflectionPoint;
//G4cout << "B2" << G4endl;
}
else
{
if ( h <= h_H )
{
// Replace
currentSimplex[ ih ] = reflectionPoint;
//G4cout << "BC" << G4endl;
}
// CONTRACTION
std::vector< G4double > contractionPoint =
getContractionPoint( currentSimplex[ ih ] , centroidPoint );
G4double hh = getValue( contractionPoint );
if ( hh <= h_H )
{
// Replace
currentSimplex[ ih ] = contractionPoint;
//G4cout << "C" << G4endl;
}
else
{
// Replace
for ( G4int j = 0 ; j <= numberOfVariable ; j++ )
{
std::vector< G4double > vec ( numberOfVariable , 0.0 );
for ( G4int k = 0 ; k < numberOfVariable ; k++ )
{
vec[ k ] = ( currentSimplex[ j ][ k ]
+ currentSimplex[ il ][ k ] ) / 2.0;
}
currentSimplex[ j ] = vec;
}
//G4cout << "D" << G4endl;
}
}
// Replace
currentSimplex[ih] = expansionPoint;
// G4cout << "A" << G4endl;
}
else
{
// Replace
currentSimplex[ih] = reflectionPoint;
// G4cout << "B1" << G4endl;
}
}
else
{
if(h <= h_H2)
{
// Replace
currentSimplex[ih] = reflectionPoint;
// G4cout << "B2" << G4endl;
}
else
{
if(h <= h_H)
{
// Replace
currentSimplex[ih] = reflectionPoint;
// G4cout << "BC" << G4endl;
}
// CONTRACTION
std::vector<G4double> contractionPoint =
getContractionPoint(currentSimplex[ih], centroidPoint);
G4double hh = getValue(contractionPoint);
if(hh <= h_H)
{
// Replace
currentSimplex[ih] = contractionPoint;
// G4cout << "C" << G4endl;
}
else
{
// Replace
for(G4int j = 0; j <= numberOfVariable; ++j)
{
std::vector<G4double> vec(numberOfVariable, 0.0);
for(G4int k = 0; k < numberOfVariable; ++k)
{
vec[k] = (currentSimplex[j][k] + currentSimplex[il][k]) / 2.0;
}
currentSimplex[j] = vec;
}
}
}
}
nth_trial++;
}
++nth_trial;
}
}
template<class T>
std::vector< G4double > G4SimplexDownhill<T>::GetMinimumPoint()
template <class T>
std::vector<G4double> G4SimplexDownhill<T>::GetMinimumPoint()
{
if ( minimized != true )
{
GetMinimum();
}
if(minimized != true)
{
GetMinimum();
}
std::vector< G4double >::iterator it_minh =
std::min_element( currentHeights.begin() , currentHeights.end() );;
G4int imin = 0;
G4int i = 0;
for ( std::vector< G4double >::iterator
it = currentHeights.begin(); it != currentHeights.end(); it++ )
{
if ( it == it_minh )
{
imin = i;
}
i++;
}
minimumPoint = currentSimplex[ imin ];
std::vector<G4double>::const_iterator it_minh =
std::min_element(currentHeights.cbegin(), currentHeights.cend());
return minimumPoint;
G4int imin = 0;
G4int i = 0;
for(auto it = currentHeights.cbegin(); it != currentHeights.cend(); ++it)
{
if(it == it_minh)
{
imin = i;
}
++i;
}
minimumPoint = currentSimplex[imin];
return minimumPoint;
}
@@ -23,159 +23,144 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
//
//
// ----------------------------------------------------------------------
// Class G4StatAnalysis
// G4StatAnalysis
//
// Class description:
//
// Class for statistical analysis of random variable
//
// Adapted
// Adapted from:
// Lux, I.
// Monte Carlo particle transport methods: neutron and photon
// calculations/authors, Ivan Lux and Laszlo Koblinger.
// ISBN 0-8493-6074-9
// 1. Neutron transport theory. 2. Photon transport theory.
// 3. Monte Carlo method. I. Koblinger, Laszlo. II. Title.
// QC793.5.N4628L88 1990
// 530.1 '38—dc20
//
// https://gnssn.iaea.org/NSNI/Shared%20Documents/OPEN%20Shared%20Files/MonteCarloParticleTransportMethodsNeutronAndPhotonCalculations.pdf
//
//
// QC793.5.N4628L88 1990 530.1 '38'20
#ifndef G4StatAnalysis_hh_
#define G4StatAnalysis_hh_
// Author: J.Madsen, 25.10.2018
// --------------------------------------------------------------------
#ifndef G4StatAnalysis_hh
#define G4StatAnalysis_hh 1
//----------------------------------------------------------------------------//
#include <iostream>
#include <iomanip>
#include <limits>
#include <fstream>
#include <cmath>
#include <fstream>
#include <iomanip>
#include <iostream>
#include <limits>
#include "globals.hh"
#include "tls.hh"
#include "G4Types.hh"
#include "G4Timer.hh"
#include "G4ios.hh"
#include "G4Allocator.hh"
#include "G4Timer.hh"
#include "G4Types.hh"
#include "G4ios.hh"
class G4StatAnalysis
{
public:
inline G4StatAnalysis();
inline ~G4StatAnalysis() { }
public:
inline G4StatAnalysis();
inline ~G4StatAnalysis() {}
public:
// Accumulated values
inline G4double GetMean() const;
inline const G4double& GetSum() const;
inline const G4double& GetSumSquared() const;
inline const G4double& GetSum1() const;
inline const G4double& GetSum2() const;
inline const G4int& GetHits() const;
inline G4int GetNumNonZero() const;
inline G4int GetNumZero() const;
// Accumulated values
inline G4double GetMean() const;
inline const G4double& GetSum() const;
inline const G4double& GetSumSquared() const;
inline const G4double& GetSum1() const;
inline const G4double& GetSum2() const;
inline const G4int& GetHits() const;
inline G4int GetNumNonZero() const;
inline G4int GetNumZero() const;
// Some control over accumulated variables
inline void SetSum(const G4double& val);
inline void SetSumSquared(const G4double& val);
inline void SetSum1(const G4double& val);
inline void SetSum2(const G4double& val);
inline void SetHits(const G4int& val);
inline void SetZero(const G4int& val);
// Some control over accumulated variables
inline void SetSum(const G4double& val);
inline void SetSumSquared(const G4double& val);
inline void SetSum1(const G4double& val);
inline void SetSum2(const G4double& val);
inline void SetHits(const G4int& val);
inline void SetZero(const G4int& val);
// Computed values
inline G4double GetFOM() const;
inline G4double GetRelativeError() const;
inline G4double GetStdDev() const;
inline G4double GetVariance() const;
inline G4double GetCoeffVariation() const;
inline G4double GetEfficiency() const;
inline G4double GetR2Int() const;
inline G4double GetR2Eff() const;
// Computed values
inline G4double GetFOM() const;
inline G4double GetRelativeError() const;
inline G4double GetStdDev() const;
inline G4double GetVariance() const;
inline G4double GetCoeffVariation() const;
inline G4double GetEfficiency() const;
inline G4double GetR2Int() const;
inline G4double GetR2Eff() const;
// Conversion
inline operator G4double() const;
// Conversion
inline operator G4double() const;
// Modifications
inline void Reset();
inline void Add(const G4double& _val, const G4double& _weight = 1.0);
inline void Rescale(const G4double& factor);
// Modifications
inline void Reset();
inline void Add(const G4double& _val, const G4double& _weight = 1.0);
inline void Rescale(const G4double& factor);
// Output
inline void PrintInfo(std::ostream& os, const std::string& = "") const;
// Output
inline void PrintInfo(std::ostream& os, const std::string& = "") const;
// Operators
inline G4StatAnalysis& operator+=(const G4double& _val);
inline G4StatAnalysis& operator/=(const G4double& _val);
inline G4StatAnalysis& operator+=(const G4StatAnalysis&);
inline G4StatAnalysis& operator-=(const G4StatAnalysis&);
// Operators
inline G4StatAnalysis& operator+=(const G4double& _val);
inline G4StatAnalysis& operator/=(const G4double& _val);
inline G4StatAnalysis& operator+=(const G4StatAnalysis&);
inline G4StatAnalysis& operator-=(const G4StatAnalysis&);
// Allocators
inline void* operator new(size_t);
inline void operator delete(void*);
// Allocators
inline void* operator new(std::size_t);
inline void operator delete(void*);
// Timing (member functions)
inline G4double GetCpuTime() const;
// Timing (static functions)
static tms*& GetCpuClock()
// Timing (member functions)
inline G4double GetCpuTime() const;
// Timing (static functions)
static tms*& GetCpuClock()
{
G4ThreadLocalStatic tms* _instance = nullptr;
if(!_instance)
{
G4ThreadLocalStatic tms* _instance = nullptr;
if(!_instance)
{
_instance = new tms;
times(_instance);
}
return _instance;
}
// Note: this above implementation was implemented in such a way as to
// conserve memory by eliminated every instance from requiring their own
// timing variables. The ResetCpuClock function below is called at the
// beginning of the run (G4Run constructor) to attempt to ensure the
// FOM is not skewed by multiple runs -- it may be necessary to
// manually invoke in some situations
static void ResetCpuClock()
{
tms*& _clock = GetCpuClock();
times(_clock);
_instance = new tms;
times(_instance);
}
return _instance;
}
// Note: this above implementation was implemented in such a way as to
// conserve memory by eliminated every instance from requiring their own
// timing variables. The ResetCpuClock function below is called at the
// beginning of the run (G4Run constructor) to attempt to ensure the
// FOM is not skewed by multiple runs -- it may be necessary to
// manually invoke in some situations
static void ResetCpuClock()
{
tms*& _clock = GetCpuClock();
times(_clock);
}
private:
// summation of each history^1
G4double fSum1;
// summation from each history^2
G4double fSum2;
// number of scoring histories
G4int fHits;
// number of histories that were not greater than 0.0
G4int fZero;
// friend operator for output
friend std::ostream& operator<<(std::ostream& os, const G4StatAnalysis& obj)
{
obj.PrintInfo(os);
return os;
}
// friend operator for addition
friend const G4StatAnalysis operator+(const G4StatAnalysis& lhs,
const G4StatAnalysis& rhs)
{
return G4StatAnalysis(lhs) += rhs;
}
// friend operator for subtraction
friend const G4StatAnalysis operator-(const G4StatAnalysis& lhs,
const G4StatAnalysis& rhs)
{
return G4StatAnalysis(lhs) -= rhs;
}
public:
// friend operator for output
friend std::ostream& operator<<(std::ostream& os, const G4StatAnalysis& obj)
{
obj.PrintInfo(os);
return os;
}
// friend operator for addition
friend const G4StatAnalysis operator+(const G4StatAnalysis& lhs,
const G4StatAnalysis& rhs)
{
return G4StatAnalysis(lhs) += rhs;
}
// friend operator for subtraction
friend const G4StatAnalysis operator-(const G4StatAnalysis& lhs,
const G4StatAnalysis& rhs)
{
return G4StatAnalysis(lhs) -= rhs;
}
private:
G4double fSum1 = 0.0; // summation of each history^1
G4double fSum2 = 0.0; // summation from each history^2
G4int fHits = 0; // number of scoring histories
G4int fZero = 0; // number of histories that were not greater than 0.0
};
#include "G4StatAnalysis.icc"
@@ -23,397 +23,320 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
// G4StatAnalysis inline methods implementation
//
//
//
// ----------------------------------------------------------------------
// Class typename G4StatAnalysis
//
// Class description:
//
// Class for statistical analysis of random variable
//
// Adapted
// Lux, I.
// Monte Carlo particle transport methods: neutron and photon
// calculations/authors, Ivan Lux and Laszlo Koblinger.
// ISBN 0-8493-6074-9
// 1. Neutron transport theory. 2. Photon transport theory.
// 3. Monte Carlo method. I. Koblinger, Laszlo. II. Title.
// QC793.5.N4628L88 1990
// 530.1 '38—dc20
//
// https://gnssn.iaea.org/NSNI/Shared%20Documents/OPEN%20Shared%20Files/MonteCarloParticleTransportMethodsNeutronAndPhotonCalculations.pdf
//
//
// Author: J.Madsen, 25.10.2018
// --------------------------------------------------------------------
#include <iostream>
#include <iomanip>
#include <limits>
#include <fstream>
#include <cmath>
#include <fstream>
#include <iomanip>
#include <iostream>
#include <limits>
#include "globals.hh"
#include "tls.hh"
#include "G4Timer.hh"
#include "G4ios.hh"
#include "globals.hh"
#include "tls.hh"
#include "G4Types.hh"
#include "G4Allocator.hh"
#include "G4Types.hh"
//----------------------------------------------------------------------------//
G4StatAnalysis::G4StatAnalysis()
: fSum1(0.0),
fSum2(0.0),
fHits(0),
fZero(0)
{ }
G4StatAnalysis::G4StatAnalysis() {}
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetMean() const
{
return (fHits > 0) ? fSum1/((G4double) fHits) : 0.;
return (fHits > 0) ? fSum1 / ((G4double) fHits) : 0.;
}
//----------------------------------------------------------------------------//
const G4double& G4StatAnalysis::GetSum() const
{
return fSum1;
}
const G4double& G4StatAnalysis::GetSum() const { return fSum1; }
//----------------------------------------------------------------------------//
const G4double& G4StatAnalysis::GetSumSquared() const
{
return fSum2;
}
const G4double& G4StatAnalysis::GetSumSquared() const { return fSum2; }
//----------------------------------------------------------------------------//
const G4double& G4StatAnalysis::GetSum1() const
{
return fSum1;
}
const G4double& G4StatAnalysis::GetSum1() const { return fSum1; }
//----------------------------------------------------------------------------//
const G4double& G4StatAnalysis::GetSum2() const
{
return fSum2;
}
const G4double& G4StatAnalysis::GetSum2() const { return fSum2; }
//----------------------------------------------------------------------------//
const G4int& G4StatAnalysis::GetHits() const
{
return fHits;
}
const G4int& G4StatAnalysis::GetHits() const { return fHits; }
//----------------------------------------------------------------------------//
G4int G4StatAnalysis::GetNumNonZero() const
{
return fHits - fZero;
}
G4int G4StatAnalysis::GetNumNonZero() const { return fHits - fZero; }
//----------------------------------------------------------------------------//
G4int G4StatAnalysis::GetNumZero() const
{
return fZero;
}
G4int G4StatAnalysis::GetNumZero() const { return fZero; }
//----------------------------------------------------------------------------//
void G4StatAnalysis::SetSum(const G4double& val)
{
fSum1 = val;
}
void G4StatAnalysis::SetSum(const G4double& val) { fSum1 = val; }
//----------------------------------------------------------------------------//
void G4StatAnalysis::SetSumSquared(const G4double& val)
{
fSum2 = val;
}
void G4StatAnalysis::SetSumSquared(const G4double& val) { fSum2 = val; }
//----------------------------------------------------------------------------//
void G4StatAnalysis::SetSum1(const G4double& val)
{
fSum1 = val;
}
void G4StatAnalysis::SetSum1(const G4double& val) { fSum1 = val; }
//----------------------------------------------------------------------------//
void G4StatAnalysis::SetSum2(const G4double& val)
{
fSum2 = val;
}
void G4StatAnalysis::SetSum2(const G4double& val) { fSum2 = val; }
//----------------------------------------------------------------------------//
void G4StatAnalysis::SetHits(const G4int& val)
{
fHits = val;
}
void G4StatAnalysis::SetHits(const G4int& val) { fHits = val; }
//----------------------------------------------------------------------------//
void G4StatAnalysis::SetZero(const G4int& val)
{
fZero = val;
}
void G4StatAnalysis::SetZero(const G4int& val) { fZero = val; }
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetFOM() const
{
G4double elapsed_time = this->GetCpuTime();
G4double relative_err = this->GetRelativeError();
// lambda for equation clarity (will be inlined)
auto compute_figure_of_merit = [&] ()
{
return ( 1.0 / ( relative_err * relative_err ) / elapsed_time );
};
return (std::fabs(relative_err) > 0.0 && elapsed_time > 0.0)
? compute_figure_of_merit() : ((fHits > 0) ? 1.0 : 0.0);
G4double elapsed_time = this->GetCpuTime();
G4double relative_err = this->GetRelativeError();
// lambda for equation clarity (will be inlined)
auto compute_figure_of_merit = [&]() {
return (1.0 / (relative_err * relative_err) / elapsed_time);
};
return (std::fabs(relative_err) > 0.0 && elapsed_time > 0.0)
? compute_figure_of_merit()
: ((fHits > 0) ? 1.0 : 0.0);
}
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetRelativeError() const
{
// lambda for equation clarity (will be inlined)
auto compute_relative_error = [&] ()
{
return ( GetStdDev() / GetMean() / std::sqrt((G4double) fHits) );
};
return (std::fabs(GetMean()) > 0 && fHits > 0)
? compute_relative_error() : ((fHits > 0) ? 1.0 : 0.0);
// lambda for equation clarity (will be inlined)
auto compute_relative_error = [&]() {
return (GetStdDev() / GetMean() / std::sqrt((G4double) fHits));
};
return (std::fabs(GetMean()) > 0 && fHits > 0) ? compute_relative_error()
: ((fHits > 0) ? 1.0 : 0.0);
}
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetStdDev() const
{
return ::sqrt(std::fabs(GetVariance()));
return ::sqrt(std::fabs(GetVariance()));
}
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetVariance() const
{
// lambda for equation clarity (will be inlined)
auto compute_variance = [&] ()
{
return ((fSum2 - (std::pow(fSum1, 2.0)/fHits))/(((G4double) fHits) - 1.0));
};
return (fHits > 1) ? compute_variance() : 0.0;
// lambda for equation clarity (will be inlined)
auto compute_variance = [&]() {
return ((fSum2 - (std::pow(fSum1, 2.0) / fHits)) /
(((G4double) fHits) - 1.0));
};
return (fHits > 1) ? compute_variance() : 0.0;
}
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetCoeffVariation() const
{
// lambda for equation clarity (will be inlined)
auto coefficient_of_variation = [&] ()
{
G4double hits = fHits;
return ::sqrt(
(hits / (hits-1.0)) *
( (fSum2/(fSum1*fSum1)) - (1.0/hits))
);
};
return (fHits > 1) ? coefficient_of_variation() : 0.0;
//return (fHits > 0 && fabs(fSum1) > 0.0)
// ? (100.0*GetStdDev()/GetMean()) : 0.0;
// lambda for equation clarity (will be inlined)
auto coefficient_of_variation = [&]() {
G4double hits = fHits;
return ::sqrt((hits / (hits - 1.0)) *
((fSum2 / (fSum1 * fSum1)) - (1.0 / hits)));
};
return (fHits > 1) ? coefficient_of_variation() : 0.0;
// return (fHits > 0 && fabs(fSum1) > 0.0)
// ? (100.0*GetStdDev()/GetMean()) : 0.0;
}
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetEfficiency() const
{
G4double hits = fHits;
G4double nzero = fHits - fZero;
return (fHits > 0) ? (nzero/hits) : 0.0;
G4double hits = fHits;
G4double nzero = fHits - fZero;
return (fHits > 0) ? (nzero / hits) : 0.0;
}
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetR2Int() const
{
G4double hits = fHits;
return (fHits > 0)
? (fSum2 / (fSum1 * fSum1)) - 1.0/(GetEfficiency() * hits)
: 0.0;
G4double hits = fHits;
return (fHits > 0)
? (fSum2 / (fSum1 * fSum1)) - 1.0 / (GetEfficiency() * hits)
: 0.0;
}
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetR2Eff() const
{
G4double hits = fHits;
return (fHits > 0)
? (1.0 - GetEfficiency()) / (GetEfficiency() * hits)
: 0.0;
G4double hits = fHits;
return (fHits > 0) ? (1.0 - GetEfficiency()) / (GetEfficiency() * hits) : 0.0;
}
//----------------------------------------------------------------------------//
G4StatAnalysis::operator G4double() const
{
return this->GetSum();
}
G4StatAnalysis::operator G4double() const { return this->GetSum(); }
//----------------------------------------------------------------------------//
void G4StatAnalysis::Reset()
{
fHits = 0;
fZero = 0;
fSum1 = 0.0;
fSum2 = 0.0;
fHits = 0;
fZero = 0;
fSum1 = 0.0;
fSum2 = 0.0;
}
//----------------------------------------------------------------------------//
void G4StatAnalysis::Add(const G4double& val, const G4double& weight)
{
fHits += 1;
fSum1 += val * weight;
fSum2 += val * val * weight;
if(std::fabs(val*weight) < std::fabs(GetMean() * std::numeric_limits<double>::epsilon()))
fZero += 1;
fHits += 1;
fSum1 += val * weight;
fSum2 += val * val * weight;
if(std::fabs(val * weight) <
std::fabs(GetMean() * std::numeric_limits<double>::epsilon()))
fZero += 1;
}
//----------------------------------------------------------------------------//
void G4StatAnalysis::Rescale(const G4double& factor)
{
fSum1 *= factor;
fSum2 *= factor * factor;
fSum1 *= factor;
fSum2 *= factor * factor;
}
//----------------------------------------------------------------------------//
void G4StatAnalysis::PrintInfo(std::ostream& os, const std::string& tab) const
{
G4int _hits = this->GetHits();
G4double _sum = this->GetSum();
G4double _sigma = this->GetStdDev();
G4double _coeff = this->GetCoeffVariation();
G4double _error = this->GetRelativeError();
G4double _eff = this->GetEfficiency();
G4double _fom = this->GetFOM();
G4double _r2int = this->GetR2Int();
G4double _r2eff = this->GetR2Eff();
G4int _hits = this->GetHits();
G4double _sum = this->GetSum();
G4double _sigma = this->GetStdDev();
G4double _coeff = this->GetCoeffVariation();
G4double _error = this->GetRelativeError();
G4double _eff = this->GetEfficiency();
G4double _fom = this->GetFOM();
G4double _r2int = this->GetR2Int();
G4double _r2eff = this->GetR2Eff();
using std::setprecision;
using std::setw;
using std::scientific;
using std::fixed;
using std::left;
using std::right;
using std::ios;
using std::fixed;
using std::ios;
using std::left;
using std::right;
using std::scientific;
using std::setprecision;
using std::setw;
std::stringstream ss;
ss << tab //<< scientific
<< setprecision(os.precision()) << right << _sum
<< left << " [sigma: " << right << _sigma
<< left << " | error: " << right << _error
<< left << " | coeff: " << right << _coeff
<< left << " | eff: " << right << _eff
<< left << " | fom: " << right << _fom
<< left << " | r2int: " << right << _r2int
<< left << " | r2eff: " << right << _r2eff
<< left << " | hits: " << right << _hits
<< left << " ]";
std::stringstream ss;
ss << tab //<< scientific
<< setprecision(os.precision()) << right << _sum << left
<< " [sigma: " << right << _sigma << left << " | error: " << right
<< _error << left << " | coeff: " << right << _coeff << left
<< " | eff: " << right << _eff << left << " | fom: " << right << _fom
<< left << " | r2int: " << right << _r2int << left << " | r2eff: " << right
<< _r2eff << left << " | hits: " << right << _hits << left << " ]";
os << ss.str();
os << ss.str();
}
//----------------------------------------------------------------------------//
G4double G4StatAnalysis::GetCpuTime() const
{
tms* startTime = GetCpuClock();
tms endTime;
times(&endTime);
return ((endTime.tms_stime - startTime->tms_stime) +
(endTime.tms_utime - startTime->tms_utime)) / sysconf(_SC_CLK_TCK);
tms* startTime = GetCpuClock();
tms endTime;
times(&endTime);
return ((endTime.tms_stime - startTime->tms_stime) +
(endTime.tms_utime - startTime->tms_utime)) /
sysconf(_SC_CLK_TCK);
}
//----------------------------------------------------------------------------//
G4StatAnalysis&
G4StatAnalysis::operator+=(const G4double& _val)
G4StatAnalysis& G4StatAnalysis::operator+=(const G4double& _val)
{
this->Add(_val);
return *this;
this->Add(_val);
return *this;
}
//----------------------------------------------------------------------------//
G4StatAnalysis&
G4StatAnalysis::operator/=(const G4double& _val)
G4StatAnalysis& G4StatAnalysis::operator/=(const G4double& _val)
{
fSum1 /= _val;
fSum2 /= (_val*_val);
return *this;
fSum1 /= _val;
fSum2 /= (_val * _val);
return *this;
}
//----------------------------------------------------------------------------//
G4StatAnalysis&
G4StatAnalysis::operator+=(const G4StatAnalysis& rhs)
G4StatAnalysis& G4StatAnalysis::operator+=(const G4StatAnalysis& rhs)
{
fHits += rhs.fHits;
fSum1 += rhs.fSum1;
fSum2 += rhs.fSum2;
fZero += rhs.fZero;
return *this;
fHits += rhs.fHits;
fSum1 += rhs.fSum1;
fSum2 += rhs.fSum2;
fZero += rhs.fZero;
return *this;
}
//----------------------------------------------------------------------------//
G4StatAnalysis&
G4StatAnalysis::operator-=(const G4StatAnalysis& rhs)
G4StatAnalysis& G4StatAnalysis::operator-=(const G4StatAnalysis& rhs)
{
fHits -= rhs.fHits;
fSum1 -= rhs.fSum1;
fSum2 -= rhs.fSum2;
fZero -= rhs.fZero;
return *this;
fHits -= rhs.fHits;
fSum1 -= rhs.fSum1;
fSum2 -= rhs.fSum2;
fZero -= rhs.fZero;
return *this;
}
//----------------------------------------------------------------------------//
inline G4Allocator<G4StatAnalysis>*& _aStatAnalysisAllocator_G4MT_TLS_()
{
G4ThreadLocalStatic G4Allocator<G4StatAnalysis>* _instance
= new G4Allocator<G4StatAnalysis>();
return _instance;
G4ThreadLocalStatic G4Allocator<G4StatAnalysis>* _instance =
new G4Allocator<G4StatAnalysis>();
return _instance;
}
//----------------------------------------------------------------------------//
void* G4StatAnalysis::operator new(size_t)
void* G4StatAnalysis::operator new(std::size_t)
{
G4Allocator<G4StatAnalysis>& _allocator = *_aStatAnalysisAllocator_G4MT_TLS_();
return (void*) _allocator.MallocSingle();
G4Allocator<G4StatAnalysis>& _allocator =
*_aStatAnalysisAllocator_G4MT_TLS_();
return (void*) _allocator.MallocSingle();
}
//----------------------------------------------------------------------------//
void G4StatAnalysis::operator delete(void* _ptr)
{
G4Allocator<G4StatAnalysis>& _allocator = *_aStatAnalysisAllocator_G4MT_TLS_();
_allocator.FreeSingle( (G4StatAnalysis*) _ptr);
G4Allocator<G4StatAnalysis>& _allocator =
*_aStatAnalysisAllocator_G4MT_TLS_();
_allocator.FreeSingle((G4StatAnalysis*) _ptr);
}
//----------------------------------------------------------------------------//
@@ -23,11 +23,7 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
//
//
// ----------------------------------------------------------------------
// Class G4StatDouble
// G4StatDouble
//
// Class description:
//
@@ -35,83 +31,82 @@
// Original Author: Giovanni Santin (ESA) - October 2005 in GRAS tool
// Adaptation and comments by: John Apostolakis (CERN) - November 2011
#ifndef G4StatDouble_h
#define G4StatDouble_h 1
// --------------------------------------------------------------------
#ifndef G4StatDouble_hh
#define G4StatDouble_hh 1
#include "globals.hh"
class G4StatDouble
class G4StatDouble
{
public:
G4StatDouble();
G4StatDouble(G4double);
virtual ~G4StatDouble();
public:
G4StatDouble();
G4StatDouble(G4double);
virtual ~G4StatDouble();
G4StatDouble(const G4StatDouble&) = default;
public:
G4StatDouble& operator=(const G4double& rhs)
{
reset();
fill(rhs);
return *this;
}
G4StatDouble& operator=(const G4StatDouble& rhs)
{
m_sum_wx = rhs.m_sum_wx;
m_sum_wx2 = rhs.m_sum_wx2;
m_n = rhs.m_n;
m_sum_w = rhs.m_sum_w;
m_sum_w2 = rhs.m_sum_w2;
m_scale = rhs.m_scale;
return *this;
}
G4StatDouble& operator+=(const G4double& rhs)
{
fill(rhs);
return *this;
}
G4StatDouble& operator+=(const G4StatDouble& rhs)
{
add(&rhs);
return *this;
}
G4StatDouble(const G4StatDouble&) = default;
void reset();
void fill(G4double x, G4double weight = 1.);
// Add new data point: value "x" with weight
void scale(G4double);
// Reset scale
G4StatDouble& operator=(const G4double &rhs)
{
reset();
fill(rhs);
return *this;
}
G4StatDouble& operator=(const G4StatDouble &rhs)
{
m_sum_wx = rhs.m_sum_wx;
m_sum_wx2 = rhs.m_sum_wx2;
m_n = rhs.m_n;
m_sum_w = rhs.m_sum_w;
m_sum_w2 = rhs.m_sum_w2;
m_scale = rhs.m_scale;
return *this;
}
G4StatDouble& operator+=(const G4double &rhs)
{ fill(rhs); return *this; }
G4StatDouble& operator+=(const G4StatDouble &rhs)
{ add(&rhs); return *this; }
G4double mean() const;
G4double rms();
// The moments
public:
G4double mean(G4double ext_sum_w) const;
// Mean scaled to sum of weights
G4double rms(G4double ext_sum_w, G4int ext_n);
// RMS scaled to sum of weights
void reset();
void fill(G4double x, G4double weight=1.);
// Add new data point: value "x" with weight
void scale(G4double);
// Reset scale
void add(const G4StatDouble*);
// merge 2 statistics
G4double mean() const;
G4double rms();
// The moments
inline G4int n() const { return m_n; }
inline G4double sum_w() const { return m_sum_w; }
inline G4double sum_w2() const { return m_sum_w2; }
inline G4double sum_wx() const { return m_sum_wx; }
inline G4double sum_wx2() const { return m_sum_wx2; }
G4double mean(G4double ext_sum_w) const;
// Mean scaled to sum of weights
G4double rms(G4double ext_sum_w, G4int ext_n);
// RMS scaled to sum of weights
protected:
G4double rms(G4double sum_wx, G4double sum_wx2, G4double sum_w, G4int n);
void add(const G4StatDouble*);
// merge 2 statistics
inline G4int n() const { return m_n; }
inline G4double sum_w() const { return m_sum_w; }
inline G4double sum_w2() const { return m_sum_w2; }
inline G4double sum_wx() const { return m_sum_wx; }
inline G4double sum_wx2() const { return m_sum_wx2; }
protected:
G4double rms(G4double sum_wx, G4double sum_wx2, G4double sum_w, G4int n);
protected:
G4double m_sum_wx;
G4double m_sum_wx2;
G4int m_n;
G4double m_sum_w;
G4double m_sum_w2;
G4double m_scale;
protected:
G4double m_sum_wx = 0.0;
G4double m_sum_wx2 = 0.0;
G4int m_n = 0;
G4double m_sum_w = 0.0;
G4double m_sum_w2 = 0.0;
G4double m_scale = 0.0;
};
#endif
@@ -23,7 +23,7 @@
// * acceptance of all terms of the Geant4 Software license. *
// ********************************************************************
//
//
// G4VGaussianQuadrature
//
// Class description:
//
@@ -31,67 +31,46 @@
// with signature double f(double) by Gaussian quadrature methods
// Roots of ortogonal polynoms and corresponding weights are calculated based on
// iteration method (by bisection Newton algorithm). Constant values for initial
// approximations were derived from the book: M. Abramowitz, I. Stegun, Handbook
// of mathematical functions, DOVER Publications INC, New York 1965 ; chapters 9,
// 10, and 22 .
//
// ---------------------------- Member data: ----------------------------------
//
// fFunction - pointer to the function to be integrated
// fNumber - the number of points in fAbscissa and fWeight arrays
// fAbscissa - array of abscissas, where function will be evaluated
// fWeight - array of corresponding weights
//
//
// ----------------------------------------------------------------------
//
// Auxiliary function which returns the value of std::log(gamma-function(x))
//
// G4double
// GammaLogarithm(G4double xx)
// ------------------------------------------------------------------------------
//
// History:
// 18.04.97 V.Grichine ( Vladimir.Grichine@cern.ch )
// approximations were derived from the book:
// M. Abramowitz, I. Stegun, Handbook of mathematical functions,
// DOVER Publications INC, New York 1965 ; chapters 9, 10, and 22.
// Author: V.Grichine, 18.04.1997
// --------------------------------------------------------------------
#ifndef G4VGAUSSIANQUADRATURE_HH
#define G4VGAUSSIANQUADRATURE_HH
#define G4VGAUSSIANQUADRATURE_HH 1
#include "globals.hh"
typedef G4double (*function)(G4double) ;
typedef G4double (*function)(G4double);
class G4VGaussianQuadrature
{
public:
public:
explicit G4VGaussianQuadrature(function pFunction);
// Base constructor
explicit G4VGaussianQuadrature( function pFunction ) ;
// Base constructor
virtual ~G4VGaussianQuadrature();
// Virtual destructor
virtual ~G4VGaussianQuadrature() ;
// Virtual destructor
G4VGaussianQuadrature(const G4VGaussianQuadrature&) = delete;
G4VGaussianQuadrature& operator=(const G4VGaussianQuadrature&) = delete;
G4double GetAbscissa(G4int index) const ;
G4double GetWeight(G4int index) const ;
G4int GetNumber() const;
// Access functions
G4double GetAbscissa(G4int index) const;
G4double GetWeight(G4int index) const;
G4int GetNumber() const;
// Access functions
protected:
protected:
G4double GammaLogarithm(G4double xx);
// Auxiliary function which returns the value of std::log(gamma-function(x))
G4double GammaLogarithm(G4double xx) ;
// Data members common for GaussianQuadrature family
//
function fFunction ;
G4double* fAbscissa ;
G4double* fWeight ;
G4int fNumber ;
private:
G4VGaussianQuadrature(const G4VGaussianQuadrature&);
G4VGaussianQuadrature& operator=(const G4VGaussianQuadrature&);
// Data members common for GaussianQuadrature family
//
function fFunction; // pointer to the function to be integrated
G4double* fAbscissa = nullptr; // array of abscissas
G4double* fWeight = nullptr; // array of corresponding weights
G4int fNumber = 0; // the number of points in fAbscissa and fWeight arrays
};
#endif