added: to Big::Add Big::Sub Big::Mul Big::Div
second parameter 'bool round = true' the rounding is made if it is true changed: in Big::ToString_CreateNewMantissaAndExponent() we should use dividing without rounding consider this 32 bit binary value: 1.1111111111111111111111111111111 previous the result from converting (to the base 10) was equal 2 now is 1.999999 git-svn-id: svn://ttmath.org/publicrep/ttmath/trunk@263 e52654a7-88a9-db11-a3e9-0013d4bc506e
This commit is contained in:
parent
82711f4441
commit
418db51f46
|
@ -869,7 +869,7 @@ public:
|
||||||
|
|
||||||
it returns carry if the sum is too big
|
it returns carry if the sum is too big
|
||||||
*/
|
*/
|
||||||
uint Add(Big<exp, man> ss2)
|
uint Add(Big<exp, man> ss2, bool round = true)
|
||||||
{
|
{
|
||||||
Int<exp> exp_offset( exponent );
|
Int<exp> exp_offset( exponent );
|
||||||
|
|
||||||
|
@ -904,7 +904,7 @@ public:
|
||||||
if( do_adding )
|
if( do_adding )
|
||||||
c += AddMantissas(ss2, last_bit_set, rest_zero, do_rounding, rounding_up);
|
c += AddMantissas(ss2, last_bit_set, rest_zero, do_rounding, rounding_up);
|
||||||
|
|
||||||
if( do_rounding && last_bit_set )
|
if( round && do_rounding && last_bit_set )
|
||||||
c += RoundHalfToEven(rest_zero, rounding_up);
|
c += RoundHalfToEven(rest_zero, rounding_up);
|
||||||
|
|
||||||
if( do_adding || (do_rounding && last_bit_set) )
|
if( do_adding || (do_rounding && last_bit_set) )
|
||||||
|
@ -919,11 +919,11 @@ public:
|
||||||
|
|
||||||
it returns carry if the result is too big
|
it returns carry if the result is too big
|
||||||
*/
|
*/
|
||||||
uint Sub(Big<exp, man> ss2)
|
uint Sub(Big<exp, man> ss2, bool round = true)
|
||||||
{
|
{
|
||||||
ss2.ChangeSign();
|
ss2.ChangeSign();
|
||||||
|
|
||||||
return Add(ss2);
|
return Add(ss2, round);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1233,7 +1233,7 @@ public:
|
||||||
multiplication this = this * ss2
|
multiplication this = this * ss2
|
||||||
this method returns a carry
|
this method returns a carry
|
||||||
*/
|
*/
|
||||||
uint Mul(const Big<exp, man> & ss2)
|
uint Mul(const Big<exp, man> & ss2, bool round = true)
|
||||||
{
|
{
|
||||||
TTMATH_REFERENCE_ASSERT( ss2 )
|
TTMATH_REFERENCE_ASSERT( ss2 )
|
||||||
|
|
||||||
|
@ -1272,7 +1272,7 @@ public:
|
||||||
for(i=0 ; i<man ; ++i)
|
for(i=0 ; i<man ; ++i)
|
||||||
mantissa.table[i] = man_result.table[i+man];
|
mantissa.table[i] = man_result.table[i+man];
|
||||||
|
|
||||||
if( (man_result.table[man-1] & TTMATH_UINT_HIGHEST_BIT) != 0 )
|
if( round && (man_result.table[man-1] & TTMATH_UINT_HIGHEST_BIT) != 0 )
|
||||||
{
|
{
|
||||||
bool is_half = CheckGreaterOrEqualHalf(man_result.table, man);
|
bool is_half = CheckGreaterOrEqualHalf(man_result.table, man);
|
||||||
c += RoundHalfToEven(is_half);
|
c += RoundHalfToEven(is_half);
|
||||||
|
@ -1304,7 +1304,7 @@ public:
|
||||||
1 - carry (in a division carry can be as well)
|
1 - carry (in a division carry can be as well)
|
||||||
2 - improper argument (ss2 is zero)
|
2 - improper argument (ss2 is zero)
|
||||||
*/
|
*/
|
||||||
uint Div(const Big<exp, man> & ss2)
|
uint Div(const Big<exp, man> & ss2, bool round = true)
|
||||||
{
|
{
|
||||||
TTMATH_REFERENCE_ASSERT( ss2 )
|
TTMATH_REFERENCE_ASSERT( ss2 )
|
||||||
|
|
||||||
|
@ -1348,10 +1348,10 @@ public:
|
||||||
for(i=0 ; i<man ; ++i)
|
for(i=0 ; i<man ; ++i)
|
||||||
mantissa.table[i] = man1.table[i+man];
|
mantissa.table[i] = man1.table[i+man];
|
||||||
|
|
||||||
if( (man1.table[man-1] & TTMATH_UINT_HIGHEST_BIT) != 0 )
|
if( round && (man1.table[man-1] & TTMATH_UINT_HIGHEST_BIT) != 0 )
|
||||||
{
|
{
|
||||||
bool is_half = CheckGreaterOrEqualHalf(man1.table, man);
|
bool is_half = CheckGreaterOrEqualHalf(man1.table, man);
|
||||||
c += RoundHalfToEven(is_half);
|
c += RoundHalfToEven(is_half, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
if( IsSign() == ss2.IsSign() )
|
if( IsSign() == ss2.IsSign() )
|
||||||
|
@ -3225,24 +3225,12 @@ private:
|
||||||
*/
|
*/
|
||||||
Int<exp+1> new_exp;
|
Int<exp+1> new_exp;
|
||||||
|
|
||||||
if( ToString_CreateNewMantissaAndExponent(result, conv, new_exp) )
|
if( ToString_CreateNewMantissaAndExponent<string_type, char_type>(result, conv, new_exp) )
|
||||||
{
|
{
|
||||||
Misc::AssignString(result, error_overflow_msg);
|
Misc::AssignString(result, error_overflow_msg);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
we're rounding the mantissa only if the base is different from 2,4,8 or 16
|
|
||||||
(this formula means that the number of bits in the base is greater than one)
|
|
||||||
*/
|
|
||||||
if( conv.base_round && conv.base!=2 && conv.base!=4 && conv.base!=8 && conv.base!=16 )
|
|
||||||
{
|
|
||||||
if( ToString_BaseRound<string_type, char_type>(result, conv, new_exp) )
|
|
||||||
{
|
|
||||||
Misc::AssignString(result, error_overflow_msg);
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if( ToString_SetCommaAndExponent<string_type, char_type>(result, conv, new_exp) )
|
if( ToString_SetCommaAndExponent<string_type, char_type>(result, conv, new_exp) )
|
||||||
{
|
{
|
||||||
|
@ -3313,7 +3301,7 @@ private:
|
||||||
M = mm * 2^ee where ee will be <= 0
|
M = mm * 2^ee where ee will be <= 0
|
||||||
|
|
||||||
next we'll move all bits of mm into the right when ee is equal zero
|
next we'll move all bits of mm into the right when ee is equal zero
|
||||||
abs(ee) must not to be too big that only few bits from mm we can leave
|
abs(ee) must not be too big that only few bits from mm we can leave
|
||||||
|
|
||||||
then we'll have:
|
then we'll have:
|
||||||
M = mmm * 2^0
|
M = mmm * 2^0
|
||||||
|
@ -3327,7 +3315,7 @@ private:
|
||||||
but we need 'new'exp' as integer then we take:
|
but we need 'new'exp' as integer then we take:
|
||||||
new_exp = [log base (2^exponent)] + 1 <- where [x] means integer value from x
|
new_exp = [log base (2^exponent)] + 1 <- where [x] means integer value from x
|
||||||
*/
|
*/
|
||||||
template<class string_type>
|
template<class string_type, class char_type>
|
||||||
uint ToString_CreateNewMantissaAndExponent( string_type & new_man, const Conv & conv,
|
uint ToString_CreateNewMantissaAndExponent( string_type & new_man, const Conv & conv,
|
||||||
Int<exp+1> & new_exp) const
|
Int<exp+1> & new_exp) const
|
||||||
{
|
{
|
||||||
|
@ -3389,7 +3377,7 @@ private:
|
||||||
// the sign don't interest us here
|
// the sign don't interest us here
|
||||||
temp.mantissa = mantissa;
|
temp.mantissa = mantissa;
|
||||||
temp.exponent = exponent;
|
temp.exponent = exponent;
|
||||||
c += temp.Div( base_ );
|
c += temp.Div(base_, false); // dividing without rounding
|
||||||
|
|
||||||
// moving all bits of the mantissa into the right
|
// moving all bits of the mantissa into the right
|
||||||
// (how many times to move depend on the exponent)
|
// (how many times to move depend on the exponent)
|
||||||
|
@ -3406,6 +3394,10 @@ private:
|
||||||
// shouldn't have had a carry
|
// shouldn't have had a carry
|
||||||
// (in the future this can be changed)
|
// (in the future this can be changed)
|
||||||
|
|
||||||
|
// base rounding
|
||||||
|
if( conv.base_round )
|
||||||
|
c += ToString_BaseRound<string_type, char_type>(new_man, conv, new_exp);
|
||||||
|
|
||||||
return (c==0)? 0 : 1;
|
return (c==0)? 0 : 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue