mirror of
https://github.com/Tencent/rapidjson.git
synced 2025-03-10 03:29:59 +01:00
Remove unused code paths in double conversions
This commit is contained in:
parent
5b89f331c5
commit
37d820a13e
@ -135,25 +135,9 @@ struct DiyFp {
|
||||
double d;
|
||||
uint64_t u64;
|
||||
}u;
|
||||
uint64_t significand = f;
|
||||
int exponent = e;
|
||||
while (significand > kDpHiddenBit + kDpSignificandMask) {
|
||||
significand >>= 1;
|
||||
exponent++;
|
||||
}
|
||||
while (exponent > kDpDenormalExponent && (significand & kDpHiddenBit) == 0) {
|
||||
significand <<= 1;
|
||||
exponent--;
|
||||
}
|
||||
if (exponent >= kDpMaxExponent) {
|
||||
u.u64 = kDpExponentMask; // Infinity
|
||||
return u.d;
|
||||
}
|
||||
else if (exponent < kDpDenormalExponent)
|
||||
return 0.0;
|
||||
const uint64_t be = (exponent == kDpDenormalExponent && (significand & kDpHiddenBit) == 0) ? 0 :
|
||||
static_cast<uint64_t>(exponent + kDpExponentBias);
|
||||
u.u64 = (significand & kDpSignificandMask) | (be << kDpSignificandSize);
|
||||
const uint64_t be = (e == kDpDenormalExponent && (f & kDpHiddenBit) == 0) ? 0 :
|
||||
static_cast<uint64_t>(e + kDpExponentBias);
|
||||
u.u64 = (f & kDpSignificandMask) | (be << kDpSignificandSize);
|
||||
return u.d;
|
||||
}
|
||||
|
||||
|
@ -50,8 +50,10 @@ inline unsigned CountDecimalDigit32(uint32_t n) {
|
||||
if (n < 1000000) return 6;
|
||||
if (n < 10000000) return 7;
|
||||
if (n < 100000000) return 8;
|
||||
if (n < 1000000000) return 9;
|
||||
return 10;
|
||||
// Will not reach 10 digits in DigitGen()
|
||||
//if (n < 1000000000) return 9;
|
||||
//return 10;
|
||||
return 9;
|
||||
}
|
||||
|
||||
inline void DigitGen(const DiyFp& W, const DiyFp& Mp, uint64_t delta, char* buffer, int* len, int* K) {
|
||||
@ -60,13 +62,12 @@ inline void DigitGen(const DiyFp& W, const DiyFp& Mp, uint64_t delta, char* buff
|
||||
const DiyFp wp_w = Mp - W;
|
||||
uint32_t p1 = static_cast<uint32_t>(Mp.f >> -one.e);
|
||||
uint64_t p2 = Mp.f & (one.f - 1);
|
||||
int kappa = CountDecimalDigit32(p1);
|
||||
int kappa = CountDecimalDigit32(p1); // kappa in [0, 9]
|
||||
*len = 0;
|
||||
|
||||
while (kappa > 0) {
|
||||
uint32_t d;
|
||||
uint32_t d = 0;
|
||||
switch (kappa) {
|
||||
case 10: d = p1 / 1000000000; p1 %= 1000000000; break;
|
||||
case 9: d = p1 / 100000000; p1 %= 100000000; break;
|
||||
case 8: d = p1 / 10000000; p1 %= 10000000; break;
|
||||
case 7: d = p1 / 1000000; p1 %= 1000000; break;
|
||||
@ -76,14 +77,6 @@ inline void DigitGen(const DiyFp& W, const DiyFp& Mp, uint64_t delta, char* buff
|
||||
case 3: d = p1 / 100; p1 %= 100; break;
|
||||
case 2: d = p1 / 10; p1 %= 10; break;
|
||||
case 1: d = p1; p1 = 0; break;
|
||||
default:
|
||||
#if defined(_MSC_VER)
|
||||
__assume(0);
|
||||
#elif __GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 5)
|
||||
__builtin_unreachable();
|
||||
#else
|
||||
d = 0;
|
||||
#endif
|
||||
}
|
||||
if (d || *len)
|
||||
buffer[(*len)++] = static_cast<char>('0' + static_cast<char>(d));
|
||||
|
@ -34,14 +34,6 @@ public:
|
||||
return Double(u + 1).Value();
|
||||
}
|
||||
|
||||
double PreviousPositiveDouble() const {
|
||||
RAPIDJSON_ASSERT(!Sign());
|
||||
if (IsZero())
|
||||
return 0.0;
|
||||
else
|
||||
return Double(u - 1).Value();
|
||||
}
|
||||
|
||||
bool Sign() const { return (u & kSignMask) != 0; }
|
||||
uint64_t Significand() const { return u & kSignificandMask; }
|
||||
int Exponent() const { return ((u & kExponentMask) >> kSignificandSize) - kExponentBias; }
|
||||
|
@ -52,7 +52,7 @@ inline T Min3(T a, T b, T c) {
|
||||
return m;
|
||||
}
|
||||
|
||||
inline int CheckWithinHalfULP(double b, const BigInteger& d, int dExp, bool* adjustToNegative) {
|
||||
inline int CheckWithinHalfULP(double b, const BigInteger& d, int dExp) {
|
||||
const Double db(b);
|
||||
const uint64_t bInt = db.IntegerSignificand();
|
||||
const int bExp = db.IntegerExponent();
|
||||
@ -104,12 +104,12 @@ inline int CheckWithinHalfULP(double b, const BigInteger& d, int dExp, bool* adj
|
||||
hS.MultiplyPow5(hS_Exp5) <<= hS_Exp2;
|
||||
|
||||
BigInteger delta(0);
|
||||
*adjustToNegative = dS.Difference(bS, &delta);
|
||||
bool adjustToNegative = dS.Difference(bS, &delta);
|
||||
|
||||
int cmp = delta.Compare(hS);
|
||||
// If delta is within 1/2 ULP, check for special case when significand is power of two.
|
||||
// In this case, need to compare with 1/2h in the lower bound.
|
||||
if (cmp < 0 && *adjustToNegative && // within and dS < bS
|
||||
if (cmp < 0 && adjustToNegative && // within and dS < bS
|
||||
db.IsNormal() && (bInt & (bInt - 1)) == 0 && // Power of 2
|
||||
db.Uint64Value() != RAPIDJSON_UINT64_C2(0x00100000, 0x00000000)) // minimum normal number must not do this
|
||||
{
|
||||
@ -213,24 +213,18 @@ inline double StrtodBigInteger(double approx, const char* decimals, size_t lengt
|
||||
const BigInteger dInt(decimals, length);
|
||||
const int dExp = (int)decimalPosition - (int)length + exp;
|
||||
Double a(approx);
|
||||
for (int i = 0; i < 10; i++) {
|
||||
bool adjustToNegative;
|
||||
int cmp = CheckWithinHalfULP(a.Value(), dInt, dExp, &adjustToNegative);
|
||||
if (cmp < 0)
|
||||
return a.Value(); // within half ULP
|
||||
else if (cmp == 0) {
|
||||
// Round towards even
|
||||
if (a.Significand() & 1)
|
||||
return adjustToNegative ? a.PreviousPositiveDouble() : a.NextPositiveDouble();
|
||||
else
|
||||
return a.Value();
|
||||
}
|
||||
else // adjustment
|
||||
a = adjustToNegative ? a.PreviousPositiveDouble() : a.NextPositiveDouble();
|
||||
int cmp = CheckWithinHalfULP(a.Value(), dInt, dExp);
|
||||
if (cmp < 0)
|
||||
return a.Value(); // within half ULP
|
||||
else if (cmp == 0) {
|
||||
// Round towards even
|
||||
if (a.Significand() & 1)
|
||||
return a.NextPositiveDouble();
|
||||
else
|
||||
return a.Value();
|
||||
}
|
||||
|
||||
// This should not happen, but in case there is really a bug, break the infinite-loop
|
||||
return a.Value();
|
||||
else // adjustment
|
||||
return a.NextPositiveDouble();
|
||||
}
|
||||
|
||||
inline double StrtodFullPrecision(double d, int p, const char* decimals, size_t length, size_t decimalPosition, int exp) {
|
||||
|
Loading…
x
Reference in New Issue
Block a user