MCPcopy Create free account
hub / github.com/apache/datafusion / invoke_with_args

Method invoke_with_args

datafusion/functions/src/math/round.rs:280–437  ·  view source on GitHub ↗
(&self, args: ScalarFunctionArgs)

Source from the content-addressed store, hash-verified

278 }
279
280 fn invoke_with_args(&self, args: ScalarFunctionArgs) -> Result<ColumnarValue> {
281 if args.arg_fields.iter().any(|a| a.data_type().is_null()) {
282 return ColumnarValue::Scalar(ScalarValue::Null)
283 .cast_to(args.return_type(), None);
284 }
285
286 let default_decimal_places = ColumnarValue::Scalar(ScalarValue::Int32(Some(0)));
287 let decimal_places = if args.args.len() == 2 {
288 &args.args[1]
289 } else {
290 &default_decimal_places
291 };
292
293 if let (ColumnarValue::Scalar(value_scalar), ColumnarValue::Scalar(dp_scalar)) =
294 (&args.args[0], decimal_places)
295 {
296 if value_scalar.is_null() || dp_scalar.is_null() {
297 return ColumnarValue::Scalar(ScalarValue::Null)
298 .cast_to(args.return_type(), None);
299 }
300
301 let dp = if let ScalarValue::Int32(Some(dp)) = dp_scalar {
302 *dp
303 } else {
304 return internal_err!(
305 "Unexpected datatype for decimal_places: {}",
306 dp_scalar.data_type()
307 );
308 };
309
310 match (value_scalar, args.return_type()) {
311 (ScalarValue::Float32(Some(v)), _) => {
312 let rounded = round_float(*v, dp)?;
313 Ok(ColumnarValue::Scalar(ScalarValue::from(rounded)))
314 }
315 (ScalarValue::Float64(Some(v)), _) => {
316 let rounded = round_float(*v, dp)?;
317 Ok(ColumnarValue::Scalar(ScalarValue::from(rounded)))
318 }
319 (
320 ScalarValue::Decimal32(Some(v), in_precision, scale),
321 Decimal32(out_precision, out_scale),
322 ) => {
323 let rounded =
324 round_decimal_or_zero(*v, *in_precision, *scale, *out_scale, dp)?;
325 let rounded = if *out_precision == Decimal32Type::MAX_PRECISION
326 && *scale == 0
327 && dp < 0
328 {
329 // With scale == 0 and negative dp, rounding can carry into an additional
330 // digit (e.g. 99 -> 100). If we're already at max precision we can't widen
331 // the type, so validate and error rather than producing an invalid decimal.
332 validate_decimal_precision::<Decimal32Type>(
333 rounded,
334 *out_precision,
335 *out_scale,
336 )
337 } else {

Callers

nothing calls this directly

Calls 14

round_decimal_or_zeroFunction · 0.85
round_columnarFunction · 0.85
round_floatFunction · 0.70
Decimal32Class · 0.50
Decimal64Class · 0.50
Decimal128Class · 0.50
Decimal256Class · 0.50
anyMethod · 0.45
iterMethod · 0.45
is_nullMethod · 0.45
data_typeMethod · 0.45
cast_toMethod · 0.45

Tested by

no test coverage detected