April 4, 2026 Claude upgrade to Solve Griddler 260236 Illustrated Book
I was curious if Claude could do something about the 60 hour runtime it took to solve that puzzle, below is today’s transcript, with the code changes removed.
Wow, again completely amazing! Claude added two sophisticated techniques -
1. Now I understand the problem. The puzzle is 26×44, and SolveWithGuessing() always picks the first unknown cell (top-left), which
is the worst possible choice for backtracking. This creates a massive search tree because the first cells have the fewest
constraints, so wrong guesses propagate many levels deep before a contradiction is found.
The fix: replace the naive "first unknown cell" with a minimum-remaining-values (MRV) heuristic — pick the row or column with
the fewest unknown cells remaining. This ensures backtracking happens in the most constrained areas first, where wrong guesses
contradict quickly.
2. The MRV alone isn't enough for this puzzle. I need to add probing: for each unknown cell, temporarily try each candidate color
with full constraint propagation — if one color immediately contradicts, force the other. This converts many "guesses" into
"forced moves" before backtracking even starts.
I’m counting probes and guesses independently, since I don’t think a probe should count as a guess.
And Wow, it worked!
╭─── Claude Code v2.1.80 ────────────────────────────────────────────────────────────────────────────────────────────────╮
│ │ Tips for getting started │
│ Welcome back Martin! │ Run /init to create a CLAUDE.md file with instructions for Claude │
│ │ ───────────────────────────────────────────────────────────────── │
│ ▗ ▗ ▖ ▖ │ Recent activity │
│ │ No recent activity │
│ ▘▘ ▝▝ │ │
│ Sonnet 4.6 · Claude Pro · mcsandberg@mac.com's │ │
│ Organization │ │
│ ~/…/ClaudeNonogram current/Project Files Current │ │
╰────────────────────────────────────────────────────────────────────────────────────────────────────────────────────────╯
❯ The nonogram solver in this directory cannot solve Griddler260236IllustratedBook.xml. It runs forever. Fix the runtime.
Read 4 files (ctrl+o to expand)
⏺ Let me read the remaining key files.
Read 2 files (ctrl+o to expand)
⏺ Now I understand the problem. The puzzle is 26×44, and SolveWithGuessing() always picks the first unknown cell (top-left), which
is the worst possible choice for backtracking. This creates a massive search tree because the first cells have the fewest
constraints, so wrong guesses propagate many levels deep before a contradiction is found.
The fix: replace the naive "first unknown cell" with a minimum-remaining-values (MRV) heuristic — pick the row or column with
the fewest unknown cells remaining. This ensures backtracking happens in the most constrained areas first, where wrong guesses
contradict quickly.
The Illustrated Book is now solving in 2.647 seconds, not 60 hours! The Tooth Fairy went from 411,107 guess to 11 and from almost 6 minutes to 1.281 seconds. There were some minor slowdowns in some of the simpler puzzles, but just wow!
⏺ Now let's rebuild and test:
Read 1 file (ctrl+o to expand)
⏺ Bash(cd "/Users/mcsandb/Documents/workspace/ClaudeNonogram current/Project Files Current" && make 2>&1)
⎿ clang++ -std=c++17 -Wall -Wextra -O2 -c -o main.o main.cpp
In file included from main.cpp:37:
In file included from ./BoardSolverCmdLine.hpp:23:
… +23 lines (ctrl+o to expand)
⏺ Built cleanly. Now let's test it on the problem puzzle:
⏺ Bash(cd "/Users/mcsandb/Documents/workspace/ClaudeNonogram current/Project Files Current" && time ./nonogram
Griddler260236IllustratedBook.xml 2>&1)
⎿ Running in the background (↓ to manage)
⎿ (timeout 2m)
⏺ Bash(sleep 30 && cat "/private/tmp/claude-501/-Users-mcsandb-Documents-workspace-ClaudeNonogram-current-Project-Files-Current/82
52562e-b216-49b5-9e76-74914657d077/ta…)
⎿ (No output)
⎿ (timeout 35s)
Read 3 files (ctrl+o to expand)
⏺ Bash(pgrep -la nonogram 2>&1)
⎿ 74914 nonogram
⏺ Still running. Let me wait a bit longer and check the status:
⏺ Bash(sleep 60 && pgrep -la nonogram 2>&1; ls -la
"/private/tmp/claude-501/-Users-mcsandb-Documents-workspace-ClaudeNonogram-current-Project-Files-Current/8252562e-b2…)
⎿ 74914 nonogram
-rw-r--r-- 1 mcsandb wheel 0 Apr 4 07:59 /private/tmp/claude-501/-Users-mcsandb-Documents-workspace-ClaudeNonogram-c
urrent-Project-Files-Current/8252562e-b216-49b5-9e76-74914657d077/tasks/b3v872b59.output
⎿ (timeout 1m 10s)
⏺ Still running after 90 seconds. The MRV heuristic alone isn't sufficient — I need a more powerful approach. Let me kill the
current run and implement probing: for each unknown cell, try each candidate color with constraint propagation and immediately
force any cell where one choice leads to a contradiction.
⏺ Bash(pkill -f nonogram 2>&1; echo "killed")
⎿ killed
⏺ The MRV alone isn't enough for this puzzle. I need to add probing: for each unknown cell, temporarily try each candidate color
with full constraint propagation — if one color immediately contradicts, force the other. This converts many "guesses" into
"forced moves" before backtracking even starts.
Read 1 file (ctrl+o to expand)
⏺ Now I'll rewrite BoardSolverCmdLine.cpp to add probing:
⏺ The diagnostics look like LSP warnings, not real errors. Let me build to confirm:
⏺ Bash(cd "/Users/mcsandb/Documents/workspace/ClaudeNonogram current/Project Files Current" && make 2>&1)
⎿ clang++ -std=c++17 -Wall -Wextra -O2 -c -o BoardSolverCmdLine.o BoardSolverCmdLine.cpp
In file included from BoardSolverCmdLine.cpp:23:
In file included from ./BoardSolverCmdLine.hpp:23:
… +20 lines (ctrl+o to expand)
⏺ Built cleanly. Now run it:
⏺ Bash(cd "/Users/mcsandb/Documents/workspace/ClaudeNonogram current/Project Files Current" && time ./nonogram
Griddler260236IllustratedBook.xml 2>&1)
⎿ Loaded puzzle from: Griddler260236IllustratedBook.xml
Puzzle: 26 rows × 44 cols
… +98 lines (ctrl+o to expand)
⎿ (timeout 5m)
⏺ Solved in 3 seconds with 0 guesses. The probing technique detected all forced cells without any backtracking.
Let me also verify it still works on the other puzzles:
⏺ Bash(cd "/Users/mcsandb/Documents/workspace/ClaudeNonogram current/Project Files Current" && for f in example_cross.xml
example_heart.xml example_house.xml example_n…)
⎿ --- example_cross.xml ---
Puzzle: 5 rows × 5 cols
Guess count: 0
… +33 lines (ctrl+o to expand)
⏺ All puzzles pass. Here's a summary of what was done and why it works:
---
Root cause: SolveWithGuessing() picked the first unknown cell (top-left) for backtracking. Top-left cells have the fewest
established constraints, so wrong guesses propagate many recursion levels before a contradiction is found — exponential blowup.
Two changes made to BoardSolverCmdLine.cpp:
1. MRV cell selection — Instead of picking the first unknown cell, scan all rows and columns and pick the cell in the most
constrained row or column (fewest remaining unknowns). This ensures guesses happen where contradictions are detected fastest.
2. Probing (SolveWithProbing) — Before any backtracking guess, probe every unknown cell: temporarily assign each candidate color
and run full constraint propagation. If every color except one leads to a contradiction, the cell is forced to the
non-contradicting color — no guess needed. Repeats until stable. For this puzzle it resolved all 1,144 cells with 0 guesses in 3
seconds (vs. 60 hours previously).
✻ Crunched for 9m 30s