PLAYER 0 // MOVE 01 // [6, 1]

PROGRESS: +6 CELLS · VALUE +0.42

01
06

THE BOARD WAITS

Self-play RL · local inference · runs in browser

Meet the
player inside
the board.

AlphaLudo is a 587,306-parameter graph transformer that learned Ludo entirely through self-play. Small enough to run right in this tab with no server and no tracking. It plays a sharp, patient game.

Explore the research

Scroll to take a turn

01 — CHANCE ENTERS

The die makes
the question.
Not the answer.

Every turn begins with uncertainty. At 1/6 probability per face, luck dictates what you roll—but intelligence decides how to extract maximum value from that roll.

DETERMINISTIC GRAPH POLICY · STOCHASTIC DICE ENGINE

02 — FOLLOW THE MOVE

One token.
One moment.
Many futures.

The camera dives into street level as Player 0 advances. Under the surface, attention layers are actively comparing candidate moves across all 225 board cells: blocking, escaping, and securing safe squares.

See how the model works

03 — THE GRAPH READS THE BOARD

225 cells as nodes.
Attention along
the routes.

Instead of scanning the board like a flat 2D image, AlphaLudo treats the entire board as an interconnected graph. Information flows along the real movement routes, evaluating threat and safety at 587K parameters.

04 — THE BOARD TURNS

The next
move is yours.

A 2.8 MB download. Instant local WebAssembly inference. No backend, no account, no tracking. Sit across the board from a neural network and see if you can beat it.

587K params 2.8MB local WASM 52.7% vs champion ~85% luck ceiling

Documentary

The AlphaLudo Museum

Play AlphaLudo — your match against the neural network

🎮

Human side

No games played yet

Tokens Home 0 / 4
Waiting…

Your side

Tokens

    Timeline

    Game Log

    50%
    50%

    AI's predicted winner

      Click to roll

      or press Space

        🤖

        Model side

        AlphaLudo AI

        Loading...

        Tokens Home 0 / 4
        Waiting…
        AI's Predicted Win Chance
        50% AI vs You 50%
        Move probabilities (last decision)

        Behind the model

        How a small network got strong.

        From a naive baseline that couldn't tell its own four tokens apart, to a graph transformer a fifth the size that beats every earlier version of itself — and the proof that what's left between it and perfection is mostly the dice. The short tour, including what didn't work.

        From V1 to V15.2

        The architecture timeline

        1. Oct 2025 · The first try The naive baseline

          The model saw the board as eight stacked black-and-white maps — but it couldn't tell its own four tokens apart. They all collapsed into one blob, so the AI was guessing which piece to move. It lost a lot.

        2. Dec 2025 · Hand-holding Engineered features

          We started feeding the network "tactical hints" we computed by hand — danger maps, capture opportunities, safe landing squares. It got better, but plateaued at 73–77% wins against scripted opponents and stopped improving.

        3. Mar 2026 · Attention Breaking through the plateau

          Added a "token attention" layer — letting the network reason about its four tokens as separate entities, with awareness of how often each had been ignored. First model to consistently win >80% against scripted opponents.

        4. Apr 2026 · Previous Less is more (V13.2)

          Stripped most of the hand-engineered features back out and gave the network mostly raw board positions plus 3 static board hints (safe cells, home stretches). Beat every earlier version of itself by a small but statistically real edge. Held this site for two weeks as the strongest version — until V13.5.

        5. May 2026 · Symmetry The four tokens are interchangeable (V13.5)

          Every encoder so far had given each of the four own tokens its own input channel — forcing the network to learn from scratch that the rules treat them identically. V13.5 collapses them into a single count-per-cell channel and re-routes the model's "which token to move" output through a rank-indexed gather. Same parameter budget, same training pipeline, same opponent pool — 51.7% wins over 3,000 games vs V13.2, and 90.4% vs the competing V13.4 temporal experiment. The first version to clear the V13-class plateau, and this site's previous champion.

        6. June 2026 · Current The board is a graph (V15.2)

          Instead of a CNN scanning the board like an image, V15.2 treats the 225 board cells as nodes in a graph transformer — each cell carries a three-number summary, attention layers pass information along the routes, and the policy picks the cell to move from. No history frames, no hand-engineered hints, no per-token channels: one frame in, one decision out. At 587K parameters — a fifth of V13.5 — it beats V13.5 52.7% over 2,000 games and the strongest V13.6 experiment 52.5%, using the reward pipeline that finally worked: win/loss only, spread over the game by GAE. This is the model you play against.

        7. Aug 2026 · Tried, and it backfired Two properties per connection (V16)

          The last idea on this list is a failure, and an instructive one. V16 gave every connection a second property, routed so a tactical objective could shape it without disturbing the weights that play the game. Mechanically it worked perfectly: danger became almost perfectly readable from the model's summary node — 0.87 → 0.999 — and removing the new property dropped it to 0.77, below the champion, while two control concepts didn't budge. But play got worse: 84.7% → 76.8% over 2,000 games. Separating the gradients did not separate the function. V15.2 still holds the site. Read the full result →

        End-to-end

        How AlphaLudo learns

        1. 01 Bootstrap

          Generate millions of practice games between scripted bots — heuristic, aggressive, defensive, expert. The network learns by watching them play.

        2. 02 Imitate the best teacher

          The new student network is trained to copy the previous best AlphaLudo's decisions. By the end of this stage it already plays as well as the teacher.

        3. 03 Self-play reinforcement

          The student plays thousands of games against itself and various opponents, gradually adjusting its strategy to win more. Once it's consistently strong, we add the previous AlphaLudo versions back in as sparring partners.

        4. 04 Take the training wheels off

          For most of the project we shaped behaviour with hand-tuned reward penalties — don't ignore the laggard token, don't walk into capture range. The final pipeline drops all of it: the only reward is winning or losing, and GAE (generalized advantage estimation) spreads that single signal fairly across every move of the game. The bad habits disappeared on their own — they were artifacts of the crutches, not the game.

        5. 05 The honest test

          Win rate against scripted bots saturates in the mid-80s, so it stops being useful as a measure. We compare versions directly — thousands of games, head to head, same dice for both sides where possible. That's the only test that distinguishes the strongest models.

        From the journal

        Five lessons we won't unlearn

        Failed

        "Mathematically clean" rewards can be poison

        An early reward-shaping scheme looked elegant on paper but quietly subtracted a tiny amount of reward every turn. Over a 150-move game it added up to about a fifth of a "loss" — the model became convinced every game was unwinnable. Took 155,000 games to figure out what was happening.

        In long games, even tiny systematic biases compound. Always check what the reward looks like end-to-end.

        Revised

        Loud rewards helped — until they didn't

        Mid-project, quieting the intermediate rewards cratered win rate from 67% to 33%: the dice noise drowned the learning signal, and loud hand-shaped rewards looked like the answer. The real answer arrived later — drop the shaping entirely and let GAE spread the pure win/loss signal across the game. Same architecture, cleaner rewards, stronger play. The shaping was scaffolding, not structure.

        Shaped rewards are a way to survive dice noise, not the way to beat it. Credit assignment done properly (GAE over terminal-only reward) replaced every crutch we'd built.

        Worked

        The encoder was the bottleneck — not the model

        For most of the project we believed the 80–83% plateau was about the opponent pool. Three architectural designs (CNN + attention, pure CNN, a temporal transformer over 8-turn history) all sat at the same ceiling. Then V13.5 broke it — by attacking the input instead of the model: collapsing the four own-token channels into a single permutation-symmetric count view. V15.2 finished the thought — erase token identity entirely, describe each board cell with three numbers, and let attention do the rest. Every step that helped made the input more honest about the game's symmetry, not the model bigger.

        When three different architectures hit the same ceiling, the bottleneck is upstream of the architecture. We were giving the model an asymmetric view of a symmetric game.

        Proven

        Know when the ceiling is the dice

        The strongest models all settle around 85% against the scripted pool — so is that a skill ceiling or a luck ceiling? We tested it six independent ways: head-to-head between champions lands at coin-flip, adding 2-ply search at play time adds nothing, an adversary trained specifically to exploit the model manages 45%, a per-decision "equity loss" audit measures ≈0 regret against rollout ground truth, retraining with richer value targets ties, and human play-testing finds no repeatable pattern to exploit. Six arrows, one answer.

        In a dice game, a single game is mostly luck between near-optimal players. ~85% against the pool is the ceiling — the remaining 15% is variance, not weakness. Knowing when to stop is a result too.

        Newest

        Separating gradients doesn't separate function

        V16's whole premise was that two objectives could share a network without interfering, if each owned its own property on every connection and the gradients were routed cleanly between them. The routing was exact. The interference happened anyway — because one property still scales the other in the forward pass, so the two objectives compose multiplicatively even when their gradients never touch. Worse, the added property settled on precisely the weights the primary objective already depended on.

        A clean split in the backward pass is not a clean split in the network. For a second objective to be genuinely independent it has to be additive and orthogonal, not multiplicative and aligned. The numbers →

        Mechanistic interpretability

        Looking inside the model

        A sister project — a battery of probing experiments asking: what has the network actually learned? Built around the V13.x generation (five experiments, ~600–2,000 board states each), plus a controlled representation study run on the way to V15. Findings from this work directly shaped the encoders that followed.

        V13.5 · CHANNEL ABLATION RE-RUN

        The rank-routing is mechanically real

        Re-ran channel-ablation on V13.5 with 600 stratified states. The four "Tok→Rank" planes (the constant channels that route the rank-indexed output back to which token to actually move) are the dominant channels globally — Policy KL 0.60–0.76, higher than any other channel. In late-game the pattern shifts: own-token-count and the leader-token rank mask take over (KL 0.68–1.01), and safe-zone reasoning becomes critical for landing.

        The symmetric-encoder bet isn't just a numerical tie — it's an active mechanism the model uses on almost every decision. Phase-specialized policy: rank routing in opening, leader-token + safe-zone reasoning in endgame. The kind of structure V13.5 was designed to expose.

        V13.2 · CHANNEL ABLATION (original finding)

        The model leans on Token 3 more than the others

        Zero out one input channel at a time and measure how much the policy distribution shifts (KL divergence). On 600 stratified states with the multi-legal filter — i.e. only states where the network actually has a choice — Token 3's channel comes out at KL ≈ 0.85, more than 2× the next-highest token (T1 at 0.38).

        This was a surprise. The four tokens are interchangeable under the rules, so a symmetric encoder shouldn't single one out. The asymmetry was real and pointed at the input encoding itself — directly motivating V13.5's token-symmetric collapse, and ultimately V15.2's identity-free encoding.

        EXPERIMENT 3 · LINEAR PROBES

        What concepts the 128-dim feature vector encodes

        Train a logistic regression on the network's GAP features to decode hand-labelled concepts. Numbers are balanced accuracy on a held-out test set; baseline is the chance-level for that label distribution.

        • Game phase (early / mid / late)79%vs 33% baseline
        • Number of tokens out of base75%vs 33%
        • Will I win this game?73%vs 51%
        • Closest token to home35%vs 38% — not encoded
        • Home-stretch token count48%vs 73% — anti-encoded

        Strategic context (phase, lead, who's winning) lives clearly in the features. Per-token spatial concepts (which token is closest, how many are nearly home) don't — the network appears to re-derive these from the input each forward pass rather than maintaining them in the residual stream.

        EXPERIMENT 2 · DICE SENSITIVITY

        It's a reactive lookup, not a planner

        Hold the board fixed, sweep the dice channel through 1–6, see how the chosen token shifts. ~78% of states flip the preferred token when the dice value changes — and the JS divergence between roll-1 and roll-6 distributions is large.

        The network behaves as f(board, dice) → action, with dice values acting as broadcast modifiers rather than something integrated into a temporal plan. Same pattern across V6, V10, and now V13.2 — annealed PPO didn't change it. Tree-search-style planning would look very different.

        EXPERIMENTS 4–5 · CAPACITY USE

        Every channel is alive, but few do real work

        Layer-knockout (skip individual ResBlocks) and channel-activation (which of the 160 channels actually fire) ran together. Result: 0 globally dead channels at any threshold — every channel produces some activation. But channel-importance is heavily long-tailed: a handful of channels dominate the policy gradient, and the bulk are weakly redundant.

        The model isn't wasting parameters in the obvious sense (no dead neurons), but it's also not packing them densely. There's likely room to compress 10× without losing strength — a prediction V15.2 later confirmed by matching the champions at a fifth of the parameters.

        CONTROLLED A/B · REPRESENTATION

        Do per-token ID embeddings scramble what the net knows?

        A one-variable experiment: train two identical networks on identical data, one with a learned per-token identity embedding, one without — then linearly decode each token's position and danger from the internal features. Across six seeded pairs, the paired difference in decodability was 0.00 ± 0.01: the identity embedding, though actively used by the network, scrambles nothing. A positive control (forcing a network to store properties in such an embedding) showed the probe detects real scrambling when it exists (r drops to ~0.2).

        Free per-object codes only garble a network's knowledge when they store the property; as pure identity tags they're harmless. In practice every strong AlphaLudo dropped them anyway — computing properties from the board beat memorising them, every time.

        Exhibit · the chronograph column

        Fifteen generations, one column

        Each ring is an era. Scrub through them and watch what the model could — and could not — perceive.

        Select an era to light its ring.

        Exhibit · the pipeline cascade

        How a generation is made

        Five stages, running downhill. Selecting one lights it and everything feeding it.

        Select a stage to light the cascade.

        Exhibit · the cortex obelisk

        Read the board the way it does

        Pick a finding. The routes it describes light up on the board beside you.

        Select a study to light the board.

        What you are looking at: these are illustrations of each finding, not dumps of the model's attention weights. The real policy scores all 225 cells at once and its attention is high-dimensional; what lights up here is the route structure the finding is about, drawn on the board where it applies. Every study cites the run it comes from.

        Exhibit · the scoreboard wall

        The tournament, in full

        Round-robin, 2,000 games per pair, mirrored orientations. Win rate of each row against each column.

        Head-to-head win rates between model generations
        vs →V13.5V13.6V15.2MCTS

        MCTS here is the opponent, not the model — the strongest scripted player in the pool, which V15.2 beats 68.3% of the time. The shipped network runs no search at all: adding 2-ply lookahead at play time was measured at 49.8%, a tie.

        Exhibit · August 2026 · newest

        Representation and behaviour came apart

        V16 gave each connection a second property, routed so one objective could carry tactics without disturbing the other. It worked. The model got worse.

        Concept decodability before and after the two-property change
        Decodable from the summary nodeChampionV16V16 with the property removed

        The result

        Exhibit · the maintenance hatch

        Three bugs that cost real time

        None of these are about machine learning. All of them changed results.

        The scoreboard

        What's shipped, what didn't work, what's settled

        Every line here comes from a logged, reproducible run in the training journal.

        DEPLOYED · this site

        V15.2 · single-frame graph transformer

        225 board cells as graph nodes, three numbers per cell, attention along the routes, a 225-way "move from this cell" policy. Trained with the pipeline that finally worked everywhere: terminal-only reward spread by GAE. 587K parameters — a fifth of the model it replaced.

        Head-to-head results: 52.7% vs V13.5 over 2,000 games (this site's previous champion) · 52.5% vs V13.6, the strongest CNN experiment · 68.3% vs an MCTS baseline. Smallest and strongest model of the project, in the same breath.

        DIDN'T WORK · resolved

        History, search, and exploiters — all null at the top

        Three separate bets on "there must be more skill to extract" each came back empty. A temporal transformer over 8-turn history lost 9.6% of head-to-head games against the stateless V13.5 — history adds no signal a single frame doesn't carry. Bolting 2-ply expectimax search onto the deployed model at play time: 49.8%, a tie — the search can't out-rank the policy it reads. Training an adversary against the frozen champion: 45.4% — it found nothing to exploit.

        SETTLED · six ways

        The ~85% pool ceiling is variance, not weakness

        Champion-vs-champion head-to-heads land at coin-flip. Play-time search adds nothing. A dedicated exploiter fails. A per-decision equity audit against double-sampled rollouts measures ≈0 lost win-probability per move. Richer value targets tie. Human play-testing finds no repeatable flaw. Two-player Ludo, for this project, is closed — the residual is dice.

        PARKED · compute-bound

        Full MCTS / AlphaZero from random init

        A stripped-down variant — shallow expectimax + the current network as leaf evaluator, distilled into a fresh student — lost 89/10 to its teacher. Not a refutation of AlphaZero; a sign that 2-ply search over the network we're trying to beat doesn't generate strong-enough targets. The full recipe (deep MCTS, millions of games from random init) stays parked until there's a real compute budget — though with the variance ceiling now proven, the expected payoff is small.

        DIDN'T WORK · Aug 2026

        V16 · two properties per connection

        Give every connection a second property and route the gradients so a tactical objective can shape it without touching the weights that play the game. The mechanism did exactly what it was built to do: danger became near-perfectly decodable from the summary node (0.8739 → 0.9985), and zeroing the new property dropped it to 0.7666 — below the champion — while both control concepts stayed put.

        Play went the other way: 84.7% → 76.8% over 2,000 games. Fixing the representation made the model worse, which also falsifies the earlier hypothesis that the champion was limited by poor capture-risk encoding. V15.2 keeps the site. Full result, including the circularity caveat →

        NOT ESTABLISHED · pre-registered

        Whether it was the routing or the objective

        V16 changed two things at once — a two-property architecture and an auxiliary objective — so its failure does not yet tell us which one hurt. The control arm that would separate them is written and has not been run. Recorded here rather than left as an implied conclusion.

        Want to see the model in action?

        ▶ Play AlphaLudo

        Inspirations & dead ends

        The lineage.

        AlphaLudo borrowed liberally and parked one idea for compute reasons. Here's the full reading list, in chronological order.

        Inspiration · 2016 · DeepMind

        AlphaGo

        The whole project started here. AlphaLudo borrows the AlphaGo recipe almost wholesale — a network that predicts both the best move and how likely you are to win, trained first by imitating a strong teacher and then by playing millions of games against itself.

        If you've never seen the documentary, watch it. It's still the best one-hour explanation of why this whole field exists.

        1992 IBM · Tesauro

        TD-Gammon

        The original "neural net plays a dice game at world-class level" result, written when most of the modern field didn't exist yet. Thirty years later, AlphaLudo rediscovered Tesauro's central lesson the hard way: in dice games, the small rewards along the way matter more than the final win/loss signal. Scale them down too far and learning collapses.

        Read on Wikipedia →
        2017 Tried, then rejected

        AlphaZero

        AlphaZero's full recipe — train from a random network, generate millions of self-play games with deep MCTS search at every move, distill the search-improved policy back into the network — is the obvious next step after AlphaGo. We didn't run that loop. The blocker isn't the idea; it's the compute. Generating millions of search-augmented games on a single GPU is months of wall-clock time we don't have.

        We did try a stripped-down variant: shallow expectimax search using our best existing network as the leaf evaluator, distilled into a fresh student. That student lost 89 / 10 to its teacher — not a refutation of AlphaZero, but a sign that 2-ply search over the same network we're trying to beat doesn't generate strong-enough targets. With a stronger leaf evaluator (or a real compute budget for full self-play search), it's still on the table.

        Original paper →
        2017 Zaheer et al.

        DeepSets

        A 2017 idea that lets a neural network reason about a "set" of things — like the four tokens you control — without caring what order they're in. We used this for one experiment in AlphaLudo, building a much smaller network with no convolutional layers at all. It hit the same ceiling as the bigger models, which is what convinced us the model itself wasn't the limit.

        arXiv:1703.06114 →
        2017 Schulman et al.

        PPO

        The reinforcement-learning algorithm doing the heavy lifting in every AlphaLudo run. PPO is the workhorse of modern RL — boring, reliable, well-understood. We didn't try to be clever with the optimiser; the interesting part of AlphaLudo is what we feed into it, not how we update the weights.

        arXiv:1707.06347 →

        Project meta

        About AlphaLudo.

        A long-running side project on what it actually takes to learn Ludo from self-play. Built end-to-end — engine, training, mechanistic interpretability, and this site.

        Runtime

        How this page works

        • Game engine: hand-written C++ compiled to WebAssembly via Emscripten
        • Inference: ONNX Runtime Web (single-threaded WASM build)
        • Frontend: vanilla ES modules, no framework, no bundler in dev
        • Hosting: Cloudflare Pages (static), no server, no telemetry
        • Total payload: ~16 MB, dominated by the ONNX runtime — the model itself is just 2.8 MB (the previous build was ~50 MB)

        Model

        What the AI is

        • 587,306 parameters, all running locally on your machine
        • Graph transformer — 4 attention layers × 128 dims over the 225 board cells as nodes, plus one summary node for the value head
        • Sees a single frame: three numbers per board cell. No history, no dice channel tricks, no hand-engineered hints, no per-token channels
        • Two outputs: a 225-way "move the token on this cell" policy, and an estimate of its own chance of winning
        • Trained by imitation on 1.5M teacher games, then PPO self-play with a terminal-only reward spread across the game by GAE

        By the numbers

        The whole project, summarised

        25M+games played across bootstrap, imitation, and self-play
        62logged experiments in the training journal
        9model generations, V1 through V15
        10generations of input encoder
        6independent tests converging on the variance ceiling
        5major dead ends documented, not hidden

        Privacy

        What we collect

        Nothing. There is no backend. Your moves never leave your browser. The page loads Google Fonts and (on the Lineage page) one YouTube embed via youtube-nocookie.com; that's the only third-party traffic. No analytics, no cookies, no telemetry.

        Ready?

        Play the model

        The network is already loaded. Pick up the dice.

        ▶ Play AlphaLudo