cd /news/artificial-intelligence/watch-a-game-ai-think-minimax-and-al… Β· home β€Ί topics β€Ί artificial-intelligence β€Ί article
[ARTICLE Β· art-103540] src=dev.to β†— pub= topic=artificial-intelligence verified=true sentiment=Β· neutral

Watch a Game AI Think: Minimax and Alpha-Beta, in a Browser Tab

A developer built an interactive browser-based tool that visualizes the minimax algorithm and alpha-beta pruning on a Tic-Tac-Toe board, allowing users to step through the search and see how pruning skips branches. The tool demonstrates that alpha-beta pruning reduces the full-depth search tree from 549,945 nodes to 36,528, a 93% cut, enabling a provably-unbeatable move to resolve in about 0.3 ms client-side. The developer also provides pseudocode and benchmarks, and notes that the same algorithm underlies AI opponents in games like Connect 4, Checkers, Othello, and Chess.

read3 min views2 publishedAug 19, 2026

Every "AI" opponent in a board game β€” Tic-Tac-Toe, Connect 4, Checkers, Othello, Chess β€” tends to run the same idea: search the game tree, assume the opponent plays their best, and pick the move with the best guaranteed outcome. That idea is minimax, and alpha-beta pruning is what makes it fast enough to run in a browser tab with no backend.

I built an interactive version where you can step through minimax on a real board and toggle alpha-beta on to watch it skip work: ** play with it here**. This post is the written companion.

Score a finished position from the AI's point of view: +1

if the AI wins, -1

if you win, 0

for a draw. Then walk the tree of possible futures. On the AI's turn it takes the max of its options; on your turn it assumes you take the min (the worst outcome for the AI). That alternation is the whole algorithm.

function minimax(node, isMax):
  if node is terminal:
    return score(node)          # +1 / -1 / 0
  if isMax:
    best = -inf
    for child in node.moves:    # AI's turn
      best = max(best, minimax(child, false))
    return best
  else:
    best = +inf
    for child in node.moves:    # your turn
      best = min(best, minimax(child, true))
    return best

Searching every branch is wasteful. Once you've found a reply that already refutes a move, you don't need to look at that move's other branches β€” they can't change the decision. Two running bounds carry that knowledge down the tree: alpha

(the best MAX can already guarantee) and beta

(the best MIN can already guarantee). When they cross, you stop.

function ab(node, alpha, beta, isMax):
  if node is terminal:
    return score(node)
  if isMax:
    best = -inf
    for child in node.moves:
      best = max(best, ab(child, alpha, beta, false))
      alpha = max(alpha, best)
      if beta <= alpha: break   # prune the rest
    return best
  else:
    best = +inf
    for child in node.moves:
      best = min(best, ab(child, alpha, beta, true))
      beta = min(beta, best)
      if beta <= alpha: break   # prune the rest
    return best

Pruning never changes the value at the root β€” only how many nodes you touch to find it. On a small Tic-Tac-Toe position with three empty squares, the full tree is 14 nodes and alpha-beta visits 10 of them. On the full-depth opening move it's dramatic: 549,945 nodes drop to 36,528 β€” a 93% cut β€” which is what lets a provably-unbeatable Tic-Tac-Toe move resolve in about 0.3 ms client-side. (The measured benchmarks are here.)

A search that looks d moves ahead visits roughly b^d

nodes, where b is the branching factor β€” how many moves you typically have. That number explodes:

Looking just 8 moves ahead in chess is on the order of 35^8 β‰ˆ 2.3 trillion positions. Alpha-beta β€” plus move ordering, transposition tables, quiescence and friends β€” is how a search reaches useful depth without visiting all of them. (Branching factors are approximate published averages, Γ  la Allis 1994, for illustration.)

Every opponent is this algorithm with a different board, a different way of scoring a position, and different tricks to search deeper without searching everything:

Game Board Branching (approx.) Search tricks
Tic-Tac-Toe 3Γ—3 ≀ 9 (~4) Minimax + alpha-beta, full depth on 3Γ—3
Connect 4 7Γ—6 ≀ 7 (~4) Bitboard negamax + alpha-beta + transposition table + iterative deepening
Checkers 8Γ—8 ~2.8 Iterative-deepening negamax + alpha-beta + capture quiescence
Othello 8Γ—8 ~10 Iterative-deepening negamax + alpha-beta + exact endgame solve
Chess 8Γ—8 ~35 Negamax + alpha-beta + null-move + quiescence + check extensions + move ordering

The pseudocode above is the shape. Here's a real, unminified engine that runs one of these opponents in the browser β€” iterative-deepening negamax with alpha-beta pruning and capture-aware quiescence, about 230 lines of vanilla JS: ** the checkers engine on GitHub Gist**.

Everything runs client-side, zero dependencies. If you'd rather watch the tree animate and prune than read about it, the interactive version is here: Watch a Game AI Think β†’

── more in #artificial-intelligence 4 stories Β· sorted by recency
── more on @tic-tac-toe 3 stories trending now
sponsored brought to you by zahid.host 4,200+ EU-deployed projects
reading about agents? ship yours in a single git push.

Run your AI side-project on zahid.host

EU-based hosting, git-push deploys, automatic HTTPS, no cold starts. Free tier with a custom domain β€” perfect for shipping the agent you just read about.

$git push zahid main
β†’ Live at https://your-agent.zahid.host βœ“
Get free account β†’ Pricing
from €0/mo Β· no card required
LIVE [news/watch-a-game-ai-thin…] indexed:0 read:3min 2026-08-19 Β· β€”