Approaches in this family

12 approaches, featured pages first. The label above each title is the technique the approach uses; the same pages appear under that technique on the approaches index.

Instruments in this directory

These play no game of their own: engines run the games and diagnostics measure them. They are listed here because they live alongside the approaches above; the full sets are under Engines and Diagnostics.

On this page

Instead of hand-writing what makes a Drop7 board good, learn it — from small patches of cells, and from millions of games the program plays against itself.

This is the family that tried to replace human judgement with data. It contains the repository's first learned policy and, after it, a long line of reinforcement-learning variants: temporal-difference updates, Q-learning, policy gradients, actor-critic, and expert iteration. Through August 2026 none of them produced a policy stronger than the hand-tuned fair depth-4 search that the project uses as its reference. On 2026-09-05 the row-and-column lookup tables, trained from billions of engine moves and placed as the leaf of the depth-3 fair search, beat that reference on 256 held-out games at screen tier, and on 2026-09-06 the same frozen tables did it again on 512 games from a second block nothing had read; a six-times-wider evaluator trained until its validation margin stopped rising passed the same gate and was no better than the first. Later that day the same tables played one ply deeper, as the leaf of the depth-4 search, and gained about as much from the fourth ply as the hand-written leaf does, keeping their whole margin over it. For how this family compares with the other three ways of learning tried here, see four ways a program can learn Drop7.

What an n-tuple network is

Pick a small window of cells — four in a row, four in a column, or a 2×2 block. Read the contents of that window as an address, and look the address up in a table of learned numbers. Do that for every window on the board, add all the numbers together, and the sum is the network's opinion of the position.

a row window333173144 cells across · 28 of thempattern 0788→ one learned numbera column window333173144 cells down · 28 of thempattern 3333→ one learned numbera 2×2 block333173144 neighbouring cells · 36 of thempattern 1091→ one learned number92 windows, one additionEvery window reads four cells andturns them into a four-digit code.The code, the rise phase and thenext disc select one slot in a bigtable of learned numbers. Add the92 numbers up and that sum is theboard's score. Windows that differonly by where they sit share atable, so 92 windows use 17tables.Nothing here is a neural network: it is alookup and a sum, which is why it is fastenough to sit at a search leaf.Board from figure seed 0x5eed031b; the window positions and codes are read off itdirectly. Table layout as implemented in src/core/native/ntuple.hpp.
Three of the 92 windows on one real position. Each turns four cells into a code, the code selects one learned number, and the 92 numbers are added together.

The position in the figure is this repository's TypeScript rules engine playing a game, not a drawing. The native implementation in src/core/native/ntuple.hpp uses 92 windows — 28 horizontal, 28 vertical, and 36 square — sharing 17 underlying tables.

Nothing in that machinery knows Drop7's rules. It only knows which small patterns of cells tended to precede good games. That is the appeal: a table lookup is far cheaper than a neural network, and the tables can hold millions of distinct local shapes. In 2048, the game this idea was borrowed from, tables like these are enough to play the game very well.

And "learning from play"

No human labels the boards. The program plays a game, sees what happened, and nudges the weights it looked up toward the outcome. Play enough games and the weights are supposed to converge on something that ranks positions correctly. The variants in this family differ mostly in what they nudge toward: the score that followed, the number of moves survived, the value of the best next move, or the advantage of one column over another.

How it works, step by step

  1. Read the position. Every program in this family is a public-information policy: the board, the visible next disc, and the rise clock. No seed, no hidden gray value, no score, no move number.
  2. Evaluate. Look up all 92 windows (plus, in some variants, extra features for board height, disc counts, and rise phase) and add the weights.
  3. Choose a column. Simulate dropping the visible disc in each legal column, evaluate the resulting board — its afterstate, and take the best. Some variants put a shallow expectimax search on top and use the network only at the leaves.
  4. Learn. After the move, compare the prediction with what actually followed, and adjust every weight that contributed. Repeat for hundreds of thousands of games, or in the later experiments tens of millions of moves.
  5. Freeze and test. Freeze the weights, then play a fixed cohort of complete games against a reference policy on the same seeds.

What happened

The first version worked well enough to be interesting and was never beaten by anything that came after it. Adding a two-move look-ahead on top of the learned values lifted it from about 182,000 to about 232,000 points per game on a fixed 64-game development probe. The improvement was real and measured on paired games. But by the time the hand-tuned depth-4 search was properly measured, that search was scoring around 308,000 on its own 64-game reference cohort, and the learned policies were not close.

Every reinforcement-learning variant that followed landed lower. The clearest example: a phase-aware n-tuple trained on 50 million moves scored 181,733 points per game, and the two-rise-deep search built on top of it scored less, at 113,644. A Rainbow-style Q-learner beat random play convincingly at 250,000 training steps, then lost decisively to a plain one-move fair search at one million. A PyTorch policy-gradient pipeline, an actor-critic with explicit safety constraints, and eight rounds of expert iteration all finished between roughly 116,000 and 176,000 points per game, and a second, C++ policy-gradient attempt never got past trying to imitate a one-move search.

ApproachRecorded mean scoreMean movesCohortSource
Row and column lookup tables as the depth-4 leaf, the same frozen tables one ply deeper516,155148.75512 never-read paired development games on a fourth block, screen tierRS-20260906T171746Z-1623f833
Row and column lookup tables as the depth-3 leaf484,577140.21256 never-read paired development games, screen tierRS-20260905T215332Z-95d18a5a
Row and column lookup tables as the depth-3 leaf, replication of the same frozen tables487,066140.83512 never-read paired development games on a second block, screen tierRS-20260906T040113Z-6ba93171
Wider lookup tables (2x4 and 4x2 windows added) as the depth-3 leaf481,869139.39the same 512 games, screen tierRS-20260906T040113Z-6ba93171
Learned value plus depth-2 search232,107.15670.76664-game development probeledger
Optimistic phase n-tuple, direct play181,733.42256.35964-game burned gateledger
Primal-dual actor-critic175,83455.006512-game calibrationledger
PyTorch PPO, best candidate142,677.78145.65664-game development cohortledger
Regenerative expert iteration, round 8116,59838.046training roll-insledger
Optimistic phase n-tuple, two-rise search113,643.96937.37564-game burned gateledger
Fair depth-4 reference, for comparison308,295.57890.03164 gamesledger
Technical record

Every figure above is ledger-recorded in the experiment history; the family's status rows are in the experiment index under "N-tuple and reinforcement learning". Five of the family's sources (bellman-ntuple.cpp, flow-curriculum-rainbow.cpp, manifold-gail-development.cpp, manifold-gail-scaled.cpp, curriculum-option-ppo.cpp) carry a task-record only verdict: an index row exists, but no ledger protocol, artifact hash, or per-game data was retained, so those rejections cannot be re-derived.

The 308,295.578 / 90.031 reference is itself weaker evidence than it looks. It appears once in the ledger, as an internal bootstrap comparator inside the regenerative expert-iteration run; the identity of its 64 seeds, its dispersion, and its censoring statistics were not retained. This is recorded as finding H2 in docs/exploratory/audit-03-claim-arithmetic.md.

The scoring-mode assignments quoted on the individual pages come from the same audit, which classifies every recorded (score, moves, n) triple in the ledger by which level bonus is arithmetically consistent with it. Where the ledger states the mode, the pages say so; where the audit infers it, the pages say that too.

No approach in this family opened a protected or final cohort. Several left their later gameplay ranges unopened, which is recorded per experiment.

What this taught us, and what is still open

The representation was never the bottleneck. The strongest single lesson is negative and repeated: more capacity, more training, and better-conditioned updates did not fix these policies. A shared-parameter bug in the temporal-difference update was found and corrected, and the corrected policy still failed. Conditioning the tables on the rise clock closed under 3% of the gap to the reference search. Training a Q-function to 50 million moves produced a policy no better than one trained far less.

The bottleneck was which moves the data covered. Almost every program here learned from the move it actually played, then, at play time, was asked to rank up to seven columns it had never been scored on. That is the sibling trap. The expert-iteration run showed that even regenerating fresh on-policy games every round did not remove it, because the targets still described only the played action.

Search on top of a weak value can hurt. The two-rise rollout over the optimistic phase n-tuple was strictly worse than just playing the network's first choice. A deeper look-ahead magnifies whatever the leaf evaluator gets wrong, and this one was wrong.

What is still open. Nobody has trained an n-tuple on data that scores every legal column at each position under shared imagined futures. The sibling-ranking and scale-out pages describe what that would take. Until it is tried, this family's negative results rule out the objectives that were tested, not pattern learning itself.