Chapter 279
Can You Break A Very Expensive Centrifuge?
The Riddler for September 18, 2020. The Express balances seven tubes around a twelve-slot centrifuge, and the Classic finds the expected number of guesses in an optimal binary search through a dictionary.
Riddler Express
A microcentrifuge has slots evenly spaced around a circle. For it to stay balanced, the centre of mass of the loaded tubes (all equal mass) must sit at the exact centre. You need to spin exactly seven tubes. In which of the slots ( through ) can you place them so the centrifuge is balanced?
The Riddler, FiveThirtyEight, September 18, 2020(original post)
Solution
Put the slots at the twelfth roots of unity. The tubes balance exactly when the sum of their slot vectors is zero. A vanishing sum of twelfth roots decomposes into rotated regular polygons whose vertex counts are the prime divisors of : diametrically opposite pairs (two vectors apart) and equilateral triangles (three vectors apart). So a balanced set of size must be a disjoint union with . Since is odd, is odd; forces . Every balanced seven-tube layout is therefore one equilateral triangle plus two diametric pairs, for example slots (the triangle together with the pairs and ). Counting them: there are rotations of the triangle, and removing one triangle leaves exactly intact diametric pairs from which to choose , so balanced arrangements in all (all rotations of one another). Equivalently, placing seven tubes is the same as choosing the five empty slots, the balanced-five problem.
The computation
Encode the balance condition directly: a subset is balanced when its slot vectors (twelfth roots of unity) sum to zero. Enumerate all seven-slot subsets and count.
import itertools, cmath
roots = [cmath.exp(2j * cmath.pi * k / 12) for k in range(12)]
balanced = [c for c in itertools.combinations(range(12), 7)
if abs(sum(roots[k] for k in c)) < 1e-9]
print(len(balanced)) # 12
ex = balanced[0]
print(tuple(k + 1 for k in ex)) # a 1-indexed layout
Exactly seven-tube layouts balance, each a triangle plus two diametric pairs.
Riddler Classic
In the game Guess My Word, a secret word is drawn uniformly from a dictionary of exactly entries. After each guess you learn whether the secret word is alphabetically before or after it. Playing as efficiently as possible, how many guesses should you expect to need?
The Riddler, FiveThirtyEight, September 18, 2020(original post)
Solution
The optimal strategy is binary search: guess the middle word, and recurse into whichever half the answer lies in. This builds a binary tree in which one word is found on guess , two words on guess , four on guess , and in general words on guess , as long as that many words remain. The full levels run from to , covering words; the remaining words sit on guess . Averaging over the uniformly random secret word, This sits just above : binary search on items averages a hair under guesses because some words are found early.
The computation
Encode the tree level by level: words are resolved on guess until the dictionary is exhausted, then take the weighted mean.
from fractions import Fraction
N = 267_751
depth, remaining, total = 1, N, 0
while remaining > 0:
count = min(2**(depth - 1), remaining) # words found on guess `depth`
total += depth * count
remaining -= count
depth += 1
E = Fraction(total, N)
print(E, float(E)) # 4563001/267751 17.0419...
The expected number of guesses is .