added: to Big<> class: support for NaN flag (Not a Number)
bool Big::IsNan() - returns true if the NaN flag is set void Big::SetNan() - sets the NaN flag The NaN flag is set by default after creating an object: Big<1, 2> a; // NaN is set (it means the object has not a valid number) std::cout << a; // cout gives "NaN" a = 123; // now NaN is not set std::cout << a; // cout gives "123" The NaN is set if there was a carry during calculations a.Mul(very_big_value); // a will have a NaN set The NaN is set if an argument is NaN too b.SetNan(); a.Add(b); // a will have NaN because b has NaN too If you try to do something on a NaN object, the result is a NaN too a.SetNan(); a.Add(2); // a is still a NaN The NaN is set if you use incorrect arguments a.Ln(-10); // a will have the NaN flag The only way to clear the NaN flag is to assign a correct value or other correct object supposing 'a' has NaN flag, to remove the flag you can either: a = 10; a.FromInt(30); a.SetOne(); a.FromBig(other_object_without_nan); etc. changed: renamed macro CONSTANTSGENERATOR to TTMATH_CONSTANTSGENERATOR git-svn-id: svn://ttmath.org/publicrep/ttmath/trunk@152 e52654a7-88a9-db11-a3e9-0013d4bc506e
This commit is contained in:
parent
5e5a106605
commit
bb2583649e
|
@ -1,6 +1,6 @@
|
||||||
o = main.o
|
o = main.o
|
||||||
CC = g++
|
CC = g++
|
||||||
CFLAGS = -s -O2 -DCONSTANTSGENERATOR
|
CFLAGS = -s -O2 -DTTMATH_CONSTANTSGENERATOR
|
||||||
name = gen
|
name = gen
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -91,7 +91,7 @@ void CalcE()
|
||||||
ttmath::Big<1,400> e;
|
ttmath::Big<1,400> e;
|
||||||
ttmath::uint steps;
|
ttmath::uint steps;
|
||||||
|
|
||||||
// macro CONSTANTSGENERATOR has to be defined
|
// macro TTMATH_CONSTANTSGENERATOR has to be defined
|
||||||
e.ExpSurrounding0(1, &steps);
|
e.ExpSurrounding0(1, &steps);
|
||||||
std::cout << "---------------- e ----------------" << std::endl;
|
std::cout << "---------------- e ----------------" << std::endl;
|
||||||
e.mantissa.PrintTable(std::cout);
|
e.mantissa.PrintTable(std::cout);
|
||||||
|
@ -105,7 +105,7 @@ void CalcLn(int x)
|
||||||
ttmath::Big<1,400> ln;
|
ttmath::Big<1,400> ln;
|
||||||
ttmath::uint steps;
|
ttmath::uint steps;
|
||||||
|
|
||||||
// macro CONSTANTSGENERATOR has to be defined
|
// macro TTMATH_CONSTANTSGENERATOR has to be defined
|
||||||
ln.LnSurrounding1(x, &steps);
|
ln.LnSurrounding1(x, &steps);
|
||||||
std::cout << "---------------- ln(" << x << ") ----------------" << std::endl;
|
std::cout << "---------------- ln(" << x << ") ----------------" << std::endl;
|
||||||
ln.mantissa.PrintTable(std::cout);
|
ln.mantissa.PrintTable(std::cout);
|
||||||
|
|
|
@ -472,11 +472,13 @@ namespace ttmath
|
||||||
{
|
{
|
||||||
// x is too big, we cannnot reduce the 2*PI period
|
// x is too big, we cannnot reduce the 2*PI period
|
||||||
// prior to version 0.8.5 the result was zero
|
// prior to version 0.8.5 the result was zero
|
||||||
|
|
||||||
|
// result has NaN flag set by default
|
||||||
|
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_overflow; // maybe another error code?
|
*err = err_overflow; // maybe another error code?
|
||||||
|
|
||||||
return result; // result we remain as undefined
|
return result; // NaN is set by default
|
||||||
}
|
}
|
||||||
|
|
||||||
result = Sin0pi05( x );
|
result = Sin0pi05( x );
|
||||||
|
@ -516,7 +518,7 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_overflow;
|
*err = err_overflow;
|
||||||
|
|
||||||
return ValueType(); // result is undefined
|
return ValueType(); // result is undefined (NaN is set by default)
|
||||||
}
|
}
|
||||||
|
|
||||||
return Sin(x, err);
|
return Sin(x, err);
|
||||||
|
@ -546,6 +548,8 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
|
result.SetNan();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -586,6 +590,8 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
|
result.SetNan();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -770,7 +776,7 @@ namespace ttmath
|
||||||
{
|
{
|
||||||
using namespace auxiliaryfunctions;
|
using namespace auxiliaryfunctions;
|
||||||
|
|
||||||
ValueType one;
|
ValueType result, one;
|
||||||
one.SetOne();
|
one.SetOne();
|
||||||
bool change_sign = false;
|
bool change_sign = false;
|
||||||
|
|
||||||
|
@ -779,7 +785,7 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
return one;
|
return result; // NaN is set by default
|
||||||
}
|
}
|
||||||
|
|
||||||
if( x.IsSign() )
|
if( x.IsSign() )
|
||||||
|
@ -790,8 +796,6 @@ namespace ttmath
|
||||||
|
|
||||||
one.exponent.SubOne(); // =0.5
|
one.exponent.SubOne(); // =0.5
|
||||||
|
|
||||||
ValueType result;
|
|
||||||
|
|
||||||
// asin(-x) = -asin(x)
|
// asin(-x) = -asin(x)
|
||||||
if( x.GreaterWithoutSignThan(one) )
|
if( x.GreaterWithoutSignThan(one) )
|
||||||
result = ASin_1(x);
|
result = ASin_1(x);
|
||||||
|
@ -1171,7 +1175,7 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
return x;
|
return ValueType(); // NaN is set by default
|
||||||
}
|
}
|
||||||
|
|
||||||
ValueType ex, emx, nominator, denominator;
|
ValueType ex, emx, nominator, denominator;
|
||||||
|
@ -1260,7 +1264,7 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
return result;
|
return result; // NaN is set by default
|
||||||
}
|
}
|
||||||
|
|
||||||
c += xx.Mul(x);
|
c += xx.Mul(x);
|
||||||
|
@ -1301,7 +1305,7 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
return result;
|
return result; // NaN is set by default
|
||||||
}
|
}
|
||||||
|
|
||||||
c += nominator.Add(one);
|
c += nominator.Add(one);
|
||||||
|
@ -1346,7 +1350,7 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
return result;
|
return result; // NaN is set by default
|
||||||
}
|
}
|
||||||
|
|
||||||
c += nominator.Add(one);
|
c += nominator.Add(one);
|
||||||
|
@ -1465,7 +1469,7 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
return delimiter;
|
return delimiter; // NaN is set by default
|
||||||
}
|
}
|
||||||
|
|
||||||
multipler = 60;
|
multipler = 60;
|
||||||
|
@ -1646,7 +1650,7 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
return x;
|
return ValueType(); // NaN is set by default
|
||||||
}
|
}
|
||||||
|
|
||||||
if( x.IsZero() )
|
if( x.IsZero() )
|
||||||
|
@ -1684,6 +1688,8 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
|
x.SetNan();
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1702,6 +1708,8 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
|
x.SetNan();
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1751,6 +1759,8 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
|
x.SetNan();
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1799,6 +1809,8 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
|
x.SetNan();
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1832,7 +1844,7 @@ namespace ttmath
|
||||||
if( RootCheckIndexZero(x, index, err) ) return x;
|
if( RootCheckIndexZero(x, index, err) ) return x;
|
||||||
if( RootCheckIndexOne (x, index, err) ) return x;
|
if( RootCheckIndexOne (x, index, err) ) return x;
|
||||||
if( RootCheckIndexFrac(x, index, err) ) return x;
|
if( RootCheckIndexFrac(x, index, err) ) return x;
|
||||||
if( RootCheckXZero(x, index, err) ) return x;
|
if( RootCheckXZero (x, index, err) ) return x;
|
||||||
|
|
||||||
// index integer and index!=0
|
// index integer and index!=0
|
||||||
// x!=0
|
// x!=0
|
||||||
|
@ -1883,6 +1895,7 @@ namespace ttmath
|
||||||
|
|
||||||
while( !carry && multipler<maxvalue )
|
while( !carry && multipler<maxvalue )
|
||||||
{
|
{
|
||||||
|
// !! the test here we don't have to make in all iterations (performance)
|
||||||
if( stop && stop->WasStopSignal() )
|
if( stop && stop->WasStopSignal() )
|
||||||
{
|
{
|
||||||
if( err )
|
if( err )
|
||||||
|
@ -1915,6 +1928,7 @@ namespace ttmath
|
||||||
|
|
||||||
while( !carry && multipler < x )
|
while( !carry && multipler < x )
|
||||||
{
|
{
|
||||||
|
// !! the test here we don't have to make in all iterations (performance)
|
||||||
if( stop && stop->WasStopSignal() )
|
if( stop && stop->WasStopSignal() )
|
||||||
{
|
{
|
||||||
if( err )
|
if( err )
|
||||||
|
@ -1958,6 +1972,8 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_improper_argument;
|
*err = err_improper_argument;
|
||||||
|
|
||||||
|
result.SetNan();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1969,6 +1985,8 @@ namespace ttmath
|
||||||
if( err )
|
if( err )
|
||||||
*err = err_overflow;
|
*err = err_overflow;
|
||||||
|
|
||||||
|
result.SetNan();
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1987,8 +2005,11 @@ namespace ttmath
|
||||||
status = FactorialMore(x, err, stop, result);
|
status = FactorialMore(x, err, stop, result);
|
||||||
|
|
||||||
if( status == 2 )
|
if( status == 2 )
|
||||||
|
{
|
||||||
// the calculation has been interrupted
|
// the calculation has been interrupted
|
||||||
|
result.SetNan();
|
||||||
return result;
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
err_tmp = status==1 ? err_overflow : err_ok;
|
err_tmp = status==1 ? err_overflow : err_ok;
|
||||||
history.Add(x, result, err_tmp);
|
history.Add(x, result, err_tmp);
|
||||||
|
|
|
@ -87,14 +87,35 @@ unsigned char info;
|
||||||
/*!
|
/*!
|
||||||
the number of a bit from 'info' which means that a value is with a sign
|
the number of a bit from 'info' which means that a value is with a sign
|
||||||
(when the bit is set)
|
(when the bit is set)
|
||||||
|
|
||||||
/at the moment the rest bits from 'info' are not used/
|
|
||||||
*/
|
*/
|
||||||
#define TTMATH_BIG_SIGN 128
|
#define TTMATH_BIG_SIGN 128
|
||||||
|
|
||||||
|
|
||||||
|
/*!
|
||||||
|
Not a number
|
||||||
|
if this bit is set that there is no a valid number
|
||||||
|
*/
|
||||||
|
#define TTMATH_BIG_NAN 64
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/*!
|
||||||
|
this method sets NaN if there was a carry (and returns 1 in such a case)
|
||||||
|
|
||||||
|
c can be 0, 1 or other value different from zero
|
||||||
|
*/
|
||||||
|
uint CheckCarry(uint c)
|
||||||
|
{
|
||||||
|
if( c != 0 )
|
||||||
|
{
|
||||||
|
SetNan();
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
|
||||||
|
|
||||||
|
@ -118,8 +139,9 @@ public:
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
uint comp = mantissa.CompensationToLeft();
|
uint comp = mantissa.CompensationToLeft();
|
||||||
|
uint c = exponent.Sub( comp );
|
||||||
|
|
||||||
return exponent.Sub( comp );
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -184,6 +206,15 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*!
|
||||||
|
this method sets NaN flag (Not a Number)
|
||||||
|
when this flag is set that means there is no a valid number
|
||||||
|
*/
|
||||||
|
void SetNan()
|
||||||
|
{
|
||||||
|
info |= TTMATH_BIG_NAN;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
|
@ -504,6 +535,7 @@ public:
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
we only have to test the mantissa
|
we only have to test the mantissa
|
||||||
|
also we don't check the NaN flag
|
||||||
*/
|
*/
|
||||||
return mantissa.IsZero();
|
return mantissa.IsZero();
|
||||||
}
|
}
|
||||||
|
@ -511,6 +543,7 @@ public:
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
this method returns true when there's the sign set
|
this method returns true when there's the sign set
|
||||||
|
also we don't check the NaN flag
|
||||||
*/
|
*/
|
||||||
bool IsSign() const
|
bool IsSign() const
|
||||||
{
|
{
|
||||||
|
@ -518,6 +551,16 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*!
|
||||||
|
this method returns true when there is not a valid number
|
||||||
|
*/
|
||||||
|
bool IsNan() const
|
||||||
|
{
|
||||||
|
return (info & TTMATH_BIG_NAN) == TTMATH_BIG_NAN;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
this method clears the sign
|
this method clears the sign
|
||||||
(there'll be an absolute value)
|
(there'll be an absolute value)
|
||||||
|
@ -540,6 +583,9 @@ public:
|
||||||
*/
|
*/
|
||||||
void Sgn()
|
void Sgn()
|
||||||
{
|
{
|
||||||
|
if( IsNan() )
|
||||||
|
return;
|
||||||
|
|
||||||
if( IsSign() )
|
if( IsSign() )
|
||||||
{
|
{
|
||||||
SetOne();
|
SetOne();
|
||||||
|
@ -614,6 +660,9 @@ public:
|
||||||
|
|
||||||
uint c = 0;
|
uint c = 0;
|
||||||
|
|
||||||
|
if( IsNan() || ss2.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
exp_offset.Sub( ss2.exponent );
|
exp_offset.Sub( ss2.exponent );
|
||||||
exp_offset.Abs();
|
exp_offset.Abs();
|
||||||
|
|
||||||
|
@ -662,7 +711,7 @@ public:
|
||||||
|
|
||||||
c += Standardizing();
|
c += Standardizing();
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -690,13 +739,16 @@ public:
|
||||||
*/
|
*/
|
||||||
uint BitAnd(Big<exp, man> ss2)
|
uint BitAnd(Big<exp, man> ss2)
|
||||||
{
|
{
|
||||||
|
if( IsNan() || ss2.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( IsSign() || ss2.IsSign() )
|
if( IsSign() || ss2.IsSign() )
|
||||||
return 2;
|
return 2;
|
||||||
|
|
||||||
Int<exp> exp_offset( exponent );
|
|
||||||
Int<exp> mantissa_size_in_bits( man * TTMATH_BITS_PER_UINT );
|
|
||||||
|
|
||||||
uint c = 0;
|
Int<exp> exp_offset( exponent );
|
||||||
|
Int<exp> mantissa_size_in_bits( man * TTMATH_BITS_PER_UINT );
|
||||||
|
|
||||||
|
uint c = 0;
|
||||||
|
|
||||||
exp_offset.Sub( ss2.exponent );
|
exp_offset.Sub( ss2.exponent );
|
||||||
exp_offset.Abs();
|
exp_offset.Abs();
|
||||||
|
@ -723,7 +775,7 @@ public:
|
||||||
|
|
||||||
c += Standardizing();
|
c += Standardizing();
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -738,13 +790,16 @@ public:
|
||||||
*/
|
*/
|
||||||
uint BitOr(Big<exp, man> ss2)
|
uint BitOr(Big<exp, man> ss2)
|
||||||
{
|
{
|
||||||
|
if( IsNan() || ss2.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( IsSign() || ss2.IsSign() )
|
if( IsSign() || ss2.IsSign() )
|
||||||
return 2;
|
return 2;
|
||||||
|
|
||||||
Int<exp> exp_offset( exponent );
|
Int<exp> exp_offset( exponent );
|
||||||
Int<exp> mantissa_size_in_bits( man * TTMATH_BITS_PER_UINT );
|
Int<exp> mantissa_size_in_bits( man * TTMATH_BITS_PER_UINT );
|
||||||
|
|
||||||
uint c = 0;
|
uint c = 0;
|
||||||
|
|
||||||
exp_offset.Sub( ss2.exponent );
|
exp_offset.Sub( ss2.exponent );
|
||||||
exp_offset.Abs();
|
exp_offset.Abs();
|
||||||
|
@ -768,7 +823,7 @@ public:
|
||||||
|
|
||||||
c += Standardizing();
|
c += Standardizing();
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -783,13 +838,16 @@ public:
|
||||||
*/
|
*/
|
||||||
uint BitXor(Big<exp, man> ss2)
|
uint BitXor(Big<exp, man> ss2)
|
||||||
{
|
{
|
||||||
|
if( IsNan() || ss2.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( IsSign() || ss2.IsSign() )
|
if( IsSign() || ss2.IsSign() )
|
||||||
return 2;
|
return 2;
|
||||||
|
|
||||||
Int<exp> exp_offset( exponent );
|
Int<exp> exp_offset( exponent );
|
||||||
Int<exp> mantissa_size_in_bits( man * TTMATH_BITS_PER_UINT );
|
Int<exp> mantissa_size_in_bits( man * TTMATH_BITS_PER_UINT );
|
||||||
|
|
||||||
uint c = 0;
|
uint c = 0;
|
||||||
|
|
||||||
exp_offset.Sub( ss2.exponent );
|
exp_offset.Sub( ss2.exponent );
|
||||||
exp_offset.Abs();
|
exp_offset.Abs();
|
||||||
|
@ -813,7 +871,7 @@ public:
|
||||||
|
|
||||||
c += Standardizing();
|
c += Standardizing();
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -828,6 +886,9 @@ public:
|
||||||
UInt<man+1> man_result;
|
UInt<man+1> man_result;
|
||||||
uint i,c = 0;
|
uint i,c = 0;
|
||||||
|
|
||||||
|
if( IsNan() )
|
||||||
|
return 1;
|
||||||
|
|
||||||
// man_result = mantissa * ss2.mantissa
|
// man_result = mantissa * ss2.mantissa
|
||||||
mantissa.MulInt(ss2, man_result);
|
mantissa.MulInt(ss2, man_result);
|
||||||
|
|
||||||
|
@ -837,7 +898,7 @@ public:
|
||||||
{
|
{
|
||||||
// 'i' will be from 0 to TTMATH_BITS_PER_UINT
|
// 'i' will be from 0 to TTMATH_BITS_PER_UINT
|
||||||
i = man_result.CompensationToLeft();
|
i = man_result.CompensationToLeft();
|
||||||
c = exponent.Add( TTMATH_BITS_PER_UINT - i );
|
c = exponent.Add( TTMATH_BITS_PER_UINT - i );
|
||||||
|
|
||||||
for(i=0 ; i<man ; ++i)
|
for(i=0 ; i<man ; ++i)
|
||||||
mantissa.table[i] = man_result.table[i+1];
|
mantissa.table[i] = man_result.table[i+1];
|
||||||
|
@ -856,7 +917,7 @@ public:
|
||||||
|
|
||||||
c += Standardizing();
|
c += Standardizing();
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -867,6 +928,9 @@ public:
|
||||||
*/
|
*/
|
||||||
uint MulInt(sint ss2)
|
uint MulInt(sint ss2)
|
||||||
{
|
{
|
||||||
|
if( IsNan() )
|
||||||
|
return 1;
|
||||||
|
|
||||||
if( ss2 == 0 )
|
if( ss2 == 0 )
|
||||||
{
|
{
|
||||||
SetZero();
|
SetZero();
|
||||||
|
@ -906,6 +970,9 @@ public:
|
||||||
UInt<man*2> man_result;
|
UInt<man*2> man_result;
|
||||||
uint i,c;
|
uint i,c;
|
||||||
|
|
||||||
|
if( IsNan() || ss2.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
// man_result = mantissa * ss2.mantissa
|
// man_result = mantissa * ss2.mantissa
|
||||||
mantissa.MulBig(ss2.mantissa, man_result);
|
mantissa.MulBig(ss2.mantissa, man_result);
|
||||||
|
|
||||||
|
@ -936,7 +1003,7 @@ public:
|
||||||
|
|
||||||
c += Standardizing();
|
c += Standardizing();
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -954,11 +1021,8 @@ public:
|
||||||
UInt<man*2> man2;
|
UInt<man*2> man2;
|
||||||
uint i,c = 0;
|
uint i,c = 0;
|
||||||
|
|
||||||
if( ss2.IsZero() )
|
if( IsNan() || ss2.IsNan() || ss2.IsZero() )
|
||||||
{
|
return CheckCarry(1);
|
||||||
// we don't divide by zero
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
for(i=0 ; i<man ; ++i)
|
for(i=0 ; i<man ; ++i)
|
||||||
{
|
{
|
||||||
|
@ -991,7 +1055,7 @@ public:
|
||||||
|
|
||||||
c += Standardizing();
|
c += Standardizing();
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1005,7 +1069,7 @@ public:
|
||||||
-12.6 mod -3 = -0.6
|
-12.6 mod -3 = -0.6
|
||||||
|
|
||||||
it means:
|
it means:
|
||||||
in other words: this(old) = ss2 * q + this(new -- result)
|
in other words: this(old) = ss2 * q + this(new)
|
||||||
*/
|
*/
|
||||||
uint Mod(const Big<exp, man> & ss2)
|
uint Mod(const Big<exp, man> & ss2)
|
||||||
{
|
{
|
||||||
|
@ -1013,6 +1077,9 @@ public:
|
||||||
|
|
||||||
uint c = 0;
|
uint c = 0;
|
||||||
|
|
||||||
|
if( IsNan() || ss2.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( !SmallerWithoutSignThan(ss2) )
|
if( !SmallerWithoutSignThan(ss2) )
|
||||||
{
|
{
|
||||||
Big<exp, man> temp(*this);
|
Big<exp, man> temp(*this);
|
||||||
|
@ -1026,7 +1093,7 @@ public:
|
||||||
c += 1;
|
c += 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1046,30 +1113,35 @@ public:
|
||||||
template<uint pow_size>
|
template<uint pow_size>
|
||||||
uint Pow(UInt<pow_size> pow)
|
uint Pow(UInt<pow_size> pow)
|
||||||
{
|
{
|
||||||
if(pow.IsZero() && IsZero())
|
if( IsNan() )
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
if( pow.IsZero() && IsZero() )
|
||||||
|
{
|
||||||
// we don't define zero^zero
|
// we don't define zero^zero
|
||||||
|
SetNan();
|
||||||
return 2;
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
Big<exp, man> start(*this), start_temp;
|
Big<exp, man> start(*this), start_temp;
|
||||||
Big<exp, man> result;
|
Big<exp, man> result;
|
||||||
result.SetOne();
|
result.SetOne();
|
||||||
|
uint c = 0;
|
||||||
|
|
||||||
while( !pow.IsZero() )
|
while( !c && !pow.IsZero() )
|
||||||
{
|
{
|
||||||
if( pow.table[0] & 1 )
|
if( pow.table[0] & 1 )
|
||||||
if( result.Mul(start) )
|
c += result.Mul(start);
|
||||||
return 1;
|
|
||||||
|
|
||||||
start_temp = start;
|
start_temp = start;
|
||||||
if( start.Mul(start_temp) )
|
c += start.Mul(start_temp);
|
||||||
return 1;
|
|
||||||
|
|
||||||
pow.Rcr(1);
|
pow.Rcr(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
*this = result;
|
*this = result;
|
||||||
|
|
||||||
return 0;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1085,27 +1157,29 @@ public:
|
||||||
template<uint pow_size>
|
template<uint pow_size>
|
||||||
uint Pow(Int<pow_size> pow)
|
uint Pow(Int<pow_size> pow)
|
||||||
{
|
{
|
||||||
|
if( IsNan() )
|
||||||
|
return 1;
|
||||||
|
|
||||||
if( !pow.IsSign() )
|
if( !pow.IsSign() )
|
||||||
return Pow( UInt<pow_size>(pow) );
|
return Pow( UInt<pow_size>(pow) );
|
||||||
|
|
||||||
if( IsZero() )
|
if( IsZero() )
|
||||||
|
{
|
||||||
// if 'p' is negative then
|
// if 'p' is negative then
|
||||||
// 'this' must be different from zero
|
// 'this' must be different from zero
|
||||||
|
SetNan();
|
||||||
return 2;
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
if( pow.ChangeSign() )
|
uint c = pow.ChangeSign();
|
||||||
return 1;
|
|
||||||
|
|
||||||
Big<exp, man> t(*this);
|
Big<exp, man> t(*this);
|
||||||
uint c_temp = t.Pow( UInt<pow_size>(pow) );
|
c += t.Pow( UInt<pow_size>(pow) ); // here can only be a carry (return:1)
|
||||||
if( c_temp > 0 )
|
|
||||||
return c_temp;
|
|
||||||
|
|
||||||
SetOne();
|
SetOne();
|
||||||
if( Div(t) )
|
c += Div(t);
|
||||||
return 1;
|
|
||||||
|
|
||||||
return 0;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1142,8 +1216,14 @@ public:
|
||||||
*/
|
*/
|
||||||
uint PowUInt(Big<exp, man> pow)
|
uint PowUInt(Big<exp, man> pow)
|
||||||
{
|
{
|
||||||
|
if( IsNan() || pow.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( pow.IsZero() && IsZero() )
|
if( pow.IsZero() && IsZero() )
|
||||||
|
{
|
||||||
|
SetNan();
|
||||||
return 2;
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
if( pow.IsSign() )
|
if( pow.IsSign() )
|
||||||
pow.Abs();
|
pow.Abs();
|
||||||
|
@ -1152,27 +1232,26 @@ public:
|
||||||
Big<exp, man> result;
|
Big<exp, man> result;
|
||||||
Big<exp, man> one;
|
Big<exp, man> one;
|
||||||
Int<exp> e_one;
|
Int<exp> e_one;
|
||||||
|
uint c = 0;
|
||||||
|
|
||||||
e_one.SetOne();
|
e_one.SetOne();
|
||||||
one.SetOne();
|
one.SetOne();
|
||||||
result = one;
|
result = one;
|
||||||
|
|
||||||
while( pow >= one )
|
while( !c && pow >= one )
|
||||||
{
|
{
|
||||||
if( pow.Mod2() )
|
if( pow.Mod2() )
|
||||||
if( result.Mul(start) )
|
c += result.Mul(start);
|
||||||
return 1;
|
|
||||||
|
|
||||||
start_temp = start;
|
start_temp = start;
|
||||||
if( start.Mul(start_temp) )
|
c += start.Mul(start_temp);
|
||||||
return 1;
|
|
||||||
|
|
||||||
pow.exponent.Sub( e_one );
|
c += pow.exponent.Sub( e_one );
|
||||||
}
|
}
|
||||||
|
|
||||||
*this = result;
|
*this = result;
|
||||||
|
|
||||||
return 0;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1190,24 +1269,27 @@ public:
|
||||||
{
|
{
|
||||||
TTMATH_REFERENCE_ASSERT( pow )
|
TTMATH_REFERENCE_ASSERT( pow )
|
||||||
|
|
||||||
|
if( IsNan() || pow.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( !pow.IsSign() )
|
if( !pow.IsSign() )
|
||||||
return PowUInt(pow);
|
return PowUInt(pow);
|
||||||
|
|
||||||
if( IsZero() )
|
if( IsZero() )
|
||||||
|
{
|
||||||
// if 'pow' is negative then
|
// if 'pow' is negative then
|
||||||
// 'this' must be different from zero
|
// 'this' must be different from zero
|
||||||
|
SetNan();
|
||||||
return 2;
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
Big<exp, man> temp(*this);
|
Big<exp, man> temp(*this);
|
||||||
uint c_temp = temp.PowUInt(pow);
|
uint c = temp.PowUInt(pow); // here can only be a carry (result:1)
|
||||||
if( c_temp > 0 )
|
|
||||||
return c_temp;
|
|
||||||
|
|
||||||
SetOne();
|
SetOne();
|
||||||
if( Div(temp) )
|
c += Div(temp);
|
||||||
return 1;
|
|
||||||
|
|
||||||
return 0;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1225,16 +1307,22 @@ public:
|
||||||
{
|
{
|
||||||
TTMATH_REFERENCE_ASSERT( pow )
|
TTMATH_REFERENCE_ASSERT( pow )
|
||||||
|
|
||||||
|
if( IsNan() || pow.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
Big<exp, man> temp;
|
Big<exp, man> temp;
|
||||||
uint c = temp.Ln(*this);
|
uint c = temp.Ln(*this);
|
||||||
|
|
||||||
if( c!= 0 )
|
if( c != 0 ) // can be 2 from Ln()
|
||||||
|
{
|
||||||
|
SetNan();
|
||||||
return c;
|
return c;
|
||||||
|
}
|
||||||
|
|
||||||
c += temp.Mul(pow);
|
c += temp.Mul(pow);
|
||||||
c += Exp(temp);
|
c += Exp(temp);
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1252,11 +1340,17 @@ public:
|
||||||
{
|
{
|
||||||
TTMATH_REFERENCE_ASSERT( pow )
|
TTMATH_REFERENCE_ASSERT( pow )
|
||||||
|
|
||||||
|
if( IsNan() || pow.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( IsZero() )
|
if( IsZero() )
|
||||||
{
|
{
|
||||||
// 0^pow will be 0 only for pow>0
|
// 0^pow will be 0 only for pow>0
|
||||||
if( pow.IsSign() || pow.IsZero() )
|
if( pow.IsSign() || pow.IsZero() )
|
||||||
|
{
|
||||||
|
SetNan();
|
||||||
return 2;
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
SetZero();
|
SetZero();
|
||||||
|
|
||||||
|
@ -1278,7 +1372,7 @@ public:
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
#ifdef CONSTANTSGENERATOR
|
#ifdef TTMATH_CONSTANTSGENERATOR
|
||||||
public:
|
public:
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -1306,7 +1400,7 @@ public:
|
||||||
old_value = *this;
|
old_value = *this;
|
||||||
|
|
||||||
// we begin from 1 in order to not testing at the beginning
|
// we begin from 1 in order to not testing at the beginning
|
||||||
#ifdef CONSTANTSGENERATOR
|
#ifdef TTMATH_CONSTANTSGENERATOR
|
||||||
for(i=1 ; true ; ++i)
|
for(i=1 ; true ; ++i)
|
||||||
#else
|
#else
|
||||||
for(i=1 ; i<=TTMATH_ARITHMETIC_MAX_LOOP ; ++i)
|
for(i=1 ; i<=TTMATH_ARITHMETIC_MAX_LOOP ; ++i)
|
||||||
|
@ -1367,6 +1461,9 @@ public:
|
||||||
{
|
{
|
||||||
uint c = 0;
|
uint c = 0;
|
||||||
|
|
||||||
|
if( x.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( x.IsZero() )
|
if( x.IsZero() )
|
||||||
{
|
{
|
||||||
SetOne();
|
SetOne();
|
||||||
|
@ -1419,7 +1516,7 @@ public:
|
||||||
c += PowUInt(e_);
|
c += PowUInt(e_);
|
||||||
}
|
}
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1427,7 +1524,7 @@ public:
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
#ifdef CONSTANTSGENERATOR
|
#ifdef TTMATH_CONSTANTSGENERATOR
|
||||||
public:
|
public:
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
@ -1469,7 +1566,7 @@ public:
|
||||||
uint i;
|
uint i;
|
||||||
|
|
||||||
|
|
||||||
#ifdef CONSTANTSGENERATOR
|
#ifdef TTMATH_CONSTANTSGENERATOR
|
||||||
for(i=1 ; true ; ++i)
|
for(i=1 ; true ; ++i)
|
||||||
#else
|
#else
|
||||||
// we begin from 1 in order to not testing at the beginning
|
// we begin from 1 in order to not testing at the beginning
|
||||||
|
@ -1532,15 +1629,21 @@ public:
|
||||||
|
|
||||||
return values:
|
return values:
|
||||||
0 - ok
|
0 - ok
|
||||||
1 - overflow
|
1 - overflow (carry)
|
||||||
2 - incorrect argument (x<=0)
|
2 - incorrect argument (x<=0)
|
||||||
*/
|
*/
|
||||||
uint Ln(const Big<exp,man> & x)
|
uint Ln(const Big<exp,man> & x)
|
||||||
{
|
{
|
||||||
TTMATH_REFERENCE_ASSERT( x )
|
TTMATH_REFERENCE_ASSERT( x )
|
||||||
|
|
||||||
|
if( x.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( x.IsSign() || x.IsZero() )
|
if( x.IsSign() || x.IsZero() )
|
||||||
|
{
|
||||||
|
SetNan();
|
||||||
return 2;
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
// m will be the value of the mantissa in range <1,2)
|
// m will be the value of the mantissa in range <1,2)
|
||||||
Big<exp,man> m(x);
|
Big<exp,man> m(x);
|
||||||
|
@ -1559,7 +1662,7 @@ public:
|
||||||
c += exponent_temp.Mul(ln2);
|
c += exponent_temp.Mul(ln2);
|
||||||
c += Add(exponent_temp);
|
c += Add(exponent_temp);
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1581,14 +1684,23 @@ public:
|
||||||
TTMATH_REFERENCE_ASSERT( base )
|
TTMATH_REFERENCE_ASSERT( base )
|
||||||
TTMATH_REFERENCE_ASSERT( x )
|
TTMATH_REFERENCE_ASSERT( x )
|
||||||
|
|
||||||
|
if( x.IsNan() || base.IsNan() )
|
||||||
|
return CheckCarry(1);
|
||||||
|
|
||||||
if( x.IsSign() || x.IsZero() )
|
if( x.IsSign() || x.IsZero() )
|
||||||
|
{
|
||||||
|
SetNan();
|
||||||
return 2;
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
Big<exp,man> denominator;;
|
Big<exp,man> denominator;;
|
||||||
denominator.SetOne();
|
denominator.SetOne();
|
||||||
|
|
||||||
if( base.IsSign() || base.IsZero() || base==denominator )
|
if( base.IsSign() || base.IsZero() || base==denominator )
|
||||||
|
{
|
||||||
|
SetNan();
|
||||||
return 3;
|
return 3;
|
||||||
|
}
|
||||||
|
|
||||||
if( x == denominator ) // (this is: if x == 1)
|
if( x == denominator ) // (this is: if x == 1)
|
||||||
{
|
{
|
||||||
|
@ -1597,14 +1709,14 @@ public:
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// another error values we've tested at the start
|
// another error values we've tested at the beginning
|
||||||
// there can be only a carry
|
// there can only be a carry
|
||||||
uint c = Ln(x);
|
uint c = Ln(x);
|
||||||
|
|
||||||
c += denominator.Ln(base);
|
c += denominator.Ln(base);
|
||||||
c += Div(denominator);
|
c += Div(denominator);
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1625,9 +1737,15 @@ public:
|
||||||
{
|
{
|
||||||
info = another.info;
|
info = another.info;
|
||||||
|
|
||||||
if( exponent.FromInt(another.exponent) )
|
if( IsNan() )
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
|
if( exponent.FromInt(another.exponent) )
|
||||||
|
{
|
||||||
|
SetNan();
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
uint man_len_min = (man < another_man)? man : another_man;
|
uint man_len_min = (man < another_man)? man : another_man;
|
||||||
uint i;
|
uint i;
|
||||||
uint c = 0;
|
uint c = 0;
|
||||||
|
@ -1641,7 +1759,7 @@ public:
|
||||||
|
|
||||||
// MS Visual Express 2005 reports a warning (in the lines with 'uint man_diff = ...'):
|
// MS Visual Express 2005 reports a warning (in the lines with 'uint man_diff = ...'):
|
||||||
// warning C4307: '*' : integral constant overflow
|
// warning C4307: '*' : integral constant overflow
|
||||||
// but we're using 'if( man > another_man )' and 'if( man < another_man )' and there'll be no such a situation here
|
// but we're using 'if( man > another_man )' and 'if( man < another_man )' and there'll be no such situation here
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
#pragma warning( disable: 4307 )
|
#pragma warning( disable: 4307 )
|
||||||
#endif
|
#endif
|
||||||
|
@ -1665,7 +1783,7 @@ public:
|
||||||
// mantissa doesn't have to be standardized (either the highest bit is set or all bits are equal zero)
|
// mantissa doesn't have to be standardized (either the highest bit is set or all bits are equal zero)
|
||||||
CorrectZero();
|
CorrectZero();
|
||||||
|
|
||||||
return (c == 0 )? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -2474,13 +2592,16 @@ public:
|
||||||
FromBig(value);
|
FromBig(value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
a default constructor
|
a default constructor
|
||||||
|
|
||||||
warning: we don't set any of the members to zero etc.
|
we don't set any of the members to zero
|
||||||
|
only NaN flag is set
|
||||||
*/
|
*/
|
||||||
Big()
|
Big()
|
||||||
{
|
{
|
||||||
|
SetNan();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -2497,7 +2618,7 @@ public:
|
||||||
*/
|
*/
|
||||||
Big<exp,man> & operator=(const Big<exp,man> & value)
|
Big<exp,man> & operator=(const Big<exp,man> & value)
|
||||||
{
|
{
|
||||||
info = value.info;
|
info = value.info;
|
||||||
exponent = value.exponent;
|
exponent = value.exponent;
|
||||||
mantissa = value.mantissa;
|
mantissa = value.mantissa;
|
||||||
|
|
||||||
|
@ -2561,9 +2682,16 @@ public:
|
||||||
char decimal_point = TTMATH_COMMA_CHARACTER_1 ) const
|
char decimal_point = TTMATH_COMMA_CHARACTER_1 ) const
|
||||||
{
|
{
|
||||||
static char error_overflow_msg[] = "overflow";
|
static char error_overflow_msg[] = "overflow";
|
||||||
|
static char error_nan_msg[] = "NaN";
|
||||||
result.erase();
|
result.erase();
|
||||||
|
|
||||||
if(base<2 || base>16)
|
if( IsNan() )
|
||||||
|
{
|
||||||
|
result = error_nan_msg;
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if( base<2 || base>16 )
|
||||||
{
|
{
|
||||||
result = error_overflow_msg;
|
result = error_overflow_msg;
|
||||||
return 1;
|
return 1;
|
||||||
|
@ -3257,6 +3385,8 @@ public:
|
||||||
|
|
||||||
if( base<2 || base>16 )
|
if( base<2 || base>16 )
|
||||||
{
|
{
|
||||||
|
SetNan();
|
||||||
|
|
||||||
if( after_source )
|
if( after_source )
|
||||||
*after_source = source;
|
*after_source = source;
|
||||||
|
|
||||||
|
@ -3286,7 +3416,7 @@ public:
|
||||||
if( value_read )
|
if( value_read )
|
||||||
*value_read = value_read_temp;
|
*value_read = value_read_temp;
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -3587,6 +3717,7 @@ public:
|
||||||
and returns the result
|
and returns the result
|
||||||
|
|
||||||
(in other words it treats 'this' and 'ss2' as values without a sign)
|
(in other words it treats 'this' and 'ss2' as values without a sign)
|
||||||
|
we don't check the NaN flag
|
||||||
*/
|
*/
|
||||||
bool SmallerWithoutSignThan(const Big<exp,man> & ss2) const
|
bool SmallerWithoutSignThan(const Big<exp,man> & ss2) const
|
||||||
{
|
{
|
||||||
|
@ -3621,6 +3752,7 @@ public:
|
||||||
and returns the result
|
and returns the result
|
||||||
|
|
||||||
(in other words it treats 'this' and 'ss2' as values without a sign)
|
(in other words it treats 'this' and 'ss2' as values without a sign)
|
||||||
|
we don't check the NaN flag
|
||||||
*/
|
*/
|
||||||
bool GreaterWithoutSignThan(const Big<exp,man> & ss2) const
|
bool GreaterWithoutSignThan(const Big<exp,man> & ss2) const
|
||||||
{
|
{
|
||||||
|
@ -3655,6 +3787,7 @@ public:
|
||||||
and returns the result
|
and returns the result
|
||||||
|
|
||||||
(in other words it treats 'this' and 'ss2' as values without a sign)
|
(in other words it treats 'this' and 'ss2' as values without a sign)
|
||||||
|
we don't check the NaN flag
|
||||||
*/
|
*/
|
||||||
bool EqualWithoutSign(const Big<exp,man> & ss2) const
|
bool EqualWithoutSign(const Big<exp,man> & ss2) const
|
||||||
{
|
{
|
||||||
|
@ -3861,7 +3994,7 @@ public:
|
||||||
*/
|
*/
|
||||||
void SkipFraction()
|
void SkipFraction()
|
||||||
{
|
{
|
||||||
if( IsZero() )
|
if( IsNan() || IsZero() )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if( !exponent.IsSign() )
|
if( !exponent.IsSign() )
|
||||||
|
@ -3895,7 +4028,7 @@ public:
|
||||||
*/
|
*/
|
||||||
void RemainFraction()
|
void RemainFraction()
|
||||||
{
|
{
|
||||||
if( IsZero() )
|
if( IsNan() || IsZero() )
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if( !exponent.IsSign() )
|
if( !exponent.IsSign() )
|
||||||
|
@ -3945,6 +4078,9 @@ public:
|
||||||
Big<exp,man> half;
|
Big<exp,man> half;
|
||||||
uint c;
|
uint c;
|
||||||
|
|
||||||
|
if( IsNan() )
|
||||||
|
return 1;
|
||||||
|
|
||||||
half.Set05();
|
half.Set05();
|
||||||
|
|
||||||
if( IsSign() )
|
if( IsSign() )
|
||||||
|
@ -3960,7 +4096,7 @@ public:
|
||||||
|
|
||||||
SkipFraction();
|
SkipFraction();
|
||||||
|
|
||||||
return c;
|
return CheckCarry(c);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1290,15 +1290,15 @@ namespace ttmath
|
||||||
#ifdef __GNUC__
|
#ifdef __GNUC__
|
||||||
uint dummy;
|
uint dummy;
|
||||||
|
|
||||||
__asm__ (
|
__asm__ (
|
||||||
|
|
||||||
"movl $-1, %1 \n"
|
"movl $-1, %1 \n"
|
||||||
"bsrl %2, %0 \n"
|
"bsrl %2, %0 \n"
|
||||||
"cmovz %1, %0 \n"
|
"cmovz %1, %0 \n"
|
||||||
|
|
||||||
: "=r" (result), "=&r" (dummy)
|
: "=r" (result), "=&r" (dummy)
|
||||||
: "r" (x)
|
: "r" (x)
|
||||||
: "cc" );
|
: "cc" );
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
|
@ -830,15 +830,15 @@ namespace ttmath
|
||||||
#ifdef __GNUC__
|
#ifdef __GNUC__
|
||||||
uint dummy;
|
uint dummy;
|
||||||
|
|
||||||
__asm__ (
|
__asm__ (
|
||||||
|
|
||||||
"movq $-1, %1 \n"
|
"movq $-1, %1 \n"
|
||||||
"bsrq %2, %0 \n"
|
"bsrq %2, %0 \n"
|
||||||
"cmovz %1, %0 \n"
|
"cmovz %1, %0 \n"
|
||||||
|
|
||||||
: "=r" (result), "=&r" (dummy)
|
: "=r" (result), "=&r" (dummy)
|
||||||
: "r" (x)
|
: "r" (x)
|
||||||
: "cc" );
|
: "cc" );
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue