| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

In This Package:

LHCb::Math Namespace Reference

Collection of math related functions for general use in LHCb. More...


Classes

struct  abs_less
 comparison by absolute value More...
struct  abs_greater
 comparison by absolute value More...
struct  Equal_To
 helper structure for comparison of floating values More...
struct  Equal_To< const TYPE >
 partial specialization for const-types More...
struct  Equal_To< TYPE & >
 partial specialization for references More...
struct  Equal_To< double >
 explicit specialization for doubles More...
struct  Equal_To< long double >
 explicit specialization for long doubles More...
struct  Equal_To< float >
 explicit specialization for floats More...

Functions

bool equal_to_double (const double value1, const double value2, const double epsilon=1.0e-6)
 compare two double numbers with relative precision 'epsilon'
bool lomont_compare_float (const float af, const float bf, const unsigned short maxULPs=100)
 equality comparison of float numbers using as the metric the maximal number of Units in the Last Place (ULP).
float next_float (const float af, const short ulps)
 Get the floating number that representation is different with respect to the argument for the certain number of "Units in the Last Position".
bool lomont_compare_double (const double af, const double bf, const unsigned int maxULPs)
 equality comparison of float numbers using as the metric the maximal number of Units in the Last Place (ULP).
double next_double (const double af, const short ulps)
 Get the floating number that representation is different with respect to the argument for the certain number of "Units in the Last Position".
template<class TYPE>
TYPE absMin (TYPE v1, TYPE v2)
 return "min_by_abs"
template<class TYPE>
TYPE absMax (TYPE v1, TYPE v2)
 return "max_by_abs"
int round (const double x)
 Round to nearest integer.
int round (const float x)
 Round to nearest integer.
bool equal_to_int (const double val, const int ref, const double eps1=1.e-6, const double eps2=0.5e-3/boost::integer_traits< int >::const_max)
 check if the double value is actually equal to the integer value
bool equal_to_int (const int ref, const double val, const double eps1=1.e-6, const double eps2=0.5e-3/boost::integer_traits< int >::const_max)
 check if the double value is actually equal to the integer value
bool equal_to_uint (const double val, const unsigned int ref, const double eps1=1.e-6, const double eps2=1.e-3/boost::integer_traits< unsigned int >::const_max)
 check if the double value is actually equal to the unsigned integer value
bool equal_to_uint (const unsigned int ref, const double val, const double eps1=1.e-6, const double eps2=1.e-3/boost::integer_traits< unsigned int >::const_max)
 check if the double value is actually equal to the integer value

Variables

static const double hiTolerance = 1e-40
 Parameters for numerical calculations (M.Needham).
static const double lowTolerance = 1e-20
static const double looseTolerance = 1e-5
static const double sqrt_12 = 3.4641016151377546
static const double inv_sqrt_12 = 0.2886751345948129

Detailed Description

Collection of math related functions for general use in LHCb.

Function Documentation

bool LHCb::Math::equal_to_double ( const double  value1,
const double  value2,
const double  epsilon = 1.0e-6 
)

compare two double numbers with relative precision 'epsilon'

Essentially it is a wrapper to gsl_fcmp function from GSL library See D.E.Knuth, "Seminumerical Algorithms", section 4.2.2

Todo:
one needs to use the "fast" IEEE-based algorithm
Author:
Vanya BELYAEV ibelyaev@physics.syr.edu
Date:
2007-11-27

Definition at line 32 of file LHCbMath.cpp.

00035 {
00036   return 
00037     !epsilon    ? 0 == gsl_fcmp ( value1 , value2 , 1.0e-6  ) : 
00038     0 < epsilon ? 0 == gsl_fcmp ( value1 , value2 , epsilon ) : 
00039     0 == gsl_fcmp ( value1 , value2 , -epsilon ) ;
00040 }

bool LHCb::Math::lomont_compare_float ( const float  af,
const float  bf,
const unsigned short  maxULPs = 100 
)

equality comparison of float numbers using as the metric the maximal number of Units in the Last Place (ULP).

It is a slightly modified version of very efficient implementation of the initial Bruce Dawson's algorithm by Chris Lomont.

See also:
www.lomont.org

http://www.cygnus-software.com/papers/comparingfloats/comparingfloats.htm

C.Lomont claims the algorithm is factor 2-10 more efficient with respect to Knuth's algorithm fomr comparions of floating number using the relative precision.

The effective relative difference depends on the choice of maxULPS:

Parameters:
af the first number
bf the second number
maxULPS the maximal metric deciation in the terms of maximal number of units in the last place
Author:
Vanya BELYAEV Ivan.Belyaev@nikhef.nl
Date:
2008-11-08

Definition at line 63 of file Lomont.cpp.

00066 {
00067   // ==========================================================================
00068   // prerequisites:
00069   BOOST_STATIC_ASSERT( std::numeric_limits<float>          ::is_specialized &&
00070                        boost::integer_traits<int>          ::is_specialized && 
00071                        boost::integer_traits<unsigned int> ::is_specialized &&
00072                        sizeof(float)==sizeof(int)                           && 
00073                        sizeof(float)==sizeof(unsigned int)                  &&
00074                        32 == boost::integer_traits<unsigned int>::digits    ) ;
00075   // ==========================================================================
00076   
00077   int ai = *reinterpret_cast<const int*>( &af ) ;
00078   int bi = *reinterpret_cast<const int*>( &bf ) ;
00079   
00080   int test = (((unsigned int)(ai^bi))>>31)-1;
00081   
00082   // assert ( (0==test) || ( boost::integer_traits<unsigned int>::const_max == test ) ) ;
00083   
00084   int diff = ((( boost::integer_traits<int>::const_min - ai ) & (~test)) | ( ai& test )) - bi ;
00085   
00086   int maxDiff_ = maxULPs ;
00087   
00088   int v1 = maxDiff_ + diff ;
00089   int v2 = maxDiff_ - diff ;
00090   
00091   return 0<=(v1|v2) ;
00092 }

float LHCb::Math::next_float ( const float  af,
const short  ulps 
)

Get the floating number that representation is different with respect to the argument for the certain number of "Units in the Last Position".

For ulps=1, it is just next float number, for ulps=-1 is is the previous one.

This routine is very convinient to test the parameter maxULPS for the routine LHCb::Math::lomont_compare_float

See also:
LHCb:Math::lomont_compare
Parameters:
af the reference number
ulps the bias
Returns:
the biased float number (on distance "ulps")
Author:
Vanya BELYAEV Ivan.Belyaev@nikhef.nl
Date:
2008-11-08

Definition at line 111 of file Lomont.cpp.

00112 {
00114   BOOST_STATIC_ASSERT( std::numeric_limits<float> ::is_specialized &&
00115                        std::numeric_limits<int>   ::is_specialized && 
00116                        sizeof(float)==sizeof(int) ) ;
00117   
00118   int ai = *reinterpret_cast<const int*>( &af ) ;
00119   ai += ulps ;
00120   return *reinterpret_cast<float*>(&ai) ;
00121 }

bool LHCb::Math::lomont_compare_double ( const double  af,
const double  bf,
const unsigned int  maxULPs 
)

equality comparison of float numbers using as the metric the maximal number of Units in the Last Place (ULP).

It is a slightly modified version of very efficient implementation of the initial Bruce Dawson's algorithm by Chris Lomont.

See also:
www.lomont.org

http://www.cygnus-software.com/papers/comparingfloats/comparingfloats.htm

C.Lomont claims the algorithm is factor 2-10 more efficient with respect to Knuth's algorithm fomr comparions of floating number using the relative precision.

The effective relative difference depends on the choice of maxULPS:

Parameters:
af the first number
bf the second number
maxULPS the maximal metric deciation in the terms of maximal number of units in the last place
Author:
Vanya BELYAEV Ivan.Belyaev@nikhef.nl
Date:
2008-11-08

Definition at line 193 of file Lomont.cpp.

00196 {
00198   BOOST_STATIC_ASSERT( std::numeric_limits<double>        ::is_specialized &&
00199                        std::numeric_limits<Long>          ::is_specialized && 
00200                        std::numeric_limits<ULong> ::is_specialized &&
00201                        boost::integer_traits<ULong> ::is_specialized &&
00202                        boost::integer_traits<Long> ::is_specialized &&
00203                        sizeof(double)==sizeof(Long)          && 
00204                        sizeof(double)==sizeof(ULong)  &&
00205                        64 == std::numeric_limits<ULong>::digits ) ;
00206   
00207   Long ai = *reinterpret_cast<const Long*>( &af ) ;
00208   Long bi = *reinterpret_cast<const Long*>( &bf ) ;
00209   
00210   Long test = (((ULong)(ai^bi))>>63)-1;
00211   
00212   // assert ( (0==test) || ( boost::integer_traits<ULong>::const_max == test ) ) ;
00213   
00214   Long diff = ((( boost::integer_traits<Long>::const_min - ai ) & (~test)) | ( ai& test )) - bi ;
00215   
00216   Long maxDiff_ = maxULPs ;
00217   
00218   Long v1 = maxDiff_ + diff ;
00219   Long v2 = maxDiff_ - diff ;
00220   
00221   return 0<=(v1|v2) ;
00222 }

double LHCb::Math::next_double ( const double  af,
const short  ulps 
)

Get the floating number that representation is different with respect to the argument for the certain number of "Units in the Last Position".

For ulps=1, it is just next float number, for ulps=-1 is is the previous one.

This routine is very convinient to test the parameter maxULPS for the routine LHCb::Math::lomont_compare_float

See also:
LHCb:Math::lomont_compare
Parameters:
af the reference number
ulps the bias
Returns:
the biased float number (on distance "ulps")
Author:
Vanya BELYAEV Ivan.Belyaev@nikhef.nl
Date:
2008-11-08

Definition at line 241 of file Lomont.cpp.

00242 {
00244   BOOST_STATIC_ASSERT( std::numeric_limits<double> ::is_specialized &&
00245                        std::numeric_limits<Long>   ::is_specialized && 
00246                        sizeof(double)==sizeof(Long) ) ;
00247   
00248   Long al = *reinterpret_cast<const Long*>( &ad ) ;
00249   al += ulps ;
00250   return *reinterpret_cast<double*>(&al) ;
00251 }

template<class TYPE>
TYPE LHCb::Math::absMin ( TYPE  v1,
TYPE  v2 
) [inline]

return "min_by_abs"

Author:
Vanya BELYAEV ibelyaev@physics.syr.edu
Date:
2007-08-17

Definition at line 86 of file LHCbMath.h.

00087     { return std::min ( std::fabs ( v1 ) , std::fabs ( v2 ) ) ; }

template<class TYPE>
TYPE LHCb::Math::absMax ( TYPE  v1,
TYPE  v2 
) [inline]

return "max_by_abs"

Author:
Vanya BELYAEV ibelyaev@physics.syr.edu
Date:
2007-08-17

Definition at line 94 of file LHCbMath.h.

00095     { return std::max ( std::fabs ( v1 ) , std::fabs ( v2 ) ) ; }

int LHCb::Math::round ( const double  x  )  [inline]

Round to nearest integer.

Rounds half integers to nearest even integer.

Author:
Matt Needham

Definition at line 195 of file LHCbMath.h.

00195                                          {
00196       int i;
00197       LHCb::Math::Equal_To<double> equal_to(lowTolerance);
00198       if (x >= 0.0) {
00199         i = int(x + 0.5);
00200         if (equal_to(x + 0.5, double(i)) && i & 1) --i;
00201       }
00202       else {
00203         i = int(x - 0.5);
00204         if (equal_to(x - 0.5 , double(i)) && i & 1) ++i;
00205         
00206       }
00207       return i;
00208     }

int LHCb::Math::round ( const float  x  )  [inline]

Round to nearest integer.

Rounds half integers to nearest even integer.

Author:
Matt Needham

Definition at line 213 of file LHCbMath.h.

00214     {
00215       return LHCb::Math::round ( double ( x ) ) ;
00216     }

bool LHCb::Math::equal_to_int ( const double  val,
const int  ref,
const double  eps1 = 1.e-6,
const double  eps2 = 0.5e-3 / boost::integer_traits<int>::const_max 
) [inline]

check if the double value is actually equal to the integer value

Parameters:
val value to be compared with the integer
ref the reference integer number
eps1 the absolute precision
eps2 the relative precision
Author:
Vanya BELYAEV Ivan.Belyaev@nikhef.nl
Date:
2008-09-17

Definition at line 227 of file LHCbMath.h.

00231     {
00232       BOOST_STATIC_ASSERT(boost::integer_traits<int>::is_specialized ) ;
00233       // 1) try the straightforward comparison 
00234       if ( val == ref                 ) { return true ; } // RETURN 
00235       // 2) check the limits 
00236       if ( val > boost::integer_traits<int>::const_max || 
00237            val < boost::integer_traits<int>::const_min ) { return false ; }
00238       // 3) compare the doubles 
00239       if ( std::fabs ( val - ref ) <= eps1 ) { return true  ; }
00240       // 3') compare the doubles  
00241       LHCb::Math::Equal_To<double> cmp ( eps2 ) ;
00242       return cmp ( val , ref ) ;
00243     }

bool LHCb::Math::equal_to_int ( const int  ref,
const double  val,
const double  eps1 = 1.e-6,
const double  eps2 = 0.5e-3 / boost::integer_traits<int>::const_max 
) [inline]

check if the double value is actually equal to the integer value

Parameters:
ref the reference integer number
val value to be compared with the integer
eps1 the absolute precision
eps2 the relative precision
Author:
Vanya BELYAEV Ivan.Belyaev@nikhef.nl
Date:
2008-09-17

Definition at line 254 of file LHCbMath.h.

00258     { 
00259       BOOST_STATIC_ASSERT(boost::integer_traits<int>::is_specialized ) ;
00260       return equal_to_int ( val , ref , eps1 , eps2 ) ; 
00261     }

bool LHCb::Math::equal_to_uint ( const double  val,
const unsigned int  ref,
const double  eps1 = 1.e-6,
const double  eps2 = 1.e-3 / boost::integer_traits<unsigned int>::const_max 
) [inline]

check if the double value is actually equal to the unsigned integer value

Parameters:
val value to be compared with the unsigned integer
ref the reference unsigned integer number
eps1 the absolute precision
eps2 the relative precision
Author:
Vanya BELYAEV Ivan.Belyaev@nikhef.nl
Date:
2008-09-17

Definition at line 272 of file LHCbMath.h.

00276     {
00277       BOOST_STATIC_ASSERT(boost::integer_traits<unsigned int>::is_specialized ) ;
00278       // 1) straightforward comparison 
00279       if ( val == ref ) { return true ; }                             // RETURN 
00280       // check the limits 
00281       if ( val > boost::integer_traits<unsigned int>::const_max || 
00282            val < boost::integer_traits<unsigned int>::const_min ) { return false ; }
00283       // 3) compare the doubles 
00284       if ( std::fabs ( val - ref ) <= eps1 ) { return true  ; }
00285       // 3') compare the doubles  
00286       LHCb::Math::Equal_To<double> cmp ( eps2 ) ;
00287       return cmp ( val , ref ) ;
00288     }

bool LHCb::Math::equal_to_uint ( const unsigned int  ref,
const double  val,
const double  eps1 = 1.e-6,
const double  eps2 = 1.e-3 / boost::integer_traits<unsigned int>::const_max 
) [inline]

check if the double value is actually equal to the integer value

Parameters:
val value to be compared with the unsigned integer
ref the reference unsigned integer number
eps the absolute precision
Author:
Vanya BELYAEV Ivan.Belyaev@nikhef.nl
Date:
2008-09-17

Definition at line 298 of file LHCbMath.h.

00302     { return equal_to_uint ( val , ref , eps1 , eps2 ) ; }


Variable Documentation

const double LHCb::Math::hiTolerance = 1e-40 [static]

Parameters for numerical calculations (M.Needham).

Definition at line 39 of file LHCbMath.h.

const double LHCb::Math::lowTolerance = 1e-20 [static]

Definition at line 40 of file LHCbMath.h.

const double LHCb::Math::looseTolerance = 1e-5 [static]

Definition at line 41 of file LHCbMath.h.

const double LHCb::Math::sqrt_12 = 3.4641016151377546 [static]

Definition at line 42 of file LHCbMath.h.

const double LHCb::Math::inv_sqrt_12 = 0.2886751345948129 [static]

Definition at line 43 of file LHCbMath.h.

| Classes | Job Modules | Data Objects | Services | Algorithms | Tools | Packages | Directories | Tracs |

Generated on Mon Apr 11 20:02:59 2011 for LHCbMath by doxygen 1.4.7