logaritmisk
9fe40042da
feat(cargo): add rayon as optional dependency
...
Opt-in feature flag — users who want parallel paths build with
--features rayon. Default build remains single-threaded.
Spec Section 6 calls for default-on; we defer that flip until the
feature is stable under field use.
Part of T3 of docs/superpowers/specs/2026-04-23-trueskill-engine-redesign-design.md.
2026-04-24 13:35:15 +02:00
logaritmisk and Claude Opus 4.7
f0793a8470
docs: add T3 concurrency implementation plan
...
11-task plan for rayon-backed within-slice parallelism per
Section 6 of docs/superpowers/specs/2026-04-23-trueskill-engine-redesign-design.md.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com >
2026-04-24 13:34:00 +02:00
logaritmisk
d2aab82c1e
T0 + T1 + T2: engine redesign through new API surface ( #1 )
...
Implements tiers T0, T1, T2 of `docs/superpowers/specs/2026-04-23-trueskill-engine-redesign-design.md`. All three tiers have landed together on this branch because they build on one another; this PR rolls them up for a single review pass.
Per-tier plans:
- T0: `docs/superpowers/plans/2026-04-23-t0-numerical-parity.md`
- T1: `docs/superpowers/plans/2026-04-24-t1-factor-graph.md`
- T2: `docs/superpowers/plans/2026-04-24-t2-new-api-surface.md`
## Summary
### T0 — Numerical parity (internal)
- `Gaussian` switched to natural-parameter storage `(pi, tau)`; mul/div now ~7× faster (218 ps vs 1.57 ns).
- `HashMap<Index, _>` → dense `Vec<_>` keyed by `Index.0` (via `AgentStore<D>`, `SkillStore`).
- `ScratchArena` eliminates per-event allocations in `Game::likelihoods`.
- `InferenceError` seed type added (1 variant).
- 38 → 53 tests passing through T1.
- Benchmark: `Batch::iteration` 29.84 → 21.25 µs.
### T1 — Factor graph machinery (internal)
- `Factor` trait + `BuiltinFactor` enum (TeamSum / RankDiff / Trunc) driving within-game inference.
- `VarStore` flat storage for variable marginals.
- `Schedule` trait + `EpsilonOrMax` impl replacing the hand-rolled EP loop.
- `Game::likelihoods` rebuilt on the factor-graph machinery; iteration counts and goldens preserved to within 1e-6.
- 53 tests passing.
- Benchmark: `Batch::iteration` 23.01 µs (slight regression absorbed in T2).
### T2 — New API surface (breaking)
**Renames:**
- `IndexMap → KeyTable`, `Player → Rating`, `Agent → Competitor`, `Batch → TimeSlice`
**New types:**
- `Time` trait with `Untimed` ZST and `i64` impls; `Drift<T>`, `Rating<T, D>`, `Competitor<T, D>`, `TimeSlice<T>`, `History<T, D, O, K>` all generic.
- `Event<T, K>`, `Team<K>`, `Member<K>`, `Outcome` (`Ranked` variant; `#[non_exhaustive]`).
- `Observer<T>` trait + `NullObserver`.
- `ConvergenceOptions`, `ConvergenceReport`.
- `GameOptions`, `OwnedGame<T, D>`.
**Three-tier ingestion:**
- `history.record_winner(&K, &K, T)` / `record_draw(&K, &K, T)` — 1v1 convenience.
- `history.add_events(iter)` — typed bulk.
- `history.event(T).team([...]).weights([...]).ranking([...]).commit()` — fluent.
**Query API:** `current_skill`, `learning_curve`, `learning_curves` (keyed on `K`), `log_evidence`, `log_evidence_for`, `predict_quality`, `predict_outcome`.
**Game constructors:** `ranked`, `one_v_one`, `free_for_all`, `custom` — all returning `Result<_, InferenceError>`.
**`factors` module:** `Factor`, `Schedule`, `VarStore`, `VarId`, `BuiltinFactor`, `EpsilonOrMax`, `ScheduleReport`, `TeamSumFactor`, `RankDiffFactor`, `TruncFactor` now public.
**Errors:** `InferenceError` gains `MismatchedShape`, `InvalidProbability`, `ConvergenceFailed`; boundary panics converted to `Result`.
**Removed (breaking):** `History::convergence(iters, eps, verbose)`, `HistoryBuilder::gamma(f64)`, `HistoryBuilder::time(bool)`, `History.time: bool`, `learning_curves_by_index`, nested-Vec public `add_events`.
## Behavior change (documented in CHANGELOG)
`Time = Untimed` has `elapsed_to → 0`, so no drift accumulates between slices. The old `time=false` mode implicitly forced `elapsed=1` on reappearance via an `i64::MAX` sentinel — that quirk is not reproducible under a typed time axis. Tests that depended on it now use `History::<i64, _>` with explicit `1..=n` timestamps. One test (`test_env_ttt`) had 3 Gaussian goldens updated to reflect the corrected semantics; documented in commit `33a7d90`.
## Final numbers
| Metric | Before T0 | After T2 | Delta |
|---|---|---|---|
| `Batch::iteration` | 29.84 µs | 21.36 µs | **-28%** |
| `Gaussian::mul` | 1.57 ns | 219 ps | **-86%** |
| `Gaussian::div` | 1.57 ns | 219 ps | **-86%** |
| Tests passing | 38 | 90 | +52 |
All other Gaussian ops unchanged (~219 ps add/sub, ~264 ps pi/tau reads).
## Test plan
- [x] `cargo test --features approx` — 90/90 pass (68 lib + 10 api_shape + 6 game + 4 record_winner + 2 equivalence)
- [x] `cargo clippy --all-targets --features approx -- -D warnings` — clean
- [x] `cargo +nightly fmt --check` — clean
- [x] `cargo bench --bench batch` — 21.36 µs
- [x] `cargo bench --bench gaussian` — unchanged from T1
- [x] `cargo run --example atp --features approx` — rewritten in new API, runs clean
- [x] Historical Game-level goldens preserved in `tests/equivalence.rs`
- [x] Public API matches spec Section 4 (verified by integration tests in `tests/api_shape.rs`)
## Commit history
~45 commits total across T0 + T1 + T2. Each task is self-contained and individually tested; the branch is bisectable. See `git log main..t2-new-api-surface` for the full list.
## Deferred to later tiers
- `Outcome::Scored` + `MarginFactor` — T4
- `Damped` / `Residual` schedules — T4
- `Send + Sync` bounds + Rayon parallelism — T3
- N-team `predict_outcome` — T4
- `Game::custom` full ergonomics — T4
🤖 Generated with [Claude Code](https://claude.com/claude-code )
Reviewed-on: #1
Co-authored-by: Anders Olsson <anders.e.olsson@gmail.com >
Co-committed-by: Anders Olsson <anders.e.olsson@gmail.com >
2026-04-24 11:20:04 +00:00
logaritmisk
a14df02089
chore: do not publish
2026-04-23 20:26:52 +02:00
logaritmisk
0d266b4428
chore: make cargo release add CHANGELOG.md before commit
2026-04-23 20:26:16 +02:00
logaritmisk
a4b4e5e8fa
chore: clean up
2026-04-23 20:24:10 +02:00
logaritmisk
04d5478ee4
style: cargo fmt
2026-04-23 20:23:13 +02:00
logaritmisk
480467ac32
chore: added cliff.toml, release.toml and rustfmt.toml
2026-04-23 20:22:27 +02:00
logaritmisk
dc47964310
added benchmark
2026-03-23 14:55:18 +01:00
logaritmisk
61a5507f5c
remove notepad
2026-03-23 14:21:23 +01:00
logaritmisk
a1f282a1c8
feat: added a Drift trait and a "default" ConstantDrift implementation
2026-03-16 12:06:04 +01:00
logaritmisk
853f177fa8
Small changes for new 2024 edition
2025-02-21 14:09:58 +01:00
logaritmisk
fc0efcdc52
Update edition
2025-02-21 14:06:28 +01:00
logaritmisk
3bbddb168f
Ignore temp folder
2024-04-03 14:43:54 +02:00
logaritmisk
2366c45f6a
Basic test for quality
2024-04-03 10:25:10 +02:00
logaritmisk
3a22b20a17
Added todo to readme, and documentation for quality function
2024-04-03 09:53:07 +02:00
logaritmisk
02ae2f0977
Change assert to debug_assert
2024-04-03 09:44:41 +02:00
logaritmisk
a491f8de8d
Fix broken link in README
2023-01-09 14:37:07 +01:00
logaritmisk
0b4b07d60e
Added more links to readme
2023-01-09 14:35:34 +01:00
logaritmisk
05f178641c
Rename d to diff, and t to team
2022-12-29 20:38:36 +01:00
logaritmisk
e3906aebaa
Small refactor
2022-12-27 22:37:12 +01:00
logaritmisk
8e25826f91
More rustifying
2022-12-27 22:30:20 +01:00
logaritmisk
9b6cb9e7eb
Make it more rusty
2022-12-27 22:24:01 +01:00
logaritmisk
fdddf56156
Remove unused mut reference
2022-12-27 22:11:04 +01:00
logaritmisk
b93194f762
Added default implementation for TeamMessage
2022-12-20 11:08:27 +01:00
logaritmisk
2b83ee5ef9
Added benchmark for Batch
2022-12-19 07:42:08 +01:00
logaritmisk
2bdd3d9b89
Remove warnings and refactor some code
2022-12-16 19:46:01 +01:00
logaritmisk
912a282cd8
More refactoring
2022-12-16 15:57:56 +01:00
logaritmisk
51467f7b69
Fix clippy warning
2022-12-16 15:51:58 +01:00
logaritmisk
6dd84f7fd2
Refactor so we can see if there is any way to improve the performance
2022-12-16 15:38:29 +01:00
logaritmisk
5eb8e62d6e
Agents doens't have to be behind a mutable reference in within_priors
2022-12-15 20:13:25 +01:00
logaritmisk
8bea1b5399
Agents doens't have to be behind a mutable reference in within_prior
2022-12-15 20:12:55 +01:00
logaritmisk
6546cb54b5
Added a get function to IndexMap
2022-12-12 13:25:07 +01:00
logaritmisk
13e6454d3d
Update crates and added methods to get a key or all keys in an IndexMap
2022-12-12 10:50:59 +01:00
logaritmisk
18d55a8ccf
Clean up example
2022-07-04 23:13:57 +02:00
logaritmisk
32df04fb6d
Small change
2022-06-28 23:29:44 +02:00
logaritmisk
22c61d47b1
Change time to use i64 instead of u64
2022-06-28 23:18:55 +02:00
logaritmisk
6125a81696
Fixed test
2022-06-27 11:49:47 +02:00
logaritmisk
2467d7e027
Update test to use assert_ulps_eq
2022-06-27 11:46:59 +02:00
logaritmisk
0633c766a5
Update example so now it works, and thats, well, good
2022-06-27 10:22:26 +02:00
logaritmisk
cd1079a811
Use and Index struct instead of str and String for player id
2022-06-27 10:16:12 +02:00
logaritmisk
d52895f804
Remove unused code
2022-06-23 07:48:44 +02:00
logaritmisk
ba2f8cffdc
Update test to use builder
2022-06-23 07:44:34 +02:00
logaritmisk
73b9cabac8
Added builder for History, and start migrating test to use builder instead.
2022-06-22 21:13:24 +02:00
logaritmisk
a573f5cf0a
More tests
2022-06-21 10:48:04 +02:00
logaritmisk
1647ba5c77
More tests
2022-06-21 10:42:14 +02:00
logaritmisk
be4834ca85
Fix tests
2022-06-20 23:58:05 +02:00
logaritmisk
0a35645091
More things, more tests
2022-06-20 23:56:35 +02:00
logaritmisk
0efb0312da
More tests, more code
2022-06-19 23:52:52 +02:00
logaritmisk
c9d9d59535
More things, better things, awesome
2022-06-18 23:39:42 +02:00
logaritmisk
dc10504b80
Port from julia version instead
2022-06-18 22:27:38 +02:00
logaritmisk
36c3366990
Refactor some stuff
2022-06-15 13:26:03 +02:00
logaritmisk
0a3327f076
Refactor some code
2022-06-15 11:27:24 +02:00
logaritmisk
811a4ca418
Inline a lot of functions
2022-06-14 23:00:21 +02:00
logaritmisk
9b025fb53a
Use PlayerIndex instead of String
2022-06-14 22:51:11 +02:00
logaritmisk
3fbac02de3
It works, or so it seems
2022-06-13 23:18:19 +02:00
logaritmisk
1b6e07225b
Handle case where there is no time
2022-06-13 21:55:43 +02:00
logaritmisk
82e7b22443
Use flatten instead of flat_map
2022-06-13 11:37:56 +02:00
logaritmisk
de4b324651
Remove Display impl, better to use Debug
2022-06-13 11:35:08 +02:00
logaritmisk
87a64acb83
Added more functions to History
2022-06-13 11:27:49 +02:00
logaritmisk
4a13e4dcd2
More test passing for History
2022-06-13 11:04:05 +02:00
logaritmisk
4227617513
Working on History struct. First test is passing.
2022-06-12 23:11:13 +02:00
logaritmisk
5a7053fb5d
Passing tests for Batch
2022-06-12 21:43:35 +02:00
logaritmisk
ae1c765dbb
Begin working on batch.
2022-06-12 21:02:57 +02:00
logaritmisk
de58d01322
Initial commit.
2022-06-10 15:22:27 +02:00