Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 7 additions & 3 deletions benchmarks/bench.sh
Original file line number Diff line number Diff line change
Expand Up @@ -106,7 +106,7 @@ wide_schema: Small-projection queries on a wide synthetic dataset (10
(runs both 'wide' and 'narrow' subgroups: narrow is an internal baseline; the wide-vs-narrow ratio is the signal)
predicate_eval: Conjunctive (AND) filter-evaluation micro-benchmarks; each subgroup is a different predicate pattern, to test how an
adaptive predicate-ordering system behaves across them (see https://github.com/apache/datafusion/issues/11262)
(subgroups via BENCH_SUBGROUP: costsel, cost, selectivity, cardinality, width, scale, neutral, correlation, drift)
(subgroups via BENCH_SUBGROUP: costsel, cost, selectivity, cardinality, width, scale, neutral, correlation, drift, nulls)
(toggle a system under test with its native DATAFUSION_* env var; size data with PRED_ROWS, string width with PRED_FILL)
parquet_row_filter_skip: Per-RG fully-matched RowFilter skip on Parquet (apache/datafusion#23696); clustered string key + low-selectivity
range filter + pushdown, so most row groups are fully matched and the per-row RowFilter is skipped on them
Expand Down Expand Up @@ -876,7 +876,11 @@ run_push_down_topk() {
# micro-benchmarks where each subgroup is a different predicate pattern, used to
# test how an adaptive predicate-ordering system behaves across them (see
# https://github.com/apache/datafusion/issues/11262). Data is generated inline
# by the suite's load SQL, so there is no data step.
# by the suite's load SQL, so there is no data step (drift q82 and q83 share 16
# small Parquet files written into sql_benchmarks/predicate_eval/scratch/, which
# is gitignored; q82 reads them with target_partitions=1, so the selectivity flip
# lands halfway through one stream, and q83 with 16, so each stream gets one whole
# file and a fixed profile).
#
# By default the suite measures DataFusion's built-in left-deep AND short-circuit
# and sets no engine config of its own. To evaluate a system under test, export
Expand All @@ -885,7 +889,7 @@ run_push_down_topk() {
# DATAFUSION_EXECUTION_ADAPTIVE_FILTER_REORDERING=true ./bench.sh run predicate_eval
# Suite-specific knobs (string-substituted into the load SQL, not engine config):
# BENCH_SUBGROUP run one subgroup (costsel, cost, selectivity, cardinality,
# width, scale, neutral, correlation, drift)
# width, scale, neutral, correlation, drift, nulls)
# PRED_ROWS synthetic row count (default 1_000_000; the scale subgroup
# overrides this per query)
# PRED_FILL filler chars per marker = string-column width knob
Expand Down
2 changes: 1 addition & 1 deletion benchmarks/sql_benchmarks/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ in the community:
| `tpcds` | TPC‑DS queries |
| `tpch` | TPC‑H queries |
| `wide_schema` | Small-projection queries on a wide (1024-col, 256-file) synthetic dataset; runs `wide` + `narrow` subgroups for comparison |
| `predicate_eval` | Conjunctive (AND) filter-evaluation micro-benchmarks; each subgroup is a different predicate pattern, to test how an adaptive predicate-ordering system behaves across them ([#11262](https://github.com/apache/datafusion/issues/11262)). Subgroups (`--subgroup`): `costsel`, `cost`, `selectivity`, `cardinality`, `width`, `scale`, `neutral`, `correlation`, `drift`. Configure the system under test through its DataFusion settings. |
| `predicate_eval` | Conjunctive (AND) filter-evaluation micro-benchmarks; each subgroup is a different predicate pattern, to test how an adaptive predicate-ordering system behaves across them ([#11262](https://github.com/apache/datafusion/issues/11262)). Subgroups (`--subgroup`): `costsel`, `cost`, `selectivity`, `cardinality`, `width`, `scale`, `neutral`, `correlation`, `drift`, `nulls`. The suite sets no engine config of its own, so by default it measures DataFusion's built-in left-deep `AND` short-circuit; point it at a system under test by exporting that system's own DataFusion setting (the harness builds its `SessionConfig` with `SessionConfig::from_env`). Every query is a `count(*)`, and the counts are checked in under `predicate_eval/results/`, so `--result-mode validate` also checks that a reordering under test still returns the same rows; the checked-in counts were persisted at the suite defaults (`PRED_ROWS=1000000`, `PRED_FILL=30`), so validation assumes those (the `scale` and `width` subgroups pin their own values per query and validate at any setting). |
| `parquet_row_filter_skip` | Micro-benchmark for the per-row-group fully-matched RowFilter skip on Parquet scans ([#23696](https://github.com/apache/datafusion/issues/23696)). Subgroups (`--subgroup`): `skip` (clustered key, most row groups fully matched by statistics so the per-row filter is skipped), `control` (scrambled key, no row group is ever fully matched). Size the data with `PRED_ROWS` and the row-group size with `RG_SIZE`. |

# Running Benchmarks
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup cardinality

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=cardinality
QPAD=30
QUERY=cardinality/q30
DATASET=ints
NAME=cardinality_q30_k2
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup cardinality

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=cardinality
QPAD=31
QUERY=cardinality/q31
DATASET=ints
NAME=cardinality_q31_k4
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup cardinality

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=cardinality
QPAD=32
QUERY=cardinality/q32
DATASET=ints
NAME=cardinality_q32_k8
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup cardinality

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=cardinality
QPAD=33
QUERY=cardinality/q33
DATASET=ints
NAME=cardinality_q33_k16
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
subgroup cardinality

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
QUERY=cardinality/q34
DATASET=ints_wide
NAME=cardinality_q34_k8_wide64
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup correlation

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=correlation
QPAD=70
QUERY=correlation/q70
DATASET=corr
NAME=correlation_q70_independent
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup correlation

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=correlation
QPAD=71
QUERY=correlation/q71
DATASET=corr
NAME=correlation_q71_positive
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup correlation

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=correlation
QPAD=72
QUERY=correlation/q72
DATASET=corr
NAME=correlation_q72_anti
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup correlation

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=correlation
QPAD=73
QUERY=correlation/q73
DATASET=corrproxy
NAME=correlation_q73_redundant_proxy
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup cost

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=cost
QPAD=10
QUERY=cost/q10
DATASET=mixed
NAME=cost_q10_expensive_first
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup cost

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=cost
QPAD=11
QUERY=cost/q11
DATASET=mixed
NAME=cost_q11_cheap_first
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup costsel

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=costsel
QPAD=01
QUERY=costsel/q01
DATASET=markers
NAME=costsel_q01_regexp_selective_last
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup costsel

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=costsel
QPAD=02
QUERY=costsel/q02
DATASET=markers
NAME=costsel_q02_regexp_selective_first
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup costsel

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=costsel
QPAD=03
QUERY=costsel/q03
DATASET=mixed
NAME=costsel_q03_cheap_unselective_then_expensive_selective
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
subgroup costsel

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
QUERY=costsel/q04
DATASET=mixed
NAME=costsel_q04_expensive_selective_then_cheap_unselective
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup drift

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=drift
QPAD=80
QUERY=drift/q80
DATASET=drift
NAME=drift_q80_a_then_b

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
subgroup drift

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
QUERY=drift/q82
DATASET=drift_split
NAME=drift_q82_late_flip

# One stream over the whole directory: the flip lands mid-scan.
init
set datafusion.execution.target_partitions = 1;
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
subgroup drift

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
QUERY=drift/q83
DATASET=drift_split
NAME=drift_q83_per_partition_skew

# One file per stream: each stream sees a single profile.
init
set datafusion.execution.target_partitions = 16;
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup neutral

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=neutral
QPAD=60
QUERY=neutral/q60
DATASET=ints
NAME=neutral_q60_cheap_uniform
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup neutral

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=neutral
QPAD=61
QUERY=neutral/q61
DATASET=markers
NAME=neutral_q61_expensive_uniform
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
subgroup nulls

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
QUERY=nulls/q90
DATASET=ints
NAME=nulls_q90_nullable_selective_first
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
subgroup nulls

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
QUERY=nulls/q91
DATASET=ints
NAME=nulls_q91_nullable_selective_last
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
subgroup scale

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=scale
QPAD=50
QUERY=costsel/q03
DATASET=mixed
PRED_ROWS=5000
NAME=scale_q50_5k
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
subgroup scale

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=scale
QPAD=51
QUERY=costsel/q03
DATASET=mixed
PRED_ROWS=100000
NAME=scale_q51_100k
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
subgroup scale

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=scale
QPAD=52
QUERY=costsel/q03
DATASET=mixed
PRED_ROWS=5000000
NAME=scale_q52_5m
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
subgroup scale

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=scale
QPAD=53
QUERY=costsel/q03
DATASET=mixed
PRED_ROWS=50000000
NAME=scale_q53_50m
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup selectivity

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=selectivity
QPAD=20
QUERY=selectivity/q20
DATASET=ints
NAME=selectivity_q20_unselective_first
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
subgroup selectivity

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=selectivity
QPAD=21
QUERY=selectivity/q21
DATASET=ints
NAME=selectivity_q21_selective_first
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
subgroup width

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=width
QPAD=40
QUERY=costsel/q01
DATASET=markers
PRED_FILL=2
NAME=width_q40_narrow
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
subgroup width

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=width
QPAD=41
QUERY=costsel/q01
DATASET=markers
PRED_FILL=30
NAME=width_q41_wide
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
subgroup width

template sql_benchmarks/predicate_eval/predicate_eval.benchmark.template
SUBGROUP=width
QPAD=42
QUERY=costsel/q01
DATASET=markers
PRED_FILL=170
NAME=width_q42_xwide
15 changes: 3 additions & 12 deletions benchmarks/sql_benchmarks/predicate_eval/load/corr.sql
Original file line number Diff line number Diff line change
@@ -1,15 +1,6 @@
-- Correlation dataset: a base column plus derived columns that control the
-- *conditional* selectivity of one predicate given another (its selectivity
-- among the rows that already passed the other).
--
-- x uniform [0,100)
-- x_pos = x (perfectly positively correlated: `x<k AND x_pos<k`
-- passes ~k%, not the ~k%^2 an independence assumption
-- predicts)
-- x_anti = 99 - x (anti-correlated: `x<k AND x_anti<k` is empty for k<=50)
-- ind independent control column, uniform [0,100)
--
-- PRED_ROWS sizes the table.
-- Correlation dataset: `x` uniform on [0,100); `x_pos` = x (perfectly positively
-- correlated); `x_anti` = 99 - x (anti-correlated); `ind` uniform on [0,100) and
-- independent of x. PRED_ROWS sizes the table.
CREATE TABLE t AS
SELECT
(value * 7) % 100 AS x,
Expand Down
34 changes: 12 additions & 22 deletions benchmarks/sql_benchmarks/predicate_eval/load/corrproxy.sql
Original file line number Diff line number Diff line change
@@ -1,30 +1,20 @@
-- Correlated-proxy dataset: a cheap integer predicate that is a perfect proxy
-- for three string predicates, plus one independent string predicate.
--
-- Correlated-proxy dataset:
-- c0 = 1 for ~30% of rows (cheap proxy)
-- s1, s2, s3 each contain a marker exactly where c0 = 1 (correlated)
-- s4 contains a marker for an independent ~30% (independent)
--
-- The four string columns are deliberately *identical in shape*: same width,
-- the same single marker at the same offset, each matched by an equally cheap
-- regex with the same ~30% marginal selectivity. Marginally the four regex
-- predicates are therefore indistinguishable -- same cost, same selectivity, in
-- every position -- so neither a marginal cost/selectivity estimator nor
-- runtime timing can prefer one over another. Only their *conditional*
-- behaviour behind the proxy differs: after `c0 = 1`, the s1/s2/s3 regexes keep
-- every survivor (each re-tests the proxy's condition) while the s4 regex still
-- discards ~70%. Only joint statistics can see that; an independence assumption
-- prices all four regexes identically in every position.
-- s1, s2, s3 each carry a marker exactly where c0 = 1 (correlated)
-- s4 carries a marker for an independent ~30% (independent)
-- PRED_FILL sets the filler width each side of the marker, PRED_ROWS the row count.
--
-- PRED_FILL sets the filler width on each side of the marker (a non-matching
-- `regexp_like` must scan the whole value), and PRED_ROWS sizes the table.
-- The four string columns are identical in shape -- same width, same marker
-- offset, same regex cost, same ~30% marginal selectivity -- so marginally they
-- are indistinguishable in every position. Only their joint distribution with the
-- proxy differs: after `c0 = 1` the s1/s2/s3 regexes keep every survivor while s4
-- still discards ~70%. Ranking them therefore takes joint statistics; an
-- independence assumption prices all four regexes identically everywhere.
CREATE TABLE t AS
WITH base AS (
SELECT
-- The cheap proxy and the independent control share one definition each, so
-- the perfect-proxy / independence invariants can't drift apart silently.
(value * 7) % 100 < 30 AS proxy, -- ~30%, drives c0 and s1/s2/s3
(value * 13) % 100 < 30 AS indep -- ~30%, independent of proxy, drives s4
(value * 7) % 100 < 30 AS proxy,
(value * 13) % 100 < 30 AS indep
FROM generate_series(1, ${PRED_ROWS:-1000000})
)
SELECT
Expand Down
Loading
Loading