nullbench
Pre-register decisions. Score them against chance. Never backfill.
nullbench is a null-first decision evaluation lab: freeze choices before outcomes, settle against equal-cost pure-chance portfolios, keep an append-only hash-chained ledger, and report descriptive percentiles plus sequential e-diagnostics.
It is not a lottery predictor. Negative expected-value domains are welcome as stress tests for methodology.
Formal question: Is any strategy distinguishable from pure chance at equal cost?
Expected (and welcome) answer for fair games: no.
Install
# Python 3.11+
pip install nullbench
# from source
pip install -e ".[dev]"
Optional extras:
pip install "nullbench[coverage]" # OR-Tools max-disjoint coverage
pip install "nullbench[stats]" # properscoring; comparecast on non-Windows
# Sequential CS + e-process: pure-Python comparecast algorithms always on
# (official comparecast needs confseq/MSVC on Windows — we ship a MIT port)
5-minute demo
nullbench demo --name demo-study --path .
# step by step
nullbench init my-study -e exp-v1 -d demo649
nullbench strategy add random --study my-study --tickets 5 --seed 1
nullbench strategy add frequency --study my-study --id frequency --tickets 5 --seed 2
nullbench freeze P0100 --study my-study
nullbench settle --study my-study --period P0100
nullbench report --study my-study
nullbench status --study my-study
nullbench coverage --study my-study --tickets 5 --top 30
Taiwan Lottery domains (network)
# 威力彩 / 大樂透 — official API, month cache, fail-closed parse
nullbench init tw-super -d taiwan_super --fetch
# or: init without fetch, then
nullbench ingest --study tw-super
nullbench strategy add random --study tw-super -n 5
# pick a historical period id present in draws.jsonl, freeze BEFORE using that outcome
nullbench freeze 115000058 --study tw-super
nullbench settle --study tw-super --period 115000058
nullbench report --study tw-super
Conservative valuation: floating jackpot tiers score as 0 by default so reports cannot be inflated by rare top prizes. Fixed tiers only.
Pure simulation. No betting. No predicted numbers.
List domains: nullbench domains
What you get
| Piece | Role |
|---|---|
| Freeze | Tickets locked with content_hash before outcome use |
| Null bank | N equal-cost random portfolios (default 200) |
| Settle | P&L under prize table; never rewrites freezes |
| Ledger | Append-only JSONL + SHA-256 chain |
| Report | Descriptive percentiles + sequential e-diagnostics |
| Claim guard | Blocks promotional language scans |
| Plugins | nullbench.strategies entry points |
Giants we stand on
| Layer | Package / plan |
|---|---|
| Schemas / CLI | Pydantic v2, Typer, Rich |
| Numerics | NumPy |
| Proper scores | properscoring (optional) |
| Sequential CS + e-process | comparecast algorithms (pure-Python port; official package when confseq builds) |
| Proper scores | properscoring optional |
| Combinatorial coverage | OR-Tools CP-SAT (nullbench coverage) |
Core honesty machinery (freeze, null bank, ledger, claim lint) stays ours.
Plugin strategies
See examples/plugin_strategy_readme.md.
[project.entry-points."nullbench.strategies"]
cold = "mypkg.strats:propose_cold"
Study layout
my-study/
experiment.json
data/draws.jsonl
data/cache/raw/<game>/YYYY-MM.json # taiwan only
ledger/events.jsonl
reports/latest.md
reports/latest.json
Domains
| Domain | Status |
|---|---|
demo649 |
Offline synthetic 6/49 |
taiwan_super |
威力彩 — official API |
taiwan_lotto649 |
大樂透 — official API |
Design rules
- No look-ahead — strategies only see draws strictly before the period.
- Change params after freezes → new experiment_id.
- Never backfill freezes after settle.
- Core path is deterministic, zero LLM required.
- Reports default descriptive — e-values are diagnostics, not discovery claims.
Development / release
pip install -e ".[dev]"
pytest
python -m build
# twine upload dist/* # requires PyPI token
Ethics
- Pure simulation / evaluation. No betting integration.
- Real-money wagering is out of scope and discouraged.
- Do not use this tool to market “predicted numbers.”
License
MIT — see LICENSE.
Lineage
Methodology DNA from private research (lotto-lab): preregistration, equal-cost nulls, hash ledgers, honesty guards. nullbench is the public product; lotto-lab remains a historical research archive.
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file nullbench-0.3.0.tar.gz.
File metadata
- Download URL: nullbench-0.3.0.tar.gz
- Upload date:
- Size: 30.2 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/7.0.0 CPython/3.11.9
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
7643d0693f6f62c26f79eadb93edd68f538a7c16b35e822da53c2c62fbb10269
|
|
| MD5 |
0f6772988c31caedf943b724db93e437
|
|
| BLAKE2b-256 |
d6a291c26e7fb751072dca8c3882cb43ec83817c334a2177cde3430bf29c2e51
|
File details
Details for the file nullbench-0.3.0-py3-none-any.whl.
File metadata
- Download URL: nullbench-0.3.0-py3-none-any.whl
- Upload date:
- Size: 37.8 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/7.0.0 CPython/3.11.9
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
1768edacf37258feae30194edd31e08351a26983da7993e1b0b2486cd202f8a1
|
|
| MD5 |
867a228aeb7f42dcbefbc32d2453b864
|
|
| BLAKE2b-256 |
39fe208d1e752ea43015a6acc8e49fe7271b37a40b721f0af17d9f932a7a8383
|