From 82d316b419f5ae872250c6732d2ee2df19eca93f Mon Sep 17 00:00:00 2001 From: Gabriel Date: Sat, 24 Dec 2022 21:57:46 +0800 Subject: [PATCH] [bug](decimalv3) Fix wrong decimal scale for arithmetic expr (#15316) --- .../org/apache/doris/analysis/ArithmeticExpr.java | 15 ++++++++++----- .../decimalv3/test_arithmetic_expressions.out | 15 +++++++++++++++ .../decimalv3/test_arithmetic_expressions.groovy | 3 +++ 3 files changed, 28 insertions(+), 5 deletions(-) diff --git a/fe/fe-core/src/main/java/org/apache/doris/analysis/ArithmeticExpr.java b/fe/fe-core/src/main/java/org/apache/doris/analysis/ArithmeticExpr.java index 67b5359348..e5502fe635 100644 --- a/fe/fe-core/src/main/java/org/apache/doris/analysis/ArithmeticExpr.java +++ b/fe/fe-core/src/main/java/org/apache/doris/analysis/ArithmeticExpr.java @@ -533,14 +533,14 @@ public class ArithmeticExpr extends Expr { scale = Math.max(t1Scale, t2Scale); precision = Math.max(widthOfIntPart1, widthOfIntPart2) + scale; } - if (precision < scale) { - type = castBinaryOp(Type.DOUBLE); - break; - } if (precision > ScalarType.MAX_DECIMAL128_PRECISION) { // TODO(gabriel): if precision is bigger than 38? precision = ScalarType.MAX_DECIMAL128_PRECISION; } + if (precision < scale) { + type = castBinaryOp(Type.DOUBLE); + break; + } type = ScalarType.createDecimalV3Type(precision, scale); if (op == Operator.ADD || op == Operator.SUBTRACT) { if (!Type.matchExactType(type, children.get(0).type)) { @@ -550,7 +550,12 @@ public class ArithmeticExpr extends Expr { castChild(type, 1); } } else if (op == Operator.DIVIDE && (t2Scale != 0) && t1.isDecimalV3()) { - castChild(ScalarType.createDecimalV3Type(precision, t1Scale + t2Scale), 0); + int targetScale = t1Scale + t2Scale; + if (precision < targetScale) { + type = castBinaryOp(Type.DOUBLE); + break; + } + castChild(ScalarType.createDecimalV3Type(precision, targetScale), 0); } break; case INT_DIVIDE: diff --git a/regression-test/data/datatype_p0/decimalv3/test_arithmetic_expressions.out b/regression-test/data/datatype_p0/decimalv3/test_arithmetic_expressions.out index a8d9df8d8d..4f68777f2a 100644 --- a/regression-test/data/datatype_p0/decimalv3/test_arithmetic_expressions.out +++ b/regression-test/data/datatype_p0/decimalv3/test_arithmetic_expressions.out @@ -17,3 +17,18 @@ 1.440000000000000000000000000000000000 1.800000000000000000000000000000000000 +-- !select -- +1.7160000000000002 +1.8719999999999999 +2.34 + +-- !select -- +2.9446560000000006 +3.504384 +5.4756 + +-- !select -- +1.7424 +2.0736 +3.2399999999999998 + diff --git a/regression-test/suites/datatype_p0/decimalv3/test_arithmetic_expressions.groovy b/regression-test/suites/datatype_p0/decimalv3/test_arithmetic_expressions.groovy index 44cd313fa0..301d719b15 100644 --- a/regression-test/suites/datatype_p0/decimalv3/test_arithmetic_expressions.groovy +++ b/regression-test/suites/datatype_p0/decimalv3/test_arithmetic_expressions.groovy @@ -45,5 +45,8 @@ suite("test_arithmetic_expressions") { qt_select "select k1 * k2 from ${table1} order by k1" qt_select "select * from (select k1 * k2 from ${table1} union all select k3 from ${table1}) a order by 1" + qt_select "select k1 * k2 * k3 from ${table1} order by k1" + qt_select "select k1 * k2 * k3 * k1 * k2 * k3 from ${table1} order by k1" + qt_select "select k1 * k2 / k3 * k1 * k2 * k3 from ${table1} order by k1" sql "drop table if exists ${table1}" }