Books · The Fiddler: Solutions
Chapter 8
Can You Hop Around the Chessboard?
A frog is hopping around a chessboard, always from the centre of one square to the centre of another. Each square has side length , but the board is -by- for some large whole number . Every jump the frog makes must be the same distance . The frog wants to make four jumps such that: after the fourth jump it has returned to its starting square; it visits four distinct squares along the way, counting the starting square; the path is not a square loop; and the frog is never on a square that is a bishop’s move or a rook’s move away from its starting square. What is the smallest jumping distance for which this is possible?
The Fiddler, Zach Wissner-Gross, May 1, 2026(original post)
Solution
Place the starting square at the origin, so every square centre is a lattice point. Each jump is a vector with , and the four jumps must sum to zero. A four-jump closed loop through four distinct squares needs at least two genuinely different jump vectors of the same length; the simplest shape is a parallelogram . The constraints act on the visited squares , , : none may have a zero coordinate (no rook move), none may have (no bishop move), and the loop must not be a square.
Two different lattice vectors of equal length exist when is a sum of two squares in two essentially different ways. The smallest candidates and are killed by zero or equal coordinates; the next is Taking , , the visited squares satisfy every condition, and an exhaustive search confirms nothing smaller works:
The computation
Search every squared length in order: list all lattice jump vectors of that length and try every triple of jumps (the fourth is forced by closure). Keep a loop only if it visits four distinct squares, none a rook or bishop move from the origin, and is not a square. The first length that admits one is .
import itertools
def ok(p): # not a rook/bishop move from the origin
dx, dy = p
return dx != 0 and dy != 0 and abs(dx) != abs(dy)
for L2 in range(1, 200):
R = range(-15, 16)
vecs = [(a, b) for a in R for b in R if a*a + b*b == L2]
hit = False
for u, w, z in itertools.product(vecs, repeat=3):
p2 = (u[0]+w[0], u[1]+w[1]); p3 = (p2[0]+z[0], p2[1]+z[1])
if p3[0]**2 + p3[1]**2 != L2: continue # closing jump length L
pts = [u, p2, p3]
if len({(0, 0), *pts}) != 4 or not all(ok(p) for p in pts): continue
sides = [u, w, z, (-p3[0], -p3[1])]
if all(s[0]*t[0] + s[1]*t[1] == 0 for s, t in zip(sides, sides[1:])):
continue # square loop
hit = True; break
if hit:
print(L2); break # 65
Extra Credit
The frog now jumps with that same minimum distance , and wants to be able to reach every square of the board. What is the minimum for which this is possible?
Solution
The available jumps are the sixteen vectors , , , . On a small board almost all of them leave the board, and the reachable set is a proper subset. As grows the reachability graph knits together: for it is still disconnected, while for every square reaches every other. The minimum board size is
The computation
For each board size, breadth-first search the reachability graph from one corner, following only jumps that stay on the board, and check whether all squares are reached. The first fully connected size is .
from collections import deque
R = range(-9, 10)
jumps = [(a, b) for a in R for b in R if a*a + b*b == 65]
def connected(N):
seen = {(0, 0)}; dq = deque(seen)
while dq:
x, y = dq.popleft()
for dx, dy in jumps:
p = (x+dx, y+dy)
if 0 <= p[0] < N and 0 <= p[1] < N and p not in seen:
seen.add(p); dq.append(p)
return len(seen) == N*N
print(next(N for N in range(8, 20) if connected(N))) # 14