Skip to content

Commit

Permalink
minor fix
Browse files Browse the repository at this point in the history
  • Loading branch information
rui-mo committed Feb 23, 2024
1 parent aa18b28 commit 74d0c45
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 22 deletions.
17 changes: 7 additions & 10 deletions velox/expression/tests/CastExprTest.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2086,12 +2086,12 @@ TEST_F(CastExprTest, doubleToDecimal) {
DOUBLE(),
DECIMAL(38, 2),
{std::numeric_limits<double>::max()},
"Cannot cast DOUBLE '1.7976931348623157E308' to DECIMAL(38, 2). Result overflows.");
"Result overflows.");
testThrow<double>(
DOUBLE(),
DECIMAL(38, 2),
{std::numeric_limits<double>::lowest()},
"Cannot cast DOUBLE '-1.7976931348623157E308' to DECIMAL(38, 2). Result overflows.");
"Result overflows.");
testCast(
makeConstant<double>(std::numeric_limits<double>::min(), 1),
makeConstant<int128_t>(0, 1, DECIMAL(38, 2)));
Expand Down Expand Up @@ -2169,10 +2169,7 @@ TEST_F(CastExprTest, realToDecimal) {
DECIMAL(38, 18)));

testThrow<float>(
REAL(),
DECIMAL(10, 2),
{9999999999999999999999.99},
"Cannot cast REAL '9.999999778196308E21' to DECIMAL(10, 2). Result overflows.");
REAL(), DECIMAL(10, 2), {9999999999999999999999.99}, "Result overflows.");
testThrow<float>(
REAL(),
DECIMAL(10, 2),
Expand All @@ -2189,22 +2186,22 @@ TEST_F(CastExprTest, realToDecimal) {
REAL(),
DECIMAL(20, 2),
{static_cast<float>(DecimalUtil::kLongDecimalMax)},
"Cannot cast REAL '9.999999680285692E37' to DECIMAL(20, 2). Result overflows.");
"Result overflows.");
testThrow<float>(
REAL(),
DECIMAL(20, 2),
{static_cast<float>(DecimalUtil::kLongDecimalMin)},
"Cannot cast REAL '-9.999999680285692E37' to DECIMAL(20, 2). Result overflows.");
"Result overflows.");
testThrow<float>(
REAL(),
DECIMAL(38, 2),
{std::numeric_limits<float>::max()},
"Cannot cast REAL '3.4028234663852886E38' to DECIMAL(38, 2). Result overflows.");
"Result overflows.");
testThrow<float>(
REAL(),
DECIMAL(38, 2),
{std::numeric_limits<float>::lowest()},
"Cannot cast REAL '-3.4028234663852886E38' to DECIMAL(38, 2). Result overflows.");
"Result overflows.");
testCast(
makeConstant<float>(std::numeric_limits<float>::min(), 1),
makeConstant<int128_t>(0, 1, DECIMAL(38, 2)));
Expand Down
27 changes: 15 additions & 12 deletions velox/type/DecimalUtil.h
Original file line number Diff line number Diff line change
Expand Up @@ -233,26 +233,29 @@ class DecimalUtil {
}

// Calculate the precise fractional digits.
const auto integralValue =
static_cast<uint128_t>(value > 0 ? value : -value);
const auto integralDigits =
integralValue == 0 ? 0 : countDigits(integralValue);
const auto fractionDigits = digits - integralDigits;
// const auto integralValue =
// static_cast<uint128_t>(value > 0 ? value : -value);
// const auto integralDigits =
// integralValue == 0 ? 0 : countDigits(integralValue);

// const auto fractionDigits = std::max(digits - integralDigits, 0);

/// Scales up the input value to keep all the precise fractional digits
/// before rounding. Convert value to long double type, as double * int128_t
/// returns int128_t and fractional digits are lost. No need to consider
/// 'toValue' becoming infinite as DOUBLE_MAX * 10^38 < LONG_DOUBLE_MAX.
const auto scaledValue =
(long double)value * DecimalUtil::kPowersOfTen[fractionDigits];
// const auto scaledValue =
// (long double)value * DecimalUtil::kPowersOfTen[digits];

long double rounded;
if (scale > fractionDigits) {
rounded = std::round(scaledValue) *
DecimalUtil::kPowersOfTen[scale - fractionDigits];
if (scale < digits) {
rounded = std::round(
std::round((long double)value * DecimalUtil::kPowersOfTen[digits]) /
DecimalUtil::kPowersOfTen[digits - scale]);
} else {
rounded = std::round(
std::round(scaledValue) /
DecimalUtil::kPowersOfTen[fractionDigits - scale]);
std::round((long double)value * DecimalUtil::kPowersOfTen[digits]) *
DecimalUtil::kPowersOfTen[scale - digits]);
}

const auto result = folly::tryTo<TOutput>(rounded);
Expand Down

0 comments on commit 74d0c45

Please sign in to comment.