Skip to content

Conversation

@jhorstmann
Copy link
Contributor

Which issue does this PR close?

Rationale for this change

Profiling showed this loop to be a clear performance hotspot and thanks to the new BooleanBufferBuilder::extend_trusted_len method introduced in #9137 there is a very simple improvement.

Benchmark results for optional structs after the fix:

arrow_array_reader/struct/Int32Array/plain encoded, optional struct, optional data, no NULLs
                        time:   [69.873 µs 69.917 µs 69.970 µs]
                        change: [−60.075% −60.046% −60.018%] (p = 0.00 < 0.05)
                        Performance has improved.
arrow_array_reader/struct/Int32Array/plain encoded, optional struct, optional data, half NULLs
                        time:   [136.62 µs 136.66 µs 136.72 µs]
                        change: [−67.663% −67.536% −67.416%] (p = 0.00 < 0.05)
                        Performance has improved.

This is a big improvement, but still significantly slower than reading non-nested data. The main hotspot still is the extend_trusted_len and manual simd code for comparing chunks and appending 64-bits at a time could potentially speed it up even more. But that would require either architecture specific intrinsics or unstable features.

What changes are included in this PR?

Are these changes tested?

Tested by existing tests.

Are there any user-facing changes?

no

@github-actions github-actions bot added the parquet Changes to the parquet crate label Jan 18, 2026
None => {
for def_level in def_levels {
bitmap_builder.append(*def_level >= self.struct_def_level)
// Safety: slice iterator has a trusted length
Copy link
Contributor Author

Choose a reason for hiding this comment

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

My benchmark did not actually cover this code, since it reads the leaf column as a primitive array. That would mean the performance might be even worse than measured, but also the improvement would be a bit bigger.

@Dandandan
Copy link
Contributor

run benchmark arrow_reader arrow_reader_row_filter arrow_reader_clickbench

@jhorstmann jhorstmann force-pushed the optimize-struct-reading branch from 7adb6ed to f447bac Compare January 18, 2026 20:02
@alamb-ghbot
Copy link

🤖 ./gh_compare_arrow.sh gh_compare_arrow.sh Running
Linux aal-dev 6.14.0-1018-gcp #19~24.04.1-Ubuntu SMP Wed Sep 24 23:23:09 UTC 2025 x86_64 x86_64 x86_64 GNU/Linux
Comparing optimize-struct-reading (f447bac) to 9c6065c diff
BENCH_NAME=arrow_reader
BENCH_COMMAND=cargo bench --features=arrow,async,test_common,experimental --bench arrow_reader
BENCH_FILTER=
BENCH_BRANCH_NAME=optimize-struct-reading
Results will be posted here when complete

@alamb-ghbot
Copy link

🤖: Benchmark completed

Details

group                                                                                                      main                                   optimize-struct-reading
-----                                                                                                      ----                                   -----------------------
arrow_array_reader/BYTE_ARRAY/Decimal128Array/plain encoded, mandatory, no NULLs                           1.05   1251.1±6.20µs        ? ?/sec    1.00  1186.9±23.48µs        ? ?/sec
arrow_array_reader/BYTE_ARRAY/Decimal128Array/plain encoded, optional, half NULLs                          1.03  1285.9±19.73µs        ? ?/sec    1.00   1245.9±9.90µs        ? ?/sec
arrow_array_reader/BYTE_ARRAY/Decimal128Array/plain encoded, optional, no NULLs                            1.06  1261.1±16.45µs        ? ?/sec    1.00  1190.8±15.22µs        ? ?/sec
arrow_array_reader/BinaryArray/dictionary encoded, mandatory, no NULLs                                     1.02    482.7±5.65µs        ? ?/sec    1.00   474.6±12.99µs        ? ?/sec
arrow_array_reader/BinaryArray/dictionary encoded, optional, half NULLs                                    1.01    658.8±4.88µs        ? ?/sec    1.00    650.2±2.29µs        ? ?/sec
arrow_array_reader/BinaryArray/dictionary encoded, optional, no NULLs                                      1.02    490.8±6.33µs        ? ?/sec    1.00    482.0±7.66µs        ? ?/sec
arrow_array_reader/BinaryArray/plain encoded, mandatory, no NULLs                                          1.04   569.8±13.20µs        ? ?/sec    1.00    550.4±4.81µs        ? ?/sec
arrow_array_reader/BinaryArray/plain encoded, optional, half NULLs                                         1.01    734.8±4.38µs        ? ?/sec    1.00    727.2±6.25µs        ? ?/sec
arrow_array_reader/BinaryArray/plain encoded, optional, no NULLs                                           1.03   575.2±11.09µs        ? ?/sec    1.00   559.0±10.35µs        ? ?/sec
arrow_array_reader/BinaryViewArray/dictionary encoded, mandatory, no NULLs                                 1.01    239.6±4.57µs        ? ?/sec    1.00    236.2±4.78µs        ? ?/sec
arrow_array_reader/BinaryViewArray/dictionary encoded, optional, half NULLs                                1.18    247.0±2.52µs        ? ?/sec    1.00    210.0±2.71µs        ? ?/sec
arrow_array_reader/BinaryViewArray/dictionary encoded, optional, no NULLs                                  1.04    246.2±3.54µs        ? ?/sec    1.00    237.6±3.98µs        ? ?/sec
arrow_array_reader/BinaryViewArray/plain encoded, mandatory, no NULLs                                      1.00    290.6±4.19µs        ? ?/sec    1.21    351.4±4.09µs        ? ?/sec
arrow_array_reader/BinaryViewArray/plain encoded, mandatory, no NULLs, short string                        1.00    304.4±1.50µs        ? ?/sec    1.07    326.5±3.07µs        ? ?/sec
arrow_array_reader/BinaryViewArray/plain encoded, optional, half NULLs                                     1.00    281.8±5.54µs        ? ?/sec    1.02    286.9±3.45µs        ? ?/sec
arrow_array_reader/BinaryViewArray/plain encoded, optional, no NULLs                                       1.00    300.4±5.40µs        ? ?/sec    1.20    360.7±3.95µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Decimal128Array/byte_stream_split encoded, mandatory, no NULLs     1.05  1134.7±67.03µs        ? ?/sec    1.00   1077.4±6.72µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Decimal128Array/byte_stream_split encoded, optional, half NULLs    1.05   986.2±25.70µs        ? ?/sec    1.00    936.2±8.47µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Decimal128Array/byte_stream_split encoded, optional, no NULLs      1.06  1143.9±46.61µs        ? ?/sec    1.00   1082.2±6.74µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Decimal128Array/plain encoded, mandatory, no NULLs                 1.11   454.5±12.22µs        ? ?/sec    1.00    410.8±7.06µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Decimal128Array/plain encoded, optional, half NULLs                1.07   640.0±13.93µs        ? ?/sec    1.00    598.2±6.02µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Decimal128Array/plain encoded, optional, no NULLs                  1.12    461.2±6.67µs        ? ?/sec    1.00    411.6±7.03µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Float16Array/byte_stream_split encoded, mandatory, no NULLs        1.26    202.8±1.95µs        ? ?/sec    1.00    160.6±0.74µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Float16Array/byte_stream_split encoded, optional, half NULLs       1.16   320.1±12.59µs        ? ?/sec    1.00   276.6±19.37µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Float16Array/byte_stream_split encoded, optional, no NULLs         1.25    207.5±2.73µs        ? ?/sec    1.00    166.3±1.15µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Float16Array/plain encoded, mandatory, no NULLs                    1.54    118.4±0.49µs        ? ?/sec    1.00     76.8±0.61µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Float16Array/plain encoded, optional, half NULLs                   1.19   276.3±13.46µs        ? ?/sec    1.00    231.9±1.01µs        ? ?/sec
arrow_array_reader/FIXED_LEN_BYTE_ARRAY/Float16Array/plain encoded, optional, no NULLs                     1.52    124.7±1.81µs        ? ?/sec    1.00     82.2±1.29µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(16)/byte_stream_split encoded, mandatory, no NULLs                    1.00    737.8±8.38µs        ? ?/sec    1.00    739.8±4.54µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(16)/byte_stream_split encoded, optional, half NULLs                   1.01    597.2±5.73µs        ? ?/sec    1.00   589.0±17.92µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(16)/byte_stream_split encoded, optional, no NULLs                     1.00    743.5±4.23µs        ? ?/sec    1.01   748.2±16.66µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(16)/plain encoded, mandatory, no NULLs                                1.04     71.1±5.53µs        ? ?/sec    1.00     68.6±4.84µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(16)/plain encoded, optional, half NULLs                               1.02    254.1±2.99µs        ? ?/sec    1.00    249.9±4.83µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(16)/plain encoded, optional, no NULLs                                 1.04     80.2±6.41µs        ? ?/sec    1.00     77.1±4.48µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(2)/byte_stream_split encoded, mandatory, no NULLs                     1.00     94.6±3.85µs        ? ?/sec    1.00     94.2±0.64µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(2)/byte_stream_split encoded, optional, half NULLs                    1.00    207.3±2.50µs        ? ?/sec    1.01    208.4±1.86µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(2)/byte_stream_split encoded, optional, no NULLs                      1.00     99.0±0.44µs        ? ?/sec    1.01    100.4±4.83µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(2)/plain encoded, mandatory, no NULLs                                 1.00      9.1±0.16µs        ? ?/sec    1.03      9.3±0.26µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(2)/plain encoded, optional, half NULLs                                1.00    165.5±2.73µs        ? ?/sec    1.00    164.7±2.08µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(2)/plain encoded, optional, no NULLs                                  1.00     14.1±0.21µs        ? ?/sec    1.01     14.2±0.23µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(4)/byte_stream_split encoded, mandatory, no NULLs                     1.00    184.1±3.24µs        ? ?/sec    1.00    184.4±1.10µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(4)/byte_stream_split encoded, optional, half NULLs                    1.00    333.2±5.02µs        ? ?/sec    1.00   332.6±17.05µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(4)/byte_stream_split encoded, optional, no NULLs                      1.00    188.9±1.34µs        ? ?/sec    1.01    191.1±5.05µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(4)/plain encoded, mandatory, no NULLs                                 1.00     14.4±0.49µs        ? ?/sec    1.03     14.9±0.71µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(4)/plain encoded, optional, half NULLs                                1.01    247.5±4.97µs        ? ?/sec    1.00    244.5±3.29µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(4)/plain encoded, optional, no NULLs                                  1.00     20.5±0.75µs        ? ?/sec    1.00     20.4±0.64µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(8)/byte_stream_split encoded, mandatory, no NULLs                     1.00    366.8±3.61µs        ? ?/sec    1.00    367.2±3.20µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(8)/byte_stream_split encoded, optional, half NULLs                    1.01    392.3±6.01µs        ? ?/sec    1.00    389.0±2.47µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(8)/byte_stream_split encoded, optional, no NULLs                      1.00    372.7±1.52µs        ? ?/sec    1.01    375.6±3.44µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(8)/plain encoded, mandatory, no NULLs                                 1.00     27.9±0.71µs        ? ?/sec    1.01     28.0±0.52µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(8)/plain encoded, optional, half NULLs                                1.00    222.1±2.03µs        ? ?/sec    1.00    221.5±5.78µs        ? ?/sec
arrow_array_reader/FixedLenByteArray(8)/plain encoded, optional, no NULLs                                  1.00     34.6±0.44µs        ? ?/sec    1.03     35.7±0.79µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/binary packed skip, mandatory, no NULLs                           1.00    110.6±1.61µs        ? ?/sec    1.01    112.1±3.05µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/binary packed skip, optional, half NULLs                          1.01    130.6±2.14µs        ? ?/sec    1.00    129.5±1.60µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/binary packed skip, optional, no NULLs                            1.00    113.5±0.72µs        ? ?/sec    1.01    114.8±1.51µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/binary packed, mandatory, no NULLs                                1.02    163.1±2.11µs        ? ?/sec    1.00    160.4±0.85µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/binary packed, optional, half NULLs                               1.00    223.4±1.02µs        ? ?/sec    1.00    222.7±1.22µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/binary packed, optional, no NULLs                                 1.01    168.4±1.25µs        ? ?/sec    1.00    167.3±1.09µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/byte_stream_split encoded, mandatory, no NULLs                    1.00     74.0±0.28µs        ? ?/sec    1.02     75.2±0.80µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/byte_stream_split encoded, optional, half NULLs                   1.01    178.4±2.52µs        ? ?/sec    1.00    176.9±0.85µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/byte_stream_split encoded, optional, no NULLs                     1.01     80.6±0.33µs        ? ?/sec    1.00     79.6±1.12µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/dictionary encoded, mandatory, no NULLs                           1.00   143.5±13.79µs        ? ?/sec    1.01    144.5±3.11µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/dictionary encoded, optional, half NULLs                          1.00    213.8±4.52µs        ? ?/sec    1.00    213.6±1.36µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/dictionary encoded, optional, no NULLs                            1.00    147.9±2.76µs        ? ?/sec    1.01    149.2±2.79µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/plain encoded, mandatory, no NULLs                                1.00     72.6±0.29µs        ? ?/sec    1.00     72.7±0.42µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/plain encoded, optional, half NULLs                               1.02    178.5±1.35µs        ? ?/sec    1.00    175.5±2.01µs        ? ?/sec
arrow_array_reader/INT32/Decimal128Array/plain encoded, optional, no NULLs                                 1.01     79.7±0.94µs        ? ?/sec    1.00     78.6±1.02µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/binary packed skip, mandatory, no NULLs                           1.01    107.6±0.58µs        ? ?/sec    1.00    106.9±1.03µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/binary packed skip, optional, half NULLs                          1.00    134.1±1.62µs        ? ?/sec    1.01    135.1±1.37µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/binary packed skip, optional, no NULLs                            1.00    111.9±2.68µs        ? ?/sec    1.00    111.5±0.48µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/binary packed, mandatory, no NULLs                                1.02    162.7±2.46µs        ? ?/sec    1.00    160.0±0.65µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/binary packed, optional, half NULLs                               1.01    233.6±4.12µs        ? ?/sec    1.00    232.2±0.95µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/binary packed, optional, no NULLs                                 1.01    167.3±0.71µs        ? ?/sec    1.00    166.0±0.54µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/byte_stream_split encoded, mandatory, no NULLs                    1.00    199.6±2.19µs        ? ?/sec    1.02    202.8±1.88µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/byte_stream_split encoded, optional, half NULLs                   1.00    247.7±1.78µs        ? ?/sec    1.02   253.0±19.00µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/byte_stream_split encoded, optional, no NULLs                     1.00    205.7±1.47µs        ? ?/sec    1.01    208.7±1.09µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/dictionary encoded, mandatory, no NULLs                           1.01    143.0±0.55µs        ? ?/sec    1.00    141.2±3.26µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/dictionary encoded, optional, half NULLs                          1.00    216.0±1.84µs        ? ?/sec    1.00    216.1±1.54µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/dictionary encoded, optional, no NULLs                            1.00    146.6±3.95µs        ? ?/sec    1.00    146.4±0.56µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/plain encoded, mandatory, no NULLs                                1.00    100.9±1.24µs        ? ?/sec    1.09    109.7±1.73µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/plain encoded, optional, half NULLs                               1.01    198.8±2.87µs        ? ?/sec    1.00    197.1±1.55µs        ? ?/sec
arrow_array_reader/INT64/Decimal128Array/plain encoded, optional, no NULLs                                 1.00    110.3±1.42µs        ? ?/sec    1.06    117.4±1.81µs        ? ?/sec
arrow_array_reader/Int16Array/binary packed skip, mandatory, no NULLs                                      1.00     79.6±1.31µs        ? ?/sec    1.00     79.3±1.75µs        ? ?/sec
arrow_array_reader/Int16Array/binary packed skip, optional, half NULLs                                     1.01    104.0±1.80µs        ? ?/sec    1.00    102.8±0.92µs        ? ?/sec
arrow_array_reader/Int16Array/binary packed skip, optional, no NULLs                                       1.01     82.4±1.86µs        ? ?/sec    1.00     81.3±0.95µs        ? ?/sec
arrow_array_reader/Int16Array/binary packed, mandatory, no NULLs                                           1.01    110.4±2.12µs        ? ?/sec    1.00    109.1±1.96µs        ? ?/sec
arrow_array_reader/Int16Array/binary packed, optional, half NULLs                                          1.01    175.8±1.87µs        ? ?/sec    1.00    174.0±3.14µs        ? ?/sec
arrow_array_reader/Int16Array/binary packed, optional, no NULLs                                            1.01    115.1±2.28µs        ? ?/sec    1.00    113.6±1.36µs        ? ?/sec
arrow_array_reader/Int16Array/byte_stream_split encoded, mandatory, no NULLs                               1.00     40.7±0.13µs        ? ?/sec    1.04     42.3±0.28µs        ? ?/sec
arrow_array_reader/Int16Array/byte_stream_split encoded, optional, half NULLs                              1.01    140.8±3.35µs        ? ?/sec    1.00    139.0±0.97µs        ? ?/sec
arrow_array_reader/Int16Array/byte_stream_split encoded, optional, no NULLs                                1.00     45.3±0.22µs        ? ?/sec    1.04     46.9±0.48µs        ? ?/sec
arrow_array_reader/Int16Array/dictionary encoded, mandatory, no NULLs                                      1.00    109.6±2.24µs        ? ?/sec    1.01    110.4±2.31µs        ? ?/sec
arrow_array_reader/Int16Array/dictionary encoded, optional, half NULLs                                     1.01    177.3±0.94µs        ? ?/sec    1.00    176.0±0.66µs        ? ?/sec
arrow_array_reader/Int16Array/dictionary encoded, optional, no NULLs                                       1.00    113.8±0.67µs        ? ?/sec    1.01    114.5±0.62µs        ? ?/sec
arrow_array_reader/Int16Array/plain encoded, mandatory, no NULLs                                           1.00     36.7±0.36µs        ? ?/sec    1.00     36.7±0.20µs        ? ?/sec
arrow_array_reader/Int16Array/plain encoded, optional, half NULLs                                          1.02    138.5±1.44µs        ? ?/sec    1.00    136.3±2.40µs        ? ?/sec
arrow_array_reader/Int16Array/plain encoded, optional, no NULLs                                            1.00     41.4±0.12µs        ? ?/sec    1.01     41.8±0.45µs        ? ?/sec
arrow_array_reader/Int32Array/binary packed skip, mandatory, no NULLs                                      1.00     84.0±0.84µs        ? ?/sec    1.00     84.1±2.29µs        ? ?/sec
arrow_array_reader/Int32Array/binary packed skip, optional, half NULLs                                     1.01    102.1±1.55µs        ? ?/sec    1.00    101.2±1.08µs        ? ?/sec
arrow_array_reader/Int32Array/binary packed skip, optional, no NULLs                                       1.00     86.6±1.33µs        ? ?/sec    1.00     86.6±2.06µs        ? ?/sec
arrow_array_reader/Int32Array/binary packed, mandatory, no NULLs                                           1.00    108.3±0.62µs        ? ?/sec    1.00    108.1±1.32µs        ? ?/sec
arrow_array_reader/Int32Array/binary packed, optional, half NULLs                                          1.01    166.2±2.40µs        ? ?/sec    1.00    164.4±1.44µs        ? ?/sec
arrow_array_reader/Int32Array/binary packed, optional, no NULLs                                            1.00    113.1±2.04µs        ? ?/sec    1.00    112.6±0.63µs        ? ?/sec
arrow_array_reader/Int32Array/byte_stream_split encoded, mandatory, no NULLs                               1.00     23.3±0.37µs        ? ?/sec    1.01     23.5±0.40µs        ? ?/sec
arrow_array_reader/Int32Array/byte_stream_split encoded, optional, half NULLs                              1.02    121.1±0.93µs        ? ?/sec    1.00    119.0±1.00µs        ? ?/sec
arrow_array_reader/Int32Array/byte_stream_split encoded, optional, no NULLs                                1.00     27.9±0.30µs        ? ?/sec    1.00     27.8±0.44µs        ? ?/sec
arrow_array_reader/Int32Array/dictionary encoded, mandatory, no NULLs                                      1.00     90.8±1.78µs        ? ?/sec    1.01     91.8±1.51µs        ? ?/sec
arrow_array_reader/Int32Array/dictionary encoded, optional, half NULLs                                     1.00    157.9±0.87µs        ? ?/sec    1.00    157.6±1.15µs        ? ?/sec
arrow_array_reader/Int32Array/dictionary encoded, optional, no NULLs                                       1.00     94.1±0.49µs        ? ?/sec    1.02     96.3±1.08µs        ? ?/sec
arrow_array_reader/Int32Array/plain encoded, mandatory, no NULLs                                           1.00     15.4±0.79µs        ? ?/sec    1.01     15.6±0.84µs        ? ?/sec
arrow_array_reader/Int32Array/plain encoded, optional, half NULLs                                          1.01    119.1±3.45µs        ? ?/sec    1.00    117.5±3.16µs        ? ?/sec
arrow_array_reader/Int32Array/plain encoded, optional, no NULLs                                            1.00     21.3±0.61µs        ? ?/sec    1.01     21.5±0.51µs        ? ?/sec
arrow_array_reader/Int64Array/binary packed skip, mandatory, no NULLs                                      1.00     79.8±0.89µs        ? ?/sec    1.00     79.8±0.67µs        ? ?/sec
arrow_array_reader/Int64Array/binary packed skip, optional, half NULLs                                     1.00    101.2±1.43µs        ? ?/sec    1.01    102.5±1.07µs        ? ?/sec
arrow_array_reader/Int64Array/binary packed skip, optional, no NULLs                                       1.00     82.4±0.36µs        ? ?/sec    1.00     82.5±0.60µs        ? ?/sec
arrow_array_reader/Int64Array/binary packed, mandatory, no NULLs                                           1.01    107.4±1.16µs        ? ?/sec    1.00    106.3±0.70µs        ? ?/sec
arrow_array_reader/Int64Array/binary packed, optional, half NULLs                                          1.00    165.2±2.61µs        ? ?/sec    1.02    169.2±1.03µs        ? ?/sec
arrow_array_reader/Int64Array/binary packed, optional, no NULLs                                            1.00    109.7±0.48µs        ? ?/sec    1.01    111.2±1.65µs        ? ?/sec
arrow_array_reader/Int64Array/byte_stream_split encoded, mandatory, no NULLs                               1.00    146.3±1.04µs        ? ?/sec    1.00    146.6±1.02µs        ? ?/sec
arrow_array_reader/Int64Array/byte_stream_split encoded, optional, half NULLs                              1.00    190.6±4.71µs        ? ?/sec    1.00    191.3±5.15µs        ? ?/sec
arrow_array_reader/Int64Array/byte_stream_split encoded, optional, no NULLs                                1.00    151.5±0.74µs        ? ?/sec    1.00    151.6±0.78µs        ? ?/sec
arrow_array_reader/Int64Array/dictionary encoded, mandatory, no NULLs                                      1.00     87.8±1.05µs        ? ?/sec    1.01     89.0±1.36µs        ? ?/sec
arrow_array_reader/Int64Array/dictionary encoded, optional, half NULLs                                     1.00    158.3±5.12µs        ? ?/sec    1.00    157.9±0.80µs        ? ?/sec
arrow_array_reader/Int64Array/dictionary encoded, optional, no NULLs                                       1.00     92.7±1.65µs        ? ?/sec    1.01     93.8±2.30µs        ? ?/sec
arrow_array_reader/Int64Array/plain encoded, mandatory, no NULLs                                           1.00     38.4±0.99µs        ? ?/sec    1.11     42.7±2.98µs        ? ?/sec
arrow_array_reader/Int64Array/plain encoded, optional, half NULLs                                          1.01    134.6±1.68µs        ? ?/sec    1.00    133.8±1.32µs        ? ?/sec
arrow_array_reader/Int64Array/plain encoded, optional, no NULLs                                            1.00     43.8±0.98µs        ? ?/sec    1.11     48.8±3.20µs        ? ?/sec
arrow_array_reader/Int8Array/binary packed skip, mandatory, no NULLs                                       1.01     83.7±1.81µs        ? ?/sec    1.00     82.9±1.38µs        ? ?/sec
arrow_array_reader/Int8Array/binary packed skip, optional, half NULLs                                      1.00    103.4±2.07µs        ? ?/sec    1.01    104.5±0.68µs        ? ?/sec
arrow_array_reader/Int8Array/binary packed skip, optional, no NULLs                                        1.01     86.4±1.86µs        ? ?/sec    1.00     85.5±0.56µs        ? ?/sec
arrow_array_reader/Int8Array/binary packed, mandatory, no NULLs                                            1.00    110.4±1.05µs        ? ?/sec    1.00    110.8±0.30µs        ? ?/sec
arrow_array_reader/Int8Array/binary packed, optional, half NULLs                                           1.00    171.5±1.71µs        ? ?/sec    1.00    171.0±2.05µs        ? ?/sec
arrow_array_reader/Int8Array/binary packed, optional, no NULLs                                             1.00    115.2±1.25µs        ? ?/sec    1.00    115.7±0.70µs        ? ?/sec
arrow_array_reader/Int8Array/byte_stream_split encoded, mandatory, no NULLs                                1.00     34.6±0.31µs        ? ?/sec    1.01     34.8±0.34µs        ? ?/sec
arrow_array_reader/Int8Array/byte_stream_split encoded, optional, half NULLs                               1.00    131.7±0.83µs        ? ?/sec    1.00    131.2±1.30µs        ? ?/sec
arrow_array_reader/Int8Array/byte_stream_split encoded, optional, no NULLs                                 1.04     39.0±0.18µs        ? ?/sec    1.00     37.5±0.49µs        ? ?/sec
arrow_array_reader/Int8Array/dictionary encoded, mandatory, no NULLs                                       1.00    101.8±0.61µs        ? ?/sec    1.01    102.5±0.74µs        ? ?/sec
arrow_array_reader/Int8Array/dictionary encoded, optional, half NULLs                                      1.00    169.5±2.17µs        ? ?/sec    1.00    169.1±0.99µs        ? ?/sec
arrow_array_reader/Int8Array/dictionary encoded, optional, no NULLs                                        1.00    106.4±0.78µs        ? ?/sec    1.01    107.2±0.61µs        ? ?/sec
arrow_array_reader/Int8Array/plain encoded, mandatory, no NULLs                                            1.00     28.8±0.25µs        ? ?/sec    1.00     28.8±0.38µs        ? ?/sec
arrow_array_reader/Int8Array/plain encoded, optional, half NULLs                                           1.01    129.4±1.67µs        ? ?/sec    1.00    128.1±0.62µs        ? ?/sec
arrow_array_reader/Int8Array/plain encoded, optional, no NULLs                                             1.00     33.6±0.41µs        ? ?/sec    1.00     33.8±0.43µs        ? ?/sec
arrow_array_reader/ListArray/plain encoded optional strings half NULLs                                     1.21      7.2±0.04ms        ? ?/sec    1.00      5.9±0.06ms        ? ?/sec
arrow_array_reader/ListArray/plain encoded optional strings no NULLs                                       1.07     12.6±0.12ms        ? ?/sec    1.00     11.8±0.15ms        ? ?/sec
arrow_array_reader/StringArray/dictionary encoded, mandatory, no NULLs                                     1.00    494.4±4.18µs        ? ?/sec    1.00    493.1±8.96µs        ? ?/sec
arrow_array_reader/StringArray/dictionary encoded, optional, half NULLs                                    1.00    662.7±6.53µs        ? ?/sec    1.01   666.9±10.81µs        ? ?/sec
arrow_array_reader/StringArray/dictionary encoded, optional, no NULLs                                      1.00    487.4±4.77µs        ? ?/sec    1.02   499.3±13.29µs        ? ?/sec
arrow_array_reader/StringArray/plain encoded, mandatory, no NULLs                                          1.03   670.7±11.07µs        ? ?/sec    1.00    650.5±8.83µs        ? ?/sec
arrow_array_reader/StringArray/plain encoded, optional, half NULLs                                         1.02    789.9±4.80µs        ? ?/sec    1.00    774.9±3.90µs        ? ?/sec
arrow_array_reader/StringArray/plain encoded, optional, no NULLs                                           1.03    681.1±7.98µs        ? ?/sec    1.00    658.3±7.86µs        ? ?/sec
arrow_array_reader/StringDictionary/dictionary encoded, mandatory, no NULLs                                1.00    312.3±4.07µs        ? ?/sec    1.06    331.6±6.35µs        ? ?/sec
arrow_array_reader/StringDictionary/dictionary encoded, optional, half NULLs                               1.00    364.5±6.15µs        ? ?/sec    1.09    396.7±2.20µs        ? ?/sec
arrow_array_reader/StringDictionary/dictionary encoded, optional, no NULLs                                 1.00    317.6±3.73µs        ? ?/sec    1.07    338.4±7.45µs        ? ?/sec
arrow_array_reader/StringViewArray/dictionary encoded, mandatory, no NULLs                                 1.03    238.3±4.18µs        ? ?/sec    1.00    230.7±3.59µs        ? ?/sec
arrow_array_reader/StringViewArray/dictionary encoded, optional, half NULLs                                1.16    246.2±0.92µs        ? ?/sec    1.00    211.3±2.12µs        ? ?/sec
arrow_array_reader/StringViewArray/dictionary encoded, optional, no NULLs                                  1.03    243.5±3.61µs        ? ?/sec    1.00    235.9±3.65µs        ? ?/sec
arrow_array_reader/StringViewArray/plain encoded, mandatory, no NULLs                                      1.00   444.4±12.44µs        ? ?/sec    1.13    500.0±6.97µs        ? ?/sec
arrow_array_reader/StringViewArray/plain encoded, optional, half NULLs                                     1.00    352.9±2.27µs        ? ?/sec    1.01    358.2±4.37µs        ? ?/sec
arrow_array_reader/StringViewArray/plain encoded, optional, no NULLs                                       1.00   454.7±20.96µs        ? ?/sec    1.13    512.2±8.39µs        ? ?/sec
arrow_array_reader/UInt16Array/binary packed skip, mandatory, no NULLs                                     1.01     94.9±1.25µs        ? ?/sec    1.00     94.4±1.12µs        ? ?/sec
arrow_array_reader/UInt16Array/binary packed skip, optional, half NULLs                                    1.00    112.1±0.46µs        ? ?/sec    1.00    112.4±5.14µs        ? ?/sec
arrow_array_reader/UInt16Array/binary packed skip, optional, no NULLs                                      1.01     97.2±2.55µs        ? ?/sec    1.00     96.6±0.79µs        ? ?/sec
arrow_array_reader/UInt16Array/binary packed, mandatory, no NULLs                                          1.01    130.1±2.46µs        ? ?/sec    1.00    128.6±2.04µs        ? ?/sec
arrow_array_reader/UInt16Array/binary packed, optional, half NULLs                                         1.01    187.1±2.83µs        ? ?/sec    1.00    185.5±4.12µs        ? ?/sec
arrow_array_reader/UInt16Array/binary packed, optional, no NULLs                                           1.02    135.1±2.97µs        ? ?/sec    1.00    133.0±1.74µs        ? ?/sec
arrow_array_reader/UInt16Array/byte_stream_split encoded, mandatory, no NULLs                              1.00     40.9±0.25µs        ? ?/sec    1.00     40.8±0.22µs        ? ?/sec
arrow_array_reader/UInt16Array/byte_stream_split encoded, optional, half NULLs                             1.01    140.0±1.00µs        ? ?/sec    1.00    138.3±1.50µs        ? ?/sec
arrow_array_reader/UInt16Array/byte_stream_split encoded, optional, no NULLs                               1.00     45.4±0.19µs        ? ?/sec    1.00     45.4±0.21µs        ? ?/sec
arrow_array_reader/UInt16Array/dictionary encoded, mandatory, no NULLs                                     1.00    109.6±0.89µs        ? ?/sec    1.01    110.5±1.05µs        ? ?/sec
arrow_array_reader/UInt16Array/dictionary encoded, optional, half NULLs                                    1.00    176.5±0.91µs        ? ?/sec    1.00    176.6±2.09µs        ? ?/sec
arrow_array_reader/UInt16Array/dictionary encoded, optional, no NULLs                                      1.00    114.5±1.37µs        ? ?/sec    1.01    115.1±1.09µs        ? ?/sec
arrow_array_reader/UInt16Array/plain encoded, mandatory, no NULLs                                          1.01     36.7±0.12µs        ? ?/sec    1.00     36.5±0.15µs        ? ?/sec
arrow_array_reader/UInt16Array/plain encoded, optional, half NULLs                                         1.02    137.7±1.65µs        ? ?/sec    1.00    135.7±0.77µs        ? ?/sec
arrow_array_reader/UInt16Array/plain encoded, optional, no NULLs                                           1.00     41.5±0.40µs        ? ?/sec    1.00     41.5±0.19µs        ? ?/sec
arrow_array_reader/UInt32Array/binary packed skip, mandatory, no NULLs                                     1.00     84.6±1.45µs        ? ?/sec    1.00     84.2±1.56µs        ? ?/sec
arrow_array_reader/UInt32Array/binary packed skip, optional, half NULLs                                    1.00    101.8±0.94µs        ? ?/sec    1.00    102.0±1.21µs        ? ?/sec
arrow_array_reader/UInt32Array/binary packed skip, optional, no NULLs                                      1.01     87.4±2.15µs        ? ?/sec    1.00     86.8±0.75µs        ? ?/sec
arrow_array_reader/UInt32Array/binary packed, mandatory, no NULLs                                          1.02    110.8±3.96µs        ? ?/sec    1.00    108.7±0.91µs        ? ?/sec
arrow_array_reader/UInt32Array/binary packed, optional, half NULLs                                         1.01    166.7±1.53µs        ? ?/sec    1.00    165.9±0.57µs        ? ?/sec
arrow_array_reader/UInt32Array/binary packed, optional, no NULLs                                           1.01    114.8±3.01µs        ? ?/sec    1.00    113.5±1.57µs        ? ?/sec
arrow_array_reader/UInt32Array/byte_stream_split encoded, mandatory, no NULLs                              1.00     22.6±0.35µs        ? ?/sec    1.06     24.0±0.39µs        ? ?/sec
arrow_array_reader/UInt32Array/byte_stream_split encoded, optional, half NULLs                             1.01    120.8±0.76µs        ? ?/sec    1.00    119.2±0.67µs        ? ?/sec
arrow_array_reader/UInt32Array/byte_stream_split encoded, optional, no NULLs                               1.00     26.8±0.35µs        ? ?/sec    1.06     28.3±0.42µs        ? ?/sec
arrow_array_reader/UInt32Array/dictionary encoded, mandatory, no NULLs                                     1.00     91.6±4.94µs        ? ?/sec    1.01     92.1±0.94µs        ? ?/sec
arrow_array_reader/UInt32Array/dictionary encoded, optional, half NULLs                                    1.00    157.5±2.14µs        ? ?/sec    1.00    158.1±3.24µs        ? ?/sec
arrow_array_reader/UInt32Array/dictionary encoded, optional, no NULLs                                      1.00     95.7±0.98µs        ? ?/sec    1.01     96.8±1.90µs        ? ?/sec
arrow_array_reader/UInt32Array/plain encoded, mandatory, no NULLs                                          1.00     18.1±0.93µs        ? ?/sec    1.03     18.6±1.00µs        ? ?/sec
arrow_array_reader/UInt32Array/plain encoded, optional, half NULLs                                         1.00    117.8±0.85µs        ? ?/sec    1.00    117.9±1.04µs        ? ?/sec
arrow_array_reader/UInt32Array/plain encoded, optional, no NULLs                                           1.03     23.8±1.07µs        ? ?/sec    1.00     23.1±0.98µs        ? ?/sec
arrow_array_reader/UInt64Array/binary packed skip, mandatory, no NULLs                                     1.00     80.0±0.84µs        ? ?/sec    1.00     79.7±0.60µs        ? ?/sec
arrow_array_reader/UInt64Array/binary packed skip, optional, half NULLs                                    1.00    101.8±1.59µs        ? ?/sec    1.01    102.9±0.80µs        ? ?/sec
arrow_array_reader/UInt64Array/binary packed skip, optional, no NULLs                                      1.00     82.7±0.57µs        ? ?/sec    1.00     82.8±0.33µs        ? ?/sec
arrow_array_reader/UInt64Array/binary packed, mandatory, no NULLs                                          1.00    106.9±1.34µs        ? ?/sec    1.00    106.6±1.55µs        ? ?/sec
arrow_array_reader/UInt64Array/binary packed, optional, half NULLs                                         1.00    166.9±1.53µs        ? ?/sec    1.01    168.2±0.86µs        ? ?/sec
arrow_array_reader/UInt64Array/binary packed, optional, no NULLs                                           1.00    110.2±1.45µs        ? ?/sec    1.01    111.8±2.47µs        ? ?/sec
arrow_array_reader/UInt64Array/byte_stream_split encoded, mandatory, no NULLs                              1.00    146.9±0.68µs        ? ?/sec    1.00    146.5±1.21µs        ? ?/sec
arrow_array_reader/UInt64Array/byte_stream_split encoded, optional, half NULLs                             1.00    189.8±1.71µs        ? ?/sec    1.01    192.1±3.56µs        ? ?/sec
arrow_array_reader/UInt64Array/byte_stream_split encoded, optional, no NULLs                               1.00    151.6±0.82µs        ? ?/sec    1.00    151.9±0.64µs        ? ?/sec
arrow_array_reader/UInt64Array/dictionary encoded, mandatory, no NULLs                                     1.00     88.4±2.37µs        ? ?/sec    1.01     89.7±1.43µs        ? ?/sec
arrow_array_reader/UInt64Array/dictionary encoded, optional, half NULLs                                    1.00    158.5±1.30µs        ? ?/sec    1.00    158.8±2.20µs        ? ?/sec
arrow_array_reader/UInt64Array/dictionary encoded, optional, no NULLs                                      1.00     92.8±1.26µs        ? ?/sec    1.01     93.7±0.83µs        ? ?/sec
arrow_array_reader/UInt64Array/plain encoded, mandatory, no NULLs                                          1.00     38.3±1.11µs        ? ?/sec    1.16     44.4±2.93µs        ? ?/sec
arrow_array_reader/UInt64Array/plain encoded, optional, half NULLs                                         1.01    136.0±2.00µs        ? ?/sec    1.00    135.2±0.79µs        ? ?/sec
arrow_array_reader/UInt64Array/plain encoded, optional, no NULLs                                           1.00     47.8±1.00µs        ? ?/sec    1.06     50.5±3.21µs        ? ?/sec
arrow_array_reader/UInt8Array/binary packed skip, mandatory, no NULLs                                      1.00     90.0±1.10µs        ? ?/sec    1.00     89.9±1.18µs        ? ?/sec
arrow_array_reader/UInt8Array/binary packed skip, optional, half NULLs                                     1.01    107.1±2.78µs        ? ?/sec    1.00    106.4±0.49µs        ? ?/sec
arrow_array_reader/UInt8Array/binary packed skip, optional, no NULLs                                       1.00     92.4±1.53µs        ? ?/sec    1.00     92.3±0.39µs        ? ?/sec
arrow_array_reader/UInt8Array/binary packed, mandatory, no NULLs                                           1.00    120.7±1.99µs        ? ?/sec    1.00    120.2±3.23µs        ? ?/sec
arrow_array_reader/UInt8Array/binary packed, optional, half NULLs                                          1.01    176.8±1.02µs        ? ?/sec    1.00    175.3±1.32µs        ? ?/sec
arrow_array_reader/UInt8Array/binary packed, optional, no NULLs                                            1.00    124.4±0.88µs        ? ?/sec    1.00    124.7±1.50µs        ? ?/sec
arrow_array_reader/UInt8Array/byte_stream_split encoded, mandatory, no NULLs                               1.00     34.6±0.18µs        ? ?/sec    1.00     34.6±0.14µs        ? ?/sec
arrow_array_reader/UInt8Array/byte_stream_split encoded, optional, half NULLs                              1.01    132.0±0.63µs        ? ?/sec    1.00    130.4±0.79µs        ? ?/sec
arrow_array_reader/UInt8Array/byte_stream_split encoded, optional, no NULLs                                1.00     38.9±0.24µs        ? ?/sec    1.00     39.0±0.55µs        ? ?/sec
arrow_array_reader/UInt8Array/dictionary encoded, mandatory, no NULLs                                      1.00    101.8±1.20µs        ? ?/sec    1.00    102.2±0.68µs        ? ?/sec
arrow_array_reader/UInt8Array/dictionary encoded, optional, half NULLs                                     1.00    169.2±1.26µs        ? ?/sec    1.00    169.7±3.37µs        ? ?/sec
arrow_array_reader/UInt8Array/dictionary encoded, optional, no NULLs                                       1.00    106.5±0.87µs        ? ?/sec    1.01    107.5±3.40µs        ? ?/sec
arrow_array_reader/UInt8Array/plain encoded, mandatory, no NULLs                                           1.00     28.7±0.16µs        ? ?/sec    1.00     28.8±0.61µs        ? ?/sec
arrow_array_reader/UInt8Array/plain encoded, optional, half NULLs                                          1.02    130.2±1.11µs        ? ?/sec    1.00    127.8±1.03µs        ? ?/sec
arrow_array_reader/UInt8Array/plain encoded, optional, no NULLs                                            1.00     33.6±0.65µs        ? ?/sec    1.00     33.4±0.39µs        ? ?/sec
arrow_array_reader/struct/Int32Array/plain encoded, mandatory struct, optional data, half NULLs            1.01    119.9±1.75µs        ? ?/sec    1.00    118.6±3.35µs        ? ?/sec
arrow_array_reader/struct/Int32Array/plain encoded, mandatory struct, optional data, no NULLs              1.02     24.1±1.20µs        ? ?/sec    1.00     23.6±1.25µs        ? ?/sec
arrow_array_reader/struct/Int32Array/plain encoded, optional struct, optional data, half NULLs             2.83    694.2±3.72µs        ? ?/sec    1.00    244.9±2.68µs        ? ?/sec
arrow_array_reader/struct/Int32Array/plain encoded, optional struct, optional data, no NULLs               2.12    265.7±5.08µs        ? ?/sec    1.00    125.1±2.11µs        ? ?/sec

@alamb-ghbot
Copy link

🤖 ./gh_compare_arrow.sh gh_compare_arrow.sh Running
Linux aal-dev 6.14.0-1018-gcp #19~24.04.1-Ubuntu SMP Wed Sep 24 23:23:09 UTC 2025 x86_64 x86_64 x86_64 GNU/Linux
Comparing optimize-struct-reading (f447bac) to 9c6065c diff
BENCH_NAME=arrow_reader_row_filter
BENCH_COMMAND=cargo bench --features=arrow,async,test_common,experimental --bench arrow_reader_row_filter
BENCH_FILTER=
BENCH_BRANCH_NAME=optimize-struct-reading
Results will be posted here when complete

@alamb-ghbot
Copy link

🤖: Benchmark completed

Details

group                                                                                main                                    optimize-struct-reading
-----                                                                                ----                                    -----------------------
arrow_reader_row_filter/float64 <= 99.0/all_columns/async                            1.01  1702.0±21.24µs        ? ?/sec     1.00   1686.8±9.32µs        ? ?/sec
arrow_reader_row_filter/float64 <= 99.0/all_columns/sync                             1.02  1819.2±31.01µs        ? ?/sec     1.00  1782.6±25.12µs        ? ?/sec
arrow_reader_row_filter/float64 <= 99.0/exclude_filter_column/async                  1.02  1559.4±12.37µs        ? ?/sec     1.00  1532.3±11.68µs        ? ?/sec
arrow_reader_row_filter/float64 <= 99.0/exclude_filter_column/sync                   1.01  1543.9±68.65µs        ? ?/sec     1.00  1530.2±39.61µs        ? ?/sec
arrow_reader_row_filter/float64 > 99.0 AND ts >= 9000/all_columns/async              1.00  1481.6±11.02µs        ? ?/sec     1.00  1483.6±20.90µs        ? ?/sec
arrow_reader_row_filter/float64 > 99.0 AND ts >= 9000/all_columns/sync               1.01  1646.1±20.61µs        ? ?/sec     1.00  1624.5±27.32µs        ? ?/sec
arrow_reader_row_filter/float64 > 99.0 AND ts >= 9000/exclude_filter_column/async    1.02  1313.3±11.60µs        ? ?/sec     1.00  1284.6±12.58µs        ? ?/sec
arrow_reader_row_filter/float64 > 99.0 AND ts >= 9000/exclude_filter_column/sync     1.02  1315.6±10.43µs        ? ?/sec     1.00  1295.4±25.20µs        ? ?/sec
arrow_reader_row_filter/float64 > 99.0/all_columns/async                             1.00  1678.4±12.21µs        ? ?/sec     1.01  1695.9±39.82µs        ? ?/sec
arrow_reader_row_filter/float64 > 99.0/all_columns/sync                              1.01  1810.8±34.25µs        ? ?/sec     1.00  1796.9±13.36µs        ? ?/sec
arrow_reader_row_filter/float64 > 99.0/exclude_filter_column/async                   1.04  1591.9±172.47µs        ? ?/sec    1.00  1536.6±15.00µs        ? ?/sec
arrow_reader_row_filter/float64 > 99.0/exclude_filter_column/sync                    1.01  1530.7±19.68µs        ? ?/sec     1.00  1511.8±19.54µs        ? ?/sec
arrow_reader_row_filter/int64 == 9999/all_columns/async                              1.00    884.8±9.14µs        ? ?/sec     1.01    896.5±6.51µs        ? ?/sec
arrow_reader_row_filter/int64 == 9999/all_columns/sync                               1.00    829.4±5.86µs        ? ?/sec     1.02    846.9±9.50µs        ? ?/sec
arrow_reader_row_filter/int64 == 9999/exclude_filter_column/async                    1.00   807.3±10.64µs        ? ?/sec     1.03    832.5±6.87µs        ? ?/sec
arrow_reader_row_filter/int64 == 9999/exclude_filter_column/sync                     1.00    818.8±6.02µs        ? ?/sec     1.03   846.4±13.23µs        ? ?/sec
arrow_reader_row_filter/int64 > 90/all_columns/async                                 1.00      2.7±0.02ms        ? ?/sec     1.00      2.7±0.02ms        ? ?/sec
arrow_reader_row_filter/int64 > 90/all_columns/sync                                  1.00      2.5±0.04ms        ? ?/sec     1.00      2.5±0.02ms        ? ?/sec
arrow_reader_row_filter/int64 > 90/exclude_filter_column/async                       1.02      2.6±0.01ms        ? ?/sec     1.00      2.6±0.03ms        ? ?/sec
arrow_reader_row_filter/int64 > 90/exclude_filter_column/sync                        1.01      2.3±0.04ms        ? ?/sec     1.00      2.3±0.02ms        ? ?/sec
arrow_reader_row_filter/ts < 9000/all_columns/async                                  1.00  1907.4±18.09µs        ? ?/sec     1.01  1921.4±48.11µs        ? ?/sec
arrow_reader_row_filter/ts < 9000/all_columns/sync                                   1.00  1973.3±48.85µs        ? ?/sec     1.00  1977.1±43.27µs        ? ?/sec
arrow_reader_row_filter/ts < 9000/exclude_filter_column/async                        1.01  1743.8±12.56µs        ? ?/sec     1.00  1729.1±24.85µs        ? ?/sec
arrow_reader_row_filter/ts < 9000/exclude_filter_column/sync                         1.01  1744.4±21.16µs        ? ?/sec     1.00  1729.5±10.27µs        ? ?/sec
arrow_reader_row_filter/ts >= 9000/all_columns/async                                 1.00   1220.7±8.94µs        ? ?/sec     1.03  1253.2±29.16µs        ? ?/sec
arrow_reader_row_filter/ts >= 9000/all_columns/sync                                  1.00  1224.2±20.71µs        ? ?/sec     1.03  1255.6±12.33µs        ? ?/sec
arrow_reader_row_filter/ts >= 9000/exclude_filter_column/async                       1.00  1100.3±26.69µs        ? ?/sec     1.02  1126.2±13.19µs        ? ?/sec
arrow_reader_row_filter/ts >= 9000/exclude_filter_column/sync                        1.00   1103.7±9.32µs        ? ?/sec     1.04  1142.5±29.15µs        ? ?/sec
arrow_reader_row_filter/utf8View <> ''/all_columns/async                             1.01      3.2±0.06ms        ? ?/sec     1.00      3.2±0.04ms        ? ?/sec
arrow_reader_row_filter/utf8View <> ''/all_columns/sync                              1.00      3.5±0.04ms        ? ?/sec     1.01      3.5±0.04ms        ? ?/sec
arrow_reader_row_filter/utf8View <> ''/exclude_filter_column/async                   1.02      2.8±0.02ms        ? ?/sec     1.00      2.7±0.02ms        ? ?/sec
arrow_reader_row_filter/utf8View <> ''/exclude_filter_column/sync                    1.01      2.5±0.01ms        ? ?/sec     1.00      2.5±0.02ms        ? ?/sec

@alamb-ghbot
Copy link

🤖 ./gh_compare_arrow.sh gh_compare_arrow.sh Running
Linux aal-dev 6.14.0-1018-gcp #19~24.04.1-Ubuntu SMP Wed Sep 24 23:23:09 UTC 2025 x86_64 x86_64 x86_64 GNU/Linux
Comparing optimize-struct-reading (f447bac) to 9c6065c diff
BENCH_NAME=arrow_reader_clickbench
BENCH_COMMAND=cargo bench --features=arrow,async,test_common,experimental --bench arrow_reader_clickbench
BENCH_FILTER=
BENCH_BRANCH_NAME=optimize-struct-reading
Results will be posted here when complete

@alamb-ghbot
Copy link

🤖: Benchmark completed

Details

group                                main                                   optimize-struct-reading
-----                                ----                                   -----------------------
arrow_reader_clickbench/async/Q1     1.00      2.3±0.04ms        ? ?/sec    1.03      2.4±0.04ms        ? ?/sec
arrow_reader_clickbench/async/Q10    1.00     12.5±0.21ms        ? ?/sec    1.03     12.9±0.21ms        ? ?/sec
arrow_reader_clickbench/async/Q11    1.00     14.1±0.24ms        ? ?/sec    1.04     14.6±0.24ms        ? ?/sec
arrow_reader_clickbench/async/Q12    1.00     25.1±0.26ms        ? ?/sec    1.02     25.6±0.45ms        ? ?/sec
arrow_reader_clickbench/async/Q13    1.00     30.4±0.36ms        ? ?/sec    1.02     31.0±0.59ms        ? ?/sec
arrow_reader_clickbench/async/Q14    1.00     27.8±0.65ms        ? ?/sec    1.01     28.2±0.67ms        ? ?/sec
arrow_reader_clickbench/async/Q19    1.00      5.3±0.07ms        ? ?/sec    1.01      5.3±0.10ms        ? ?/sec
arrow_reader_clickbench/async/Q20    1.34    153.5±1.06ms        ? ?/sec    1.00    114.8±1.38ms        ? ?/sec
arrow_reader_clickbench/async/Q21    1.24    163.3±0.98ms        ? ?/sec    1.00    132.0±0.53ms        ? ?/sec
arrow_reader_clickbench/async/Q22    1.17   320.7±17.89ms        ? ?/sec    1.00    274.0±5.73ms        ? ?/sec
arrow_reader_clickbench/async/Q23    1.00    402.7±2.69ms        ? ?/sec    1.01    408.1±3.17ms        ? ?/sec
arrow_reader_clickbench/async/Q24    1.01     34.5±0.91ms        ? ?/sec    1.00     34.1±0.82ms        ? ?/sec
arrow_reader_clickbench/async/Q27    1.00     98.1±0.74ms        ? ?/sec    1.02    100.1±1.21ms        ? ?/sec
arrow_reader_clickbench/async/Q28    1.00     97.2±1.14ms        ? ?/sec    1.02     98.9±0.90ms        ? ?/sec
arrow_reader_clickbench/async/Q30    1.00     30.5±0.64ms        ? ?/sec    1.01     30.9±0.32ms        ? ?/sec
arrow_reader_clickbench/async/Q36    1.00    106.6±0.56ms        ? ?/sec    1.02    109.0±0.72ms        ? ?/sec
arrow_reader_clickbench/async/Q37    1.00     82.7±1.14ms        ? ?/sec    1.02     84.7±0.48ms        ? ?/sec
arrow_reader_clickbench/async/Q38    1.00     32.1±0.30ms        ? ?/sec    1.02     32.8±0.33ms        ? ?/sec
arrow_reader_clickbench/async/Q39    1.00     45.3±0.59ms        ? ?/sec    1.02     46.3±0.58ms        ? ?/sec
arrow_reader_clickbench/async/Q40    1.00     26.8±0.33ms        ? ?/sec    1.02     27.3±0.35ms        ? ?/sec
arrow_reader_clickbench/async/Q41    1.00     21.5±0.33ms        ? ?/sec    1.02     22.1±0.40ms        ? ?/sec
arrow_reader_clickbench/async/Q42    1.00     10.6±0.08ms        ? ?/sec    1.03     10.9±0.25ms        ? ?/sec
arrow_reader_clickbench/sync/Q1      1.00      2.1±0.03ms        ? ?/sec    1.00      2.1±0.01ms        ? ?/sec
arrow_reader_clickbench/sync/Q10     1.00      9.7±0.14ms        ? ?/sec    1.02      9.9±0.22ms        ? ?/sec
arrow_reader_clickbench/sync/Q11     1.00     11.2±0.07ms        ? ?/sec    1.04     11.6±0.20ms        ? ?/sec
arrow_reader_clickbench/sync/Q12     1.00     33.2±1.28ms        ? ?/sec    1.01     33.6±1.08ms        ? ?/sec
arrow_reader_clickbench/sync/Q13     1.00     43.4±4.31ms        ? ?/sec    1.00     43.3±2.28ms        ? ?/sec
arrow_reader_clickbench/sync/Q14     1.17     41.7±0.77ms        ? ?/sec    1.00     35.6±0.43ms        ? ?/sec
arrow_reader_clickbench/sync/Q19     1.01      4.2±0.03ms        ? ?/sec    1.00      4.2±0.05ms        ? ?/sec
arrow_reader_clickbench/sync/Q20     1.00    174.0±1.29ms        ? ?/sec    1.01    176.3±1.70ms        ? ?/sec
arrow_reader_clickbench/sync/Q21     1.01    228.3±1.78ms        ? ?/sec    1.00    225.0±1.41ms        ? ?/sec
arrow_reader_clickbench/sync/Q22     1.00    467.1±3.87ms        ? ?/sec    1.02    477.8±3.49ms        ? ?/sec
arrow_reader_clickbench/sync/Q23     1.00   435.7±14.66ms        ? ?/sec    1.00   437.8±16.98ms        ? ?/sec
arrow_reader_clickbench/sync/Q24     1.05     44.7±0.39ms        ? ?/sec    1.00     42.7±0.67ms        ? ?/sec
arrow_reader_clickbench/sync/Q27     1.00    150.2±1.47ms        ? ?/sec    1.03    154.9±1.51ms        ? ?/sec
arrow_reader_clickbench/sync/Q28     1.00    145.6±1.28ms        ? ?/sec    1.02    148.7±0.86ms        ? ?/sec
arrow_reader_clickbench/sync/Q30     1.00     30.6±0.32ms        ? ?/sec    1.01     30.9±0.33ms        ? ?/sec
arrow_reader_clickbench/sync/Q36     1.00    149.6±1.52ms        ? ?/sec    1.04    155.4±2.53ms        ? ?/sec
arrow_reader_clickbench/sync/Q37     1.00     85.3±0.67ms        ? ?/sec    1.03     88.1±0.97ms        ? ?/sec
arrow_reader_clickbench/sync/Q38     1.00     28.3±0.46ms        ? ?/sec    1.02     29.0±0.27ms        ? ?/sec
arrow_reader_clickbench/sync/Q39     1.00     32.6±0.51ms        ? ?/sec    1.04     33.8±0.43ms        ? ?/sec
arrow_reader_clickbench/sync/Q40     1.00     25.6±0.54ms        ? ?/sec    1.03     26.4±0.60ms        ? ?/sec
arrow_reader_clickbench/sync/Q41     1.00     28.1±0.32ms        ? ?/sec    1.03     28.8±0.43ms        ? ?/sec
arrow_reader_clickbench/sync/Q42     1.00     12.1±0.07ms        ? ?/sec    1.01     12.3±0.29ms        ? ?/sec

Copy link
Contributor

@alamb alamb left a comment

Choose a reason for hiding this comment

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

Love it -- thank you @jhorstmann and @Dandandan

for i in &levels[start..] {
nulls.append(i == max_level);
// Safety: slice iterator has a trusted length
unsafe {
Copy link
Contributor

Choose a reason for hiding this comment

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

Another thing that we could potentially try is to evaluate to a bitmap first and then append that bitmap directly via set_bits or something -- though now that I type this I am not sure that would be be any better 🤔

Copy link
Contributor Author

Choose a reason for hiding this comment

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

That would be interesting to try out. It probably will only be faster when using explicit simd intrinsics to compute that bitmap.

@Dandandan Dandandan merged commit ba21a83 into apache:main Jan 19, 2026
16 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

parquet Changes to the parquet crate

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Parquet] Optimize struct reading

4 participants