Skip to content

perf(arrow): build repeated constant string/binary columns without per-row clones - #3080

Open
anoopj wants to merge 1 commit into
apache:mainfrom
anoopj:perf-repeated-array-alloc
Open

perf(arrow): build repeated constant string/binary columns without per-row clones#3080
anoopj wants to merge 1 commit into
apache:mainfrom
anoopj:perf-repeated-array-alloc

Conversation

@anoopj

@anoopj anoopj commented Aug 26, 2026

Copy link
Copy Markdown
Member

Which issue does this PR close?

Fixes #3079

What changes are included in this PR?

create_primitive_array_repeated built a throwaway vec![value.clone(); num_rows] for the Utf8/Binary/LargeBinary/FixedSizeBinary arms before handing it to the array constructor. For strings that clones the value into num_rows separate heap allocations per batch; the binary arms allocate a throwaway intermediate Vec.

Stream the single value straight into the Arrow buffer via from_iter_values with std::iter::repeat_n instead.

Benchmarks (release, throwaway harness, old vs new toggled on this file only):

  • leaf create_primitive_array_repeated (Utf8, 8192-row batch): 23.0 -> 4.1 ns/row (5.6x)
  • full scan select(x, _partition) over a real manifest + 262k-row parquet file, string-partitioned: 20.9 -> 5.7 ns/row (3.7x)

Note that the gain is allocation-counts and scales with how much of the projection is the string partition column.

Are these changes tested?

New + old tests

…r-row clones

create_primitive_array_repeated built a throwaway `vec![value.clone(); num_rows]`
for the Utf8/Binary/LargeBinary/FixedSizeBinary arms before handing it to the array
constructor. For strings that clones the value into num_rows separate heap
allocations per batch; the binary arms allocate a throwaway intermediate Vec.

Stream the single value straight into the Arrow buffer via `from_iter_values` with
`std::iter::repeat_n` instead.

Benchmarks (release, throwaway harness, old vs new toggled on this file only):
- leaf create_primitive_array_repeated (Utf8, 8192-row batch): 23.0 -> 4.1 ns/row (5.6x)
- full scan select(x, _partition) over a real manifest + 262k-row parquet file,
  string-partitioned: 20.9 -> 5.7 ns/row (3.7x)

Note that the gain is allocation-counts and scales with how much of the
projection is the string partition column.

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Repeated constant string/binary columns clone the value per row

1 participant