liukun4515 commented on a change in pull request #1483:
URL: https://github.com/apache/arrow-datafusion/pull/1483#discussion_r785624489
##########
File path: datafusion/src/physical_plan/expressions/binary.rs
##########
@@ -1907,4 +2226,348 @@ mod tests {
.collect();
assert_eq!(result.as_ref(), &expected);
}
+
+ fn create_decimal_array(
+ array: &[Option<i128>],
+ precision: usize,
+ scale: usize,
+ ) -> Result<DecimalArray> {
+ let mut decimal_builder = DecimalBuilder::new(array.len(), precision,
scale);
+ for value in array {
+ match value {
+ None => {
+ decimal_builder.append_null()?;
+ }
+ Some(v) => {
+ decimal_builder.append_value(*v)?;
+ }
+ }
+ }
+ Ok(decimal_builder.finish())
+ }
+
+ #[test]
+ fn comparison_decimal_op_test() -> Result<()> {
+ let value_i128: i128 = 123;
+ let decimal_array = create_decimal_array(
+ &[
+ Some(value_i128),
+ None,
+ Some(value_i128 - 1),
+ Some(value_i128 + 1),
+ ],
+ 25,
+ 3,
+ )?;
+ // eq: array = i128
+ let result = eq_decimal_scalar(&decimal_array, value_i128)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(true), None, Some(false),
Some(false)]),
+ result
+ );
+ // neq: array != i128
+ let result = neq_decimal_scalar(&decimal_array, value_i128)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(false), None, Some(true),
Some(true)]),
+ result
+ );
+ // lt: array < i128
+ let result = lt_decimal_scalar(&decimal_array, value_i128)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(false), None, Some(true),
Some(false)]),
+ result
+ );
+ // lt_eq: array <= i128
+ let result = lt_eq_decimal_scalar(&decimal_array, value_i128)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(true), None, Some(true),
Some(false)]),
+ result
+ );
+ // gt: array > i128
+ let result = gt_decimal_scalar(&decimal_array, value_i128)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(false), None, Some(false),
Some(true)]),
+ result
+ );
+ // gt_eq: array >= i128
+ let result = gt_eq_decimal_scalar(&decimal_array, value_i128)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(true), None, Some(false),
Some(true)]),
+ result
+ );
+
+ let left_decimal_array = decimal_array;
+ let right_decimal_array = create_decimal_array(
+ &[
+ Some(value_i128 - 1),
+ Some(value_i128),
+ Some(value_i128 + 1),
+ Some(value_i128 + 1),
+ ],
+ 25,
+ 3,
+ )?;
+ // eq: left == right
+ let result = eq_decimal(&left_decimal_array, &right_decimal_array)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(false), None, Some(false),
Some(true)]),
+ result
+ );
+ // neq: left != right
+ let result = neq_decimal(&left_decimal_array, &right_decimal_array)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(true), None, Some(true),
Some(false)]),
+ result
+ );
+ // lt: left < right
+ let result = lt_decimal(&left_decimal_array, &right_decimal_array)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(false), None, Some(true),
Some(false)]),
+ result
+ );
+ // lt_eq: left <= right
+ let result = lt_eq_decimal(&left_decimal_array, &right_decimal_array)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(false), None, Some(true),
Some(true)]),
+ result
+ );
+ // gt: left > right
+ let result = gt_decimal(&left_decimal_array, &right_decimal_array)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(true), None, Some(false),
Some(false)]),
+ result
+ );
+ // gt_eq: left >= right
+ let result = gt_eq_decimal(&left_decimal_array, &right_decimal_array)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(true), None, Some(false),
Some(true)]),
+ result
+ );
+ // is_distinct: left distinct right
+ let result = is_distinct_from_decimal(&left_decimal_array,
&right_decimal_array)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(true), Some(true), Some(true),
Some(false)]),
+ result
+ );
+ // is_distinct: left distinct right
+ let result =
+ is_not_distinct_from_decimal(&left_decimal_array,
&right_decimal_array)?;
+ assert_eq!(
+ BooleanArray::from(vec![Some(false), Some(false), Some(false),
Some(true)]),
+ result
+ );
+ Ok(())
+ }
+
+ #[test]
+ fn comparison_decimal_expr_test() -> Result<()> {
+ let decimal_scalar = ScalarValue::Decimal128(Some(123_456), 10, 3);
+ let schema = Arc::new(Schema::new(vec![Field::new("a",
DataType::Int64, true)]));
+ // scalar == array
+ apply_logic_op_scalar_arr(
+ &schema,
+ &decimal_scalar,
+ &(Arc::new(Int64Array::from(vec![Some(124), None])) as ArrayRef),
+ Operator::Eq,
+ &BooleanArray::from(vec![Some(false), None]),
+ )
+ .unwrap();
+
+ // array != scalar
+ apply_logic_op_arr_scalar(
+ &schema,
+ &(Arc::new(Int64Array::from(vec![Some(123), None, Some(1)])) as
ArrayRef),
+ &decimal_scalar,
+ Operator::NotEq,
+ &BooleanArray::from(vec![Some(true), None, Some(true)]),
+ )
+ .unwrap();
+
+ // array < scalar
+ apply_logic_op_arr_scalar(
+ &schema,
+ &(Arc::new(Int64Array::from(vec![Some(123), None, Some(124)])) as
ArrayRef),
+ &decimal_scalar,
+ Operator::Lt,
+ &BooleanArray::from(vec![Some(true), None, Some(false)]),
+ )
+ .unwrap();
+
+ // array > scalar
+ apply_logic_op_arr_scalar(
+ &schema,
+ &(Arc::new(Int64Array::from(vec![Some(123), None, Some(124)])) as
ArrayRef),
+ &decimal_scalar,
+ Operator::Gt,
+ &BooleanArray::from(vec![Some(false), None, Some(true)]),
+ )
+ .unwrap();
+
+ let schema =
+ Arc::new(Schema::new(vec![Field::new("a", DataType::Float64,
true)]));
+ // array == scalar
+ apply_logic_op_arr_scalar(
+ &schema,
+ &(Arc::new(Float64Array::from(vec![Some(123.456), None,
Some(123.457)]))
+ as ArrayRef),
+ &decimal_scalar,
+ Operator::Eq,
+ &BooleanArray::from(vec![Some(true), None, Some(false)]),
+ )
+ .unwrap();
+
+ // array <= scalar
+ apply_logic_op_arr_scalar(
+ &schema,
+ &(Arc::new(Float64Array::from(vec![
+ Some(123.456),
+ None,
+ Some(123.457),
+ Some(123.45),
+ ])) as ArrayRef),
+ &decimal_scalar,
+ Operator::LtEq,
+ &BooleanArray::from(vec![Some(true), None, Some(false),
Some(true)]),
+ )
+ .unwrap();
+ // array >= scalar
+ apply_logic_op_arr_scalar(
+ &schema,
+ &(Arc::new(Float64Array::from(vec![
+ Some(123.456),
+ None,
+ Some(123.457),
+ Some(123.45),
+ ])) as ArrayRef),
+ &decimal_scalar,
+ Operator::GtEq,
+ &BooleanArray::from(vec![Some(true), None, Some(true),
Some(false)]),
+ )
+ .unwrap();
+
+ // compare decimal array with other array type
+ let schema = Arc::new(Schema::new(vec![
+ Field::new("a", DataType::Int64, true),
+ Field::new("b", DataType::Decimal(10, 0), true),
+ ]));
+
+ let value: i64 = 123;
+
+ let decimal_array = Arc::new(create_decimal_array(
+ &[
+ Some(value as i128),
+ None,
+ Some((value - 1) as i128),
+ Some((value + 1) as i128),
+ ],
+ 10,
+ 0,
+ )?) as ArrayRef;
+
+ let int64_array = Arc::new(Int64Array::from(vec![
+ Some(value),
+ Some(value - 1),
+ Some(value),
+ Some(value + 1),
+ ])) as ArrayRef;
+
+ // eq: int64array == decimal array
+ apply_logic_op(
+ &schema,
+ &int64_array,
+ &decimal_array,
+ Operator::Eq,
+ BooleanArray::from(vec![Some(true), None, Some(false),
Some(true)]),
+ )
+ .unwrap();
+ // neq: int64array != decimal array
+ apply_logic_op(
+ &schema,
+ &int64_array,
+ &decimal_array,
+ Operator::NotEq,
+ BooleanArray::from(vec![Some(false), None, Some(true),
Some(false)]),
+ )
+ .unwrap();
+
+ let schema = Arc::new(Schema::new(vec![
+ Field::new("a", DataType::Float64, true),
+ Field::new("b", DataType::Decimal(10, 2), true),
+ ]));
+
+ let value: i128 = 123;
+ let decimal_array = Arc::new(create_decimal_array(
+ &[
+ Some(value as i128), // 1.23
+ None,
+ Some((value - 1) as i128), // 1.22
+ Some((value + 1) as i128), // 1.24
+ ],
+ 10,
+ 2,
+ )?) as ArrayRef;
+ let float64_array = Arc::new(Float64Array::from(vec![
+ Some(1.23),
+ Some(1.22),
+ Some(1.23),
+ Some(1.24),
+ ])) as ArrayRef;
+ // lt: float64array < decimal array
+ apply_logic_op(
+ &schema,
+ &float64_array,
+ &decimal_array,
+ Operator::Lt,
+ BooleanArray::from(vec![Some(false), None, Some(false),
Some(false)]),
+ )
+ .unwrap();
+ // lt_eq: float64array <= decimal array
+ apply_logic_op(
+ &schema,
+ &float64_array,
+ &decimal_array,
+ Operator::LtEq,
+ BooleanArray::from(vec![Some(true), None, Some(false),
Some(true)]),
+ )
+ .unwrap();
+ // gt: float64array > decimal array
+ apply_logic_op(
+ &schema,
+ &float64_array,
+ &decimal_array,
+ Operator::Gt,
+ BooleanArray::from(vec![Some(false), None, Some(true),
Some(false)]),
+ )
+ .unwrap();
+ apply_logic_op(
+ &schema,
+ &float64_array,
+ &decimal_array,
+ Operator::GtEq,
+ BooleanArray::from(vec![Some(true), None, Some(true), Some(true)]),
+ )
+ .unwrap();
+ // is distinct: float64array is distinct decimal array
+ // TODO: now we do not refactor the `is distinct or is not distinct`
rule of coercion.
Review comment:
https://github.com/apache/arrow-datafusion/issues/1590 tracked.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]