mirror of
https://github.com/GreptimeTeam/greptimedb.git
synced 2026-09-24 14:15:49 +00:00
* feat(function): add mergeable binary average states Signed-off-by: discord9 <discord9@163.com> * feat(function): expose avg_calc as an OSS scalar Signed-off-by: discord9 <discord9@163.com> * fix(function): borrow invalid AVG scalar argument type Signed-off-by: discord9 <discord9@163.com> * test(function): verify public AVG state SQL finalization Signed-off-by: discord9 <discord9@163.com> * fix(function): return canonical AVG1 state for empty window frames DataFusion's plain-aggregate window executor bypasses the accumulator and calls default_value() directly when a window frame contains no rows. create_udaf's SimpleAggregateUDF derives default_value from the return type, which yields SQL NULL for Binary output instead of the canonical AVG1 empty state, so empty frames and frames over only NULL inputs became observable differently (IS NULL, direct state saves, state comparisons). Register avg_state/avg_merge through a small AggregateUDFImpl (AvgUdaf) that keeps the existing accumulator and declares the canonical AVG1 empty state as default_value, restoring the documented contract. Add a unit test asserting default_value equals the empty accumulator's evaluate() and an sqlness case covering the empty-frame window. Signed-off-by: discord9 <discord9@outlook.com> --------- Signed-off-by: discord9 <discord9@163.com> Signed-off-by: discord9 <discord9@outlook.com> Co-authored-by: discord9 <discord9@outlook.com>
19 lines
785 B
SQL
19 lines
785 B
SQL
-- The persisted states have counts 2 and 1 and sums 3.0 and 6.0.
|
|
-- Null and canonical empty states do not change the merged AVG1 state.
|
|
SELECT avg_merge(state) = X'4156473103000000000000000000000000002240' AS merged_state_matches
|
|
FROM avg1_states;
|
|
|
|
-- A new state over the equivalent Float64 values has the exact same AVG1 bytes.
|
|
WITH generated_values AS (
|
|
SELECT CAST(1.0 AS DOUBLE) AS value
|
|
UNION ALL SELECT CAST(2.0 AS DOUBLE)
|
|
UNION ALL SELECT CAST(6.0 AS DOUBLE)
|
|
)
|
|
SELECT avg_state(value) = X'4156473103000000000000000000000000002240' AS generated_state_matches
|
|
FROM generated_values;
|
|
|
|
-- A null-only merge is the canonical empty AVG1 state.
|
|
SELECT avg_merge(state) = X'4156473100000000000000000000000000000000' AS null_state_is_empty
|
|
FROM avg1_states
|
|
WHERE state IS NULL;
|