Skip to content

Conversation

@kumarUjjawal
Copy link
Contributor

Which issue does this PR close?

Rationale for this change

The round function currently converts scalar inputs to arrays before processing, even when both value and decimal_places are scalar values. This adds unnecessary overhead for constant folding scenarios like

What changes are included in this PR?

  • Add scalar fast path in RoundFunc::invoke_with_args for Float64 and Float32 inputs
  • Directly compute the result when both inputs are scalars, avoiding array conversion overhead
  • Add benchmark

Are these changes tested?

Yes

Type Before After Speedup
round_f64_scalar 570 ns 195 ns 2.9x
round_f32_scalar 564 ns 192 ns 2.9x

Are there any user-facing changes?

No

@github-actions github-actions bot added the functions Changes to functions implementation label Jan 15, 2026
return Ok(ColumnarValue::Scalar(ScalarValue::Float64(None)));
}
_ => {
// Fall through to array path for non-Int32 decimal places
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this arm possible in normal execution?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, it's unreachable because decimal_places is coerced to Int32 by the signature.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If it is unreachable in normal execution then it should return an internal error to indicate so

ScalarValue::Float32(None) => {
return Ok(ColumnarValue::Scalar(ScalarValue::Float32(None)));
}
// For decimals and other types: fall through to array path
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there anything stopping us from supporting decimals as well?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The round_decimal function requires the scale parameter from the decimal type (e.g., Decimal128(precision, scale)), which makes extracting and processing scalars more involved than for floats.

For float scalars, we just call round_float(*v, dp) directly. For decimals, we'd need to:

  • Extract the native value from ScalarValue::Decimal128 (or other decimal variants)
  • Get the scale from the type
  • Call round_decimal(value, scale, dp)
  • Reconstruct the ScalarValue with precision/scale

If you're comfortable with these changes in this PR for the decimal then I can introduce these as well. What do you think?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should do it in this PR

let dp = match dp_scalar {
ScalarValue::Int32(Some(dp)) => *dp,
ScalarValue::Int32(None) => {
// Return type depends on input type, but for null dp we return null
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This fails to take into account decimals

ScalarValue::Float32(None) => {
return Ok(ColumnarValue::Scalar(ScalarValue::Float32(None)));
}
// For decimals and other types: fall through to array path
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should do it in this PR

return Ok(ColumnarValue::Scalar(ScalarValue::Float64(None)));
}
_ => {
// Fall through to array path for non-Int32 decimal places
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If it is unreachable in normal execution then it should return an internal error to indicate so

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

functions Changes to functions implementation

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants