Wed, 31 Dec 2014 07:22:50 +0100
Correct previous dual key logic pending first delivery installment.
michael@0 | 1 | diff --git a/mfbt/decimal/Decimal.cpp b/mfbt/decimal/Decimal.cpp |
michael@0 | 2 | --- a/mfbt/decimal/Decimal.cpp |
michael@0 | 3 | +++ b/mfbt/decimal/Decimal.cpp |
michael@0 | 4 | @@ -618,26 +618,26 @@ Decimal::AlignedOperands Decimal::alignO |
michael@0 | 5 | Decimal Decimal::ceiling() const |
michael@0 | 6 | { |
michael@0 | 7 | if (isSpecial()) |
michael@0 | 8 | return *this; |
michael@0 | 9 | |
michael@0 | 10 | if (exponent() >= 0) |
michael@0 | 11 | return *this; |
michael@0 | 12 | |
michael@0 | 13 | - uint64_t result = m_data.coefficient(); |
michael@0 | 14 | - const int numberOfDigits = countDigits(result); |
michael@0 | 15 | + uint64_t coefficient = m_data.coefficient(); |
michael@0 | 16 | + const int numberOfDigits = countDigits(coefficient); |
michael@0 | 17 | const int numberOfDropDigits = -exponent(); |
michael@0 | 18 | if (numberOfDigits < numberOfDropDigits) |
michael@0 | 19 | return isPositive() ? Decimal(1) : zero(Positive); |
michael@0 | 20 | |
michael@0 | 21 | - result = scaleDown(result, numberOfDropDigits - 1); |
michael@0 | 22 | - if (sign() == Positive && result % 10 > 0) |
michael@0 | 23 | - result += 10; |
michael@0 | 24 | - result /= 10; |
michael@0 | 25 | + uint64_t result = scaleDown(coefficient, numberOfDropDigits); |
michael@0 | 26 | + uint64_t droppedDigits = coefficient - scaleUp(result, numberOfDropDigits); |
michael@0 | 27 | + if (droppedDigits && isPositive()) |
michael@0 | 28 | + result += 1; |
michael@0 | 29 | return Decimal(sign(), 0, result); |
michael@0 | 30 | } |
michael@0 | 31 | |
michael@0 | 32 | Decimal Decimal::compareTo(const Decimal& rhs) const |
michael@0 | 33 | { |
michael@0 | 34 | const Decimal result(*this - rhs); |
michael@0 | 35 | switch (result.m_data.formatClass()) { |
michael@0 | 36 | case EncodedData::ClassInfinity: |
michael@0 | 37 | @@ -660,26 +660,27 @@ Decimal Decimal::compareTo(const Decimal |
michael@0 | 38 | Decimal Decimal::floor() const |
michael@0 | 39 | { |
michael@0 | 40 | if (isSpecial()) |
michael@0 | 41 | return *this; |
michael@0 | 42 | |
michael@0 | 43 | if (exponent() >= 0) |
michael@0 | 44 | return *this; |
michael@0 | 45 | |
michael@0 | 46 | - uint64_t result = m_data.coefficient(); |
michael@0 | 47 | - const int numberOfDigits = countDigits(result); |
michael@0 | 48 | + uint64_t coefficient = m_data.coefficient(); |
michael@0 | 49 | + const int numberOfDigits = countDigits(coefficient); |
michael@0 | 50 | const int numberOfDropDigits = -exponent(); |
michael@0 | 51 | if (numberOfDigits < numberOfDropDigits) |
michael@0 | 52 | return isPositive() ? zero(Positive) : Decimal(-1); |
michael@0 | 53 | |
michael@0 | 54 | - result = scaleDown(result, numberOfDropDigits - 1); |
michael@0 | 55 | - if (isNegative() && result % 10 > 0) |
michael@0 | 56 | - result += 10; |
michael@0 | 57 | - result /= 10; |
michael@0 | 58 | + uint64_t result = scaleDown(coefficient, numberOfDropDigits); |
michael@0 | 59 | + uint64_t droppedDigits = coefficient - scaleUp(result, numberOfDropDigits); |
michael@0 | 60 | + if (droppedDigits && isNegative()) { |
michael@0 | 61 | + result += 1; |
michael@0 | 62 | + } |
michael@0 | 63 | return Decimal(sign(), 0, result); |
michael@0 | 64 | } |
michael@0 | 65 | |
michael@0 | 66 | Decimal Decimal::fromDouble(double doubleValue) |
michael@0 | 67 | { |
michael@0 | 68 | if (std::isfinite(doubleValue)) |
michael@0 | 69 | return fromString(String::numberToStringECMAScript(doubleValue)); |
michael@0 | 70 | |
michael@0 | 71 | @@ -915,16 +916,18 @@ Decimal Decimal::round() const |
michael@0 | 72 | return *this; |
michael@0 | 73 | |
michael@0 | 74 | uint64_t result = m_data.coefficient(); |
michael@0 | 75 | const int numberOfDigits = countDigits(result); |
michael@0 | 76 | const int numberOfDropDigits = -exponent(); |
michael@0 | 77 | if (numberOfDigits < numberOfDropDigits) |
michael@0 | 78 | return zero(Positive); |
michael@0 | 79 | |
michael@0 | 80 | + // We're implementing round-half-away-from-zero, so we only need the one |
michael@0 | 81 | + // (the most significant) fractional digit: |
michael@0 | 82 | result = scaleDown(result, numberOfDropDigits - 1); |
michael@0 | 83 | if (result % 10 >= 5) |
michael@0 | 84 | result += 10; |
michael@0 | 85 | result /= 10; |
michael@0 | 86 | return Decimal(sign(), 0, result); |
michael@0 | 87 | } |
michael@0 | 88 | |
michael@0 | 89 | double Decimal::toDouble() const |