- added AboutEqualWithoutSign() to big<> to allow 'suppression' of some unexpected results (that are perfectly logical though, given the possibly unrepresentable nature of binary representation of decimals) like

big<>("10.456466") * 2 == big<>("20.912932")

resulting in FALSE result.

git-svn-id: svn://ttmath.org/publicrep/ttmath/branches/chk@171 e52654a7-88a9-db11-a3e9-0013d4bc506e
This commit is contained in:
Christian Kaiser
2009-06-25 14:11:17 +00:00
parent de64608eba
commit de58378488
3 changed files with 306 additions and 306 deletions

View File

@@ -45,7 +45,7 @@
\brief Mathematics functions. \brief Mathematics functions.
*/ */
#include "ttmathconfig.h" #include "ttmathconfig.h"
#include "ttmathbig.h" #include "ttmathbig.h"
#include "ttmathobjects.h" #include "ttmathobjects.h"
@@ -96,21 +96,21 @@ namespace ttmath
-2.7 = -3 -2.7 = -3
*/ */
template<class ValueType> template<class ValueType>
ValueType Round(const ValueType & x, ErrorCode * err = 0) ValueType Round(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType result( x ); ValueType result( x );
uint c = result.Round(); uint c = result.Round();
if( err ) if( err )
*err = c ? err_overflow : err_ok; *err = c ? err_overflow : err_ok;
return result; return result;
} }
@@ -131,14 +131,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Ceil(const ValueType & x, ErrorCode * err = 0) ValueType Ceil(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType result(x); ValueType result(x);
uint c = 0; uint c = 0;
@@ -178,14 +178,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Floor(const ValueType & x, ErrorCode * err = 0) ValueType Floor(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType result(x); ValueType result(x);
uint c = 0; uint c = 0;
@@ -226,14 +226,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Ln(const ValueType & x, ErrorCode * err = 0) ValueType Ln(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType result; ValueType result;
uint state = result.Ln(x); uint state = result.Ln(x);
@@ -267,14 +267,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Log(const ValueType & x, const ValueType & base, ErrorCode * err = 0) ValueType Log(const ValueType & x, const ValueType & base, ErrorCode * err = 0)
{ {
if( x.IsNan() || base.IsNan() ) if( x.IsNan() || base.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return ValueType(); // default NaN return ValueType(); // default NaN
} }
ValueType result; ValueType result;
uint state = result.Log(x, base); uint state = result.Log(x, base);
@@ -308,14 +308,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Exp(const ValueType & x, ErrorCode * err = 0) ValueType Exp(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType result; ValueType result;
uint c = result.Exp(x); uint c = result.Exp(x);
@@ -345,7 +345,7 @@ namespace ttmath
(you don't have to call this function) (you don't have to call this function)
*/ */
template<class ValueType> template<class ValueType>
uint PrepareSin(ValueType & x, bool & change_sign) uint PrepareSin(ValueType & x, bool & change_sign)
{ {
ValueType temp; ValueType temp;
@@ -361,10 +361,10 @@ namespace ttmath
// we're reducing the period 2*PI // we're reducing the period 2*PI
// (for big values there'll always be zero) // (for big values there'll always be zero)
temp.Set2Pi(); temp.Set2Pi();
if( x.Mod(temp) ) if( x.Mod(temp) )
return 1; return 1;
// we're setting 'x' as being in the range of <0, 0.5PI> // we're setting 'x' as being in the range of <0, 0.5PI>
@@ -385,8 +385,8 @@ namespace ttmath
x.Sub( temp ); x.Sub( temp );
x = temp - x; x = temp - x;
} }
return 0; return 0;
} }
@@ -473,7 +473,7 @@ namespace ttmath
if( c ) if( c )
// Sin is from <-1,1> and cannot make an overflow // Sin is from <-1,1> and cannot make an overflow
// but the carry can be from the Taylor series // but the carry can be from the Taylor series
// (then we only break our calculations) // (then we only break our calculations)
break; break;
if( addition ) if( addition )
@@ -505,23 +505,23 @@ namespace ttmath
this function calculates the Sine this function calculates the Sine
*/ */
template<class ValueType> template<class ValueType>
ValueType Sin(ValueType x, ErrorCode * err = 0) ValueType Sin(ValueType x, ErrorCode * err = 0)
{ {
using namespace auxiliaryfunctions; using namespace auxiliaryfunctions;
ValueType one, result; ValueType one, result;
bool change_sign; bool change_sign;
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return result; // NaN is set by default return result; // NaN is set by default
} }
if( err ) if( err )
*err = err_ok; *err = err_ok;
if( PrepareSin( x, change_sign ) ) if( PrepareSin( x, change_sign ) )
{ {
@@ -531,7 +531,7 @@ namespace ttmath
// result has NaN flag set by default // result has NaN flag set by default
if( err ) if( err )
*err = err_overflow; // maybe another error code? err_improper_argument? *err = err_overflow; // maybe another error code? err_improper_argument?
return result; // NaN is set by default return result; // NaN is set by default
} }
@@ -561,20 +561,20 @@ namespace ttmath
we're using the formula cos(x) = sin(x + PI/2) we're using the formula cos(x) = sin(x + PI/2)
*/ */
template<class ValueType> template<class ValueType>
ValueType Cos(ValueType x, ErrorCode * err = 0) ValueType Cos(ValueType x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType pi05; ValueType pi05;
pi05.Set05Pi(); pi05.Set05Pi();
uint c = x.Add( pi05 ); uint c = x.Add( pi05 );
if( c ) if( c )
{ {
@@ -584,9 +584,9 @@ namespace ttmath
return ValueType(); // result is undefined (NaN is set by default) return ValueType(); // result is undefined (NaN is set by default)
} }
return Sin(x, err); return Sin(x, err);
} }
/*! /*!
this function calulates the Tangent this function calulates the Tangent
@@ -601,10 +601,10 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Tan(const ValueType & x, ErrorCode * err = 0) ValueType Tan(const ValueType & x, ErrorCode * err = 0)
{ {
ValueType result = Cos(x, err); ValueType result = Cos(x, err);
if( err && *err != err_ok ) if( err && *err != err_ok )
return result; return result;
if( result.IsZero() ) if( result.IsZero() )
{ {
@@ -616,7 +616,7 @@ namespace ttmath
return result; return result;
} }
return Sin(x, err) / result; return Sin(x, err) / result;
} }
@@ -643,10 +643,10 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Cot(const ValueType & x, ErrorCode * err = 0) ValueType Cot(const ValueType & x, ErrorCode * err = 0)
{ {
ValueType result = Sin(x, err); ValueType result = Sin(x, err);
if( err && *err != err_ok ) if( err && *err != err_ok )
return result; return result;
if( result.IsZero() ) if( result.IsZero() )
{ {
@@ -658,7 +658,7 @@ namespace ttmath
return result; return result;
} }
return Cos(x, err) / result; return Cos(x, err) / result;
} }
@@ -843,14 +843,14 @@ namespace ttmath
one.SetOne(); one.SetOne();
bool change_sign = false; bool change_sign = false;
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return result; // NaN is set by default return result; // NaN is set by default
} }
if( x.GreaterWithoutSignThan(one) ) if( x.GreaterWithoutSignThan(one) )
{ {
if( err ) if( err )
@@ -1073,9 +1073,9 @@ namespace ttmath
one.SetOne(); one.SetOne();
bool change_sign = false; bool change_sign = false;
if( x.IsNan() ) if( x.IsNan() )
return result; // NaN is set by default return result; // NaN is set by default
// if x is negative we're using the formula: // if x is negative we're using the formula:
// atan(-x) = -atan(x) // atan(-x) = -atan(x)
if( x.IsSign() ) if( x.IsSign() )
@@ -1156,14 +1156,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Sinh(const ValueType & x, ErrorCode * err = 0) ValueType Sinh(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType ex, emx; ValueType ex, emx;
uint c = 0; uint c = 0;
@@ -1188,14 +1188,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Cosh(const ValueType & x, ErrorCode * err = 0) ValueType Cosh(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType ex, emx; ValueType ex, emx;
uint c = 0; uint c = 0;
@@ -1220,14 +1220,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Tanh(const ValueType & x, ErrorCode * err = 0) ValueType Tanh(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType ex, emx, nominator, denominator; ValueType ex, emx, nominator, denominator;
uint c = 0; uint c = 0;
@@ -1268,14 +1268,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Coth(const ValueType & x, ErrorCode * err = 0) ValueType Coth(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
if( x.IsZero() ) if( x.IsZero() )
{ {
if( err ) if( err )
@@ -1333,14 +1333,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType ASinh(const ValueType & x, ErrorCode * err = 0) ValueType ASinh(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType xx(x), one, result; ValueType xx(x), one, result;
uint c = 0; uint c = 0;
one.SetOne(); one.SetOne();
@@ -1369,14 +1369,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType ACosh(const ValueType & x, ErrorCode * err = 0) ValueType ACosh(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType xx(x), one, result; ValueType xx(x), one, result;
uint c = 0; uint c = 0;
one.SetOne(); one.SetOne();
@@ -1418,14 +1418,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType ATanh(const ValueType & x, ErrorCode * err = 0) ValueType ATanh(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType nominator(x), denominator, one, result; ValueType nominator(x), denominator, one, result;
uint c = 0; uint c = 0;
one.SetOne(); one.SetOne();
@@ -1471,14 +1471,14 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType ACoth(const ValueType & x, ErrorCode * err = 0) ValueType ACoth(const ValueType & x, ErrorCode * err = 0)
{ {
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return x; // NaN return x; // NaN
} }
ValueType nominator(x), denominator(x), one, result; ValueType nominator(x), denominator(x), one, result;
uint c = 0; uint c = 0;
one.SetOne(); one.SetOne();
@@ -1537,14 +1537,14 @@ namespace ttmath
ValueType result, temp; ValueType result, temp;
uint c = 0; uint c = 0;
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return result; // NaN is set by default return result; // NaN is set by default
} }
result = x; result = x;
// it is better to make division first and then multiplication // it is better to make division first and then multiplication
@@ -1573,14 +1573,14 @@ namespace ttmath
ValueType result, delimiter; ValueType result, delimiter;
uint c = 0; uint c = 0;
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return result; // NaN is set by default return result; // NaN is set by default
} }
result = 180; result = 180;
c += result.Mul(x); c += result.Mul(x);
@@ -1618,7 +1618,7 @@ namespace ttmath
ValueType delimiter, multipler; ValueType delimiter, multipler;
uint c = 0; uint c = 0;
if( d.IsNan() || m.IsNan() || s.IsNan() || m.IsSign() || s.IsSign() ) if( d.IsNan() || m.IsNan() || s.IsNan() || m.IsSign() || s.IsSign() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
@@ -1672,14 +1672,14 @@ namespace ttmath
ValueType result, temp; ValueType result, temp;
uint c = 0; uint c = 0;
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return result; // NaN is set by default return result; // NaN is set by default
} }
result = x; result = x;
// it is better to make division first and then multiplication // it is better to make division first and then multiplication
@@ -1708,14 +1708,14 @@ namespace ttmath
ValueType result, delimiter; ValueType result, delimiter;
uint c = 0; uint c = 0;
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return result; // NaN is set by default return result; // NaN is set by default
} }
result = 200; result = 200;
c += result.Mul(x); c += result.Mul(x);
@@ -1740,14 +1740,14 @@ namespace ttmath
ValueType result, temp; ValueType result, temp;
uint c = 0; uint c = 0;
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return result; // NaN is set by default return result; // NaN is set by default
} }
result = x; result = x;
temp = 200; temp = 200;
@@ -1790,14 +1790,14 @@ namespace ttmath
ValueType result, temp; ValueType result, temp;
uint c = 0; uint c = 0;
if( x.IsNan() ) if( x.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return result; // NaN is set by default return result; // NaN is set by default
} }
result = x; result = x;
temp = 180; temp = 180;
@@ -1831,7 +1831,7 @@ namespace ttmath
template<class ValueType> template<class ValueType>
ValueType Sqrt(ValueType x, ErrorCode * err = 0) ValueType Sqrt(ValueType x, ErrorCode * err = 0)
{ {
if( x.IsNan() || x.IsSign() ) if( x.IsNan() || x.IsSign() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
@@ -1913,7 +1913,7 @@ namespace ttmath
template<class ValueType> template<class ValueType>
bool RootCheckIndexOne(const ValueType & index, ErrorCode * err) bool RootCheckIndexOne(const ValueType & index, ErrorCode * err)
{ {
ValueType one; ValueType one;
one.SetOne(); one.SetOne();
@@ -1955,12 +1955,12 @@ namespace ttmath
template<class ValueType> template<class ValueType>
bool RootCheckXZero(ValueType & x, ErrorCode * err) bool RootCheckXZero(ValueType & x, ErrorCode * err)
{ {
if( x.IsZero() ) if( x.IsZero() )
{ {
// root(0;index) is zero (if index!=0) // root(0;index) is zero (if index!=0)
// RootCheckIndexZero() must be called beforehand // RootCheckIndexZero() must be called beforehand
x.SetZero(); x.SetZero();
if( err ) if( err )
@@ -2027,19 +2027,19 @@ namespace ttmath
{ {
using namespace auxiliaryfunctions; using namespace auxiliaryfunctions;
if( x.IsNan() || index.IsNan() ) if( x.IsNan() || index.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return ValueType(); // NaN is set by default return ValueType(); // NaN is set by default
} }
if( RootCheckIndexSign(x, index, err) ) return x; if( RootCheckIndexSign(x, index, err) ) return x;
if( RootCheckIndexZero(x, index, err) ) return x; if( RootCheckIndexZero(x, index, err) ) return x;
if( RootCheckIndexOne ( index, err) ) return x; if( RootCheckIndexOne ( index, err) ) return x;
if( RootCheckIndexFrac(x, index, err) ) return x; if( RootCheckIndexFrac(x, index, err) ) return x;
if( RootCheckXZero (x, err) ) return x; if( RootCheckXZero (x, err) ) return x;
// index integer and index!=0 // index integer and index!=0
// x!=0 // x!=0
@@ -2090,17 +2090,17 @@ namespace ttmath
while( !carry && multipler<maxvalue ) while( !carry && multipler<maxvalue )
{ {
if( stop && (multipler & 127)==0 ) // it means 'stop && (multipler % 128)==0' if( stop && (multipler & 127)==0 ) // it means 'stop && (multipler % 128)==0'
{ {
// after each 128 iterations we make a test // after each 128 iterations we make a test
if( stop->WasStopSignal() ) if( stop->WasStopSignal() )
{ {
if( err ) if( err )
*err = err_interrupt; *err = err_interrupt;
return 2; return 2;
} }
} }
++multipler; ++multipler;
carry += result.MulUInt(multipler); carry += result.MulUInt(multipler);
@@ -2123,25 +2123,25 @@ namespace ttmath
one.SetOne(); one.SetOne();
uint carry = 0; uint carry = 0;
uint iter = 1; // only for testing the stop object uint iter = 1; // only for testing the stop object
while( !carry && multipler < x ) while( !carry && multipler < x )
{ {
if( stop && (iter & 31)==0 ) // it means 'stop && (iter % 32)==0' if( stop && (iter & 31)==0 ) // it means 'stop && (iter % 32)==0'
{ {
// after each 32 iterations we make a test // after each 32 iterations we make a test
if( stop->WasStopSignal() ) if( stop->WasStopSignal() )
{ {
if( err ) if( err )
*err = err_interrupt; *err = err_interrupt;
return 2; return 2;
} }
} }
carry += multipler.Add(one); carry += multipler.Add(one);
carry += result.Mul(multipler); carry += result.Mul(multipler);
++iter; ++iter;
} }
if( err ) if( err )
@@ -2168,16 +2168,16 @@ namespace ttmath
static History<ValueType> history; static History<ValueType> history;
ValueType result; ValueType result;
if( x.IsNan() || x.IsSign() ) if( x.IsNan() || x.IsSign() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return result; // NaN set by default return result; // NaN set by default
} }
result.SetOne(); result.SetOne();
if( !x.exponent.IsSign() && !x.exponent.IsZero() ) if( !x.exponent.IsSign() && !x.exponent.IsZero() )
{ {
// when x.exponent>0 there's no sense to calculate the formula // when x.exponent>0 there's no sense to calculate the formula
@@ -2256,25 +2256,25 @@ namespace ttmath
e.g. e.g.
mod( 12.6 ; 3) = 0.6 because 12.6 = 3*4 + 0.6 mod( 12.6 ; 3) = 0.6 because 12.6 = 3*4 + 0.6
mod(-12.6 ; 3) = -0.6 bacause -12.6 = 3*(-4) + (-0.6) mod(-12.6 ; 3) = -0.6 bacause -12.6 = 3*(-4) + (-0.6)
mod( 12.6 ; -3) = 0.6 mod( 12.6 ; -3) = 0.6
mod(-12.6 ; -3) = -0.6 mod(-12.6 ; -3) = -0.6
*/ */
template<class ValueType> template<class ValueType>
ValueType Mod(ValueType a, const ValueType & b, ErrorCode * err = 0) ValueType Mod(ValueType a, const ValueType & b, ErrorCode * err = 0)
{ {
if( a.IsNan() || b.IsNan() ) if( a.IsNan() || b.IsNan() )
{ {
if( err ) if( err )
*err = err_improper_argument; *err = err_improper_argument;
return ValueType(); // NaN is set by default return ValueType(); // NaN is set by default
} }
uint c = a.Mod(b); uint c = a.Mod(b);
if( err ) if( err )
*err = c ? err_overflow : err_ok; *err = c ? err_overflow : err_ok;
return a; return a;
} }
@@ -2290,11 +2290,11 @@ namespace ttmath
*/ */
#include "ttmathparser.h" #include "ttmathparser.h"
#ifdef _MSC_VER #ifdef _MSC_VER
#pragma warning( default: 4127 ) #pragma warning( default: 4127 )
//warning C4127: conditional expression is constant //warning C4127: conditional expression is constant
#endif
#endif #endif
#endif

View File

@@ -3864,26 +3864,36 @@ public:
return false; return false;
} }
bool IsNearZero() const bool AboutEqualWithoutSign(const Big<exp,man> & ss2, int nBitsToIgnore = 4) const
{ {
// we should check the mantissas beforehand because sometimes we can have // we should check the mantissas beforehand because sometimes we can have
// a mantissa set to zero but in the exponent something another value // a mantissa set to zero but in the exponent something another value
// (maybe we've forgotten about calling CorrectZero() ?) // (maybe we've forgotten about calling CorrectZero() ?)
if( mantissa.IsZero() ) if( mantissa.IsZero() && ss2.mantissa.IsZero())
{ {
return true; return true;
} }
UInt<man> m(mantissa); if( exponent==ss2.exponent )
{
m.Rcr(man*3); // pi * thumb rule... if (mantissa == ss2.mantissa)
{
return(m.IsZero()); return(true);
}
ASSERT(nBitsToIgnore < TTMATH_BITS_PER_UINT);
for (int n = man-1; n > 0; --n)
{
if (mantissa.table[n] != ss2.mantissa.table[n])
return(false);
}
uint nMask = ~((1 << nBitsToIgnore) - 1);
return((mantissa.table[0] & nMask) == (ss2.mantissa.table[0] & nMask));
}
return false; return false;
} }
bool operator<(const Big<exp,man> & ss2) const bool operator<(const Big<exp,man> & ss2) const
{ {
if( IsSign() && !ss2.IsSign() ) if( IsSign() && !ss2.IsSign() )
@@ -3914,16 +3924,6 @@ public:
} }
bool operator^=(const Big<exp,man> & ss2) const
{
if( IsSign() != ss2.IsSign() )
return false;
return AboutEqualWithoutSign( ss2 );
}
bool operator>(const Big<exp,man> & ss2) const bool operator>(const Big<exp,man> & ss2) const
{ {
if( IsSign() && !ss2.IsSign() ) if( IsSign() && !ss2.IsSign() )

View File

@@ -64,8 +64,8 @@
*/ */
#define TTMATH_MAJOR_VER 0 #define TTMATH_MAJOR_VER 0
#define TTMATH_MINOR_VER 8 #define TTMATH_MINOR_VER 8
#define TTMATH_REVISION_VER 5 #define TTMATH_REVISION_VER 5
#define TTMATH_PRERELEASE_VER 0 #define TTMATH_PRERELEASE_VER 0
/*! /*!
@@ -232,16 +232,16 @@ namespace ttmath
/*! /*!
this is a limit when calculating Karatsuba multiplication this is a limit when calculating Karatsuba multiplication
if the size of a vector is smaller than TTMATH_USE_KARATSUBA_MULTIPLICATION_FROM_SIZE if the size of a vector is smaller than TTMATH_USE_KARATSUBA_MULTIPLICATION_FROM_SIZE
the Karatsuba algorithm will use standard schoolbook multiplication the Karatsuba algorithm will use standard schoolbook multiplication
*/ */
#ifdef __GNUC__ #ifdef __GNUC__
#define TTMATH_USE_KARATSUBA_MULTIPLICATION_FROM_SIZE 3 #define TTMATH_USE_KARATSUBA_MULTIPLICATION_FROM_SIZE 3
#else #else
#define TTMATH_USE_KARATSUBA_MULTIPLICATION_FROM_SIZE 5 #define TTMATH_USE_KARATSUBA_MULTIPLICATION_FROM_SIZE 5
#endif #endif
namespace ttmath namespace ttmath
{ {