The receipts · published verbatim from the working file
The speed-adjusted gap — pre-registration
Frozen 2026-07-13, with the way it could fail stated first and a pre-committed reading of the counter-test.
Last changed
Pre-registration — the speed-adjusted gap (H-SPG)
Frozen 2026-07-13, before any 2021→2022 or 2025→2026 pair was examined for this question. The git timestamp of this file is the freeze receipt. One confirmatory run; results published regardless.
The claim on trial
H-SP (sp-confirmatory-results-2026-07-13.md) proved sprint speed
carries information our boards ignore: +0.136 on next-season value on
contact beyond current value, EV95 and the luck gap (p<0.0001,
replicating TRAIN's +0.137). It did NOT prove that a speed-adjusted gap
makes a better Fade board. That is a separate claim and it gets its own
test.
The candidate signal:
gap_sa = luck_gap_adj − (a + b · sprint_speed)
with a and b from a single OLS of gap on sprint speed fit over TRAIN
seasons 2015–2019 only, and never refit. It asks: after the physics
have been told about legs, whose results still outran them?
Why this can fail — the part that makes it worth running
gap_sa fuses two variables into one number, and it fuses them at a
ratio set by the level relationship (how the gap tracks speed), not
by the outcome relationship (how each predicts decline). Those two
ratios have no reason to be equal. A two-column model that keeps the gap
and sprint speed separate is free to weight them optimally; the fused
number is not.
So there is a live possibility — near even money — that the honest answer is: don't fuse. Show speed as its own column and leave the gap alone. That is a MISS and it gets published exactly like a pass.
Test pairs — declared, and thin
Eleven seasons exist and three studies have spent most of them. H2 used 2015–2019 + 2021 as train and 2022–2023 as holdout. H-SP used 2015–2019 as train and 2022/2023/2024 as reserved test. What has never been used as a predictor pair for any question about the gap:
PAIR A 2021 -> 2022 n = 309
PAIR B 2025 -> 2026 n = 260 (outcome is season-to-date)
(Counts observed at freeze time; no variable relationships computed on either pair.) Both pooled, one run. Pair B is the deployment scenario — last season's signal against this season in progress. Its outcome window is partial, which makes it noisier, not biased.
The adjustment is fit on 2015–2019 only, so neither test pair's predictor NOR outcome season touches the fit. Fitting on 2022–24 would leak into Pair A, whose outcome year is 2022. It is not done.
PRIMARY (confirmatory)
Within each pair, rank every qualified batter by each signal and take the
top quintile — the same unit H2's published fade claim uses ("the top
quintile declined −0.68 annualized WAR vs the field"). Outcome: mean
Δ value on contact, aval_next − aval. A fade signal is good if the men
it flags actually fall.
SUCCESS = mean Δaval (top quintile by gap_sa)
< mean Δaval (top quintile by raw gap)
pooled across both pairs, AND a paired bootstrap over players
(2,000 replicates, resampled within pair, both quintiles
re-formed on each replicate, seed 20260713) gives a 95% CI on
the difference that excludes zero.
Anything else — wrong sign, CI spanning zero — is a MISS.
Qualification: ≥100 balls in play in BOTH seasons of the pair, ≥10 competitive runs on the Savant leaderboard in the predictor season. Requiring outcome-season BIP conditions on survival, a known bias; it is identical for both signals, so the comparison is fair, and it is declared here rather than discovered later.
SECONDARY (reported, with criterion)
The board that actually ships: top 15 by each signal, the live Fade board's size.
SUCCESS = mean Δaval (top 15 by gap_sa) < (top 15 by raw gap)
in BOTH pairs independently.
Declared in advance: n=15 per pair is thin and this criterion is underpowered on purpose. It is the product's real unit, so it is reported; the primary does not depend on it.
TERTIARY (reported, no criterion — the counter-test)
Three models, head to head, on the confirmatory pairs:
R aval_next ~ aval + ev95 + gap (today's engine)
S aval_next ~ aval + ev95 + gap_sa (the fused signal)
T aval_next ~ aval + ev95 + gap + sprint (two columns)
Reported: adjusted R² of each and the gap coefficient in each.
Pre-committed reading, written before the numbers exist: if T beats S materially, I will recommend against the fused signal even if the PRIMARY passes. A board ranked on a worse number is worse, whatever a ranking test says about it versus an even worse number.
Integration gate
- PRIMARY passes AND S is not materially beaten by T: the Fade board
ranks by
gap_sa; a Legend entry defines it; the methodology page carries this receipt. - PRIMARY passes BUT T beats S: the board keeps the raw gap as its rank and the engine gains sprint speed as a second signal — the fade thesis becomes two-dimensional. Design filed separately.
- PRIMARY fails: the Fade board stands exactly as it is.
In every branch, sprint speed is displayed as a column on the Fade board, with the H-SP receipt behind it. That much is already earned: a reader looking at Chandler Simpson deserves to see the 95th-percentile wheels that explain his gap, whether or not the engine ranks on them.
Out of scope, banked
The breakout overlay's gap term (−0.2781) inherits the same bias. Fixing it means re-validating a composite whose coefficients H2's confirmatory froze — a bigger claim, its own pre-registration (H-SPO), not smuggled in here.
Open calls
Unaffected. Fade calls already filed stand as filed, under the signal they were filed under. Nothing is edited after filing.
Execution
One evaluation. No re-runs, no threshold shopping. The script is
catalyst/analysis/spg_confirmatory.py, committed in the same commit as
this file, before it is run.