The breakthrough for me – the first one – was realising there are only 54 rolls of the dice available, so there cannot be more than 56 squares in either direction. That immediately gives us that the square is between 44 and 57 (inclusive), which is a start …

]]>It uses some routines from my **enigma.py** library (notably Primes()).

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 |
from itertools import combinations, product from enigma import irange, Primes, printf # primes up to 100 primes = Primes(100) # check possible deltas, such that the squares [1, 100] lie in the # interval [<a>,<b>], and the missing squares (given by offsets in # ) are prime, but not in def check(a, b, ds, d2): # consider possible deltas for d in irange(100 - b, 1 - a): # find the missing squares missing = tuple(x + d for x in ds) # missing squares should be prime and not on die 2 if all(x not in d2 and x in primes for x in missing): printf("current square = {d}, die2 = {d2}, missing squares = {missing}") # the first die is numbered 1 to 10 d1 = set(irange(1, 10)) # the second die is numbered with 4 primes for d2 in combinations(primes, 4): # find the delta for each throw of the dice ds = set().union(d1, d2, map(sum, product(d1, d2))) # find up to three missing deltas deltas = [] for i in irange(1, 99): if i not in ds: deltas.append(i) if len(deltas) > 2: break # check ranges that cover 100 squares if len(deltas) > 2 and deltas[0] + deltas[2] > 100: check(1 - deltas[0], deltas[2] - 1, (deltas[0], deltas[1]), d2) check(1 - deltas[2], deltas[0] - 1, (-deltas[1], -deltas[0]), d2) if len(deltas) > 1 and deltas[1] > 50: check( 1 - deltas[1], deltas[1] - 1, (-deltas[0], deltas[0]), d2) |

51+11+/(1-10)=52-72

51-11-/(1-10)=30-50

51+23+/(1-10)=74-84

51-23-/(1-10)=18-28

51+31+/(1-10)=82-92

51-31-/(1-10)=10-20

51+41+/(1-10)=92-100

51-41-/(1-10)=1-10

hence 29 and 73 are the prime numbered squares unreachable with 11,23,31 and 41 being the primes on the four sided die and touching square being 51.

]]>
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 |
from itertools import combinations # primees in the range 1 .. 100 pr = (2, 3, 5, 7) pr = set(pr) | set(x for x in range(11, 100, 2) if all(x % p for p in pr)) # choose the primes for the four sided die in the range 10 .. 50 # (since we have to span 1 .. 100 with forward or backward moves) for p4 in combinations((x for x in pr if 10 < x < 50), 4): # find the set of moves that can be made either forward or # backward with this die when combined with the ten sided one moves = (set(p4) | set(range(1, 11)) | set(p + q for q in range(1, 11) for p in p4)) # now find the numbers in 1 .. 50 that cannot be thrown with # this pair of dice - only one number can be missing missing, *z = set(range(1, 51)) - moves if not z: # consider positions from which both 1 and 100 can be reached for pos in range(100 - max(moves), max(moves) + 1): # find the two missing numbers p, q = pos - missing, pos + missing # and check that they are primes not on the four sided die if set((p, q)) < pr and p not in p4 and q not in p4: fs = '(a) {}, (b) {} ({} and {} cannot be reached).' print(fs.format(pos, ', '.join(str(x) for x in p4), p, q)) |