# Enigmatic Code

Programming Enigma Puzzles

## Enigma 1710: Carregio

From New Scientist #2877, 11th August 2012 [link]

Since the second world war, car registrations in my country have consisted of three parts: the first is the four-figure year of manufacture, the second is made up of two letters, and the third consists of a number which, in my case, has three digits. However, we are now switching to all-digit car registrations, consisting of three parts. Existing registrations such as mine will be adapted by changing the two letters to a number by replacing A by 1, B by 2, and so on, so that, for example, GL would become 712.

The three numbers making up the three parts of my car’s registration will then all be multiples of 18, but none will be a perfect square. And overall the registration will use each of the digits 0 to 9 exactly once.

What is my car’s registration before the changes?

[enigma1710]

### 3 responses to “Enigma 1710: Carregio”

1. Jim Randell 8 August 2012 at 5:37 pm

The following Python code runs in 31ms.

```from itertools import product
from enigma import is_square, irange

# the registration is: YYYY-XX-NNN (where X is a letter and N is a number)
# then XX is also converted  to a (3-digit) number
# each part is then a multiple of 18, and a non-square

# we need to find 3-digit non-square multiples of 18, with no repeated digits
ns = []
for n in irange(108, 999, step=18):
if is_square(n): continue
s = str(n)
if len(set(s)) != 3: continue
ns.append(s)

# which are composed of the ordinal numbers of two letters
# (NOTE: this is non-unique: e.g. both AZ and LF map to 126)
xs = dict()
for (i, j) in product(irange(1, 26), repeat=2):
s = str(i) + str(j)
if s not in ns: continue
xs[chr(64 + i) + chr(64 + j)] = s

# the year is a post war multiple of 18
for y in irange(1944, 2012, step=18):
if is_square(y): continue
ds = set(str(y))
if len(ds) != 4: continue

# we need a disjoint 3-digit non-square multiple of 18 transcribed from letters
for (s, x) in xs.items():
ds2 = ds.union(set(x))
if len(ds2) != 7: continue

# and a 3-digit non-square made up of the remaining digits
for n in ns:
ds3 = ds2.union(set(n))
if len(ds3) != 10: continue

print(y, s, n)
```

Solution: Before the changes the registration was 1980 WD 756.

• Naim Uygun 8 August 2012 at 7:40 pm

The candidate years: 1962, 1980
The candidate numbers of two letters: GT=720, WD=234,GB=72, ED=54
Hence, my car registration before the changes is 1980-WD-756

2. Brian Gladman 9 August 2012 at 8:14 am

Here is an alternative version:

```# check that a tuple partitioning the digits of a three digit
# number either (1, 2) or (2, 1) gives valid two letter codes
def nbr_to_str(x):

def trans(t, i, j):
return (chr(ord('A') + t[0] - 1) + chr(ord('A') + t[1] - 1)
if 0 < t[i] < 10 and 10 <= t[j] <= 26 else '')

c = trans(divmod(x, 100), 0, 1) + trans(divmod(x, 10), 1, 0)
# only return unambiguous two letter codes
return c if len(c) == 2 else None

# a map of four digit squares
sq = {x*x:x for x in range(100)}

# the middle three digits of the new number
for mid in range(108, 1008, 18):

# check that these digits represent a valid two letter code
ltrs = nbr_to_str(mid)
set_mid = set(str(mid))
if mid not in sq and len(set_mid) == 3 and ltrs:

# the first four digits for the year
for year in range(1944, 2016, 18):
set_year = set(str(year))
if year not in sq and len(set_year) == 4:

# the set of used digits so far
used_set = set_mid | set_year
# the final three digits
for final in range(108, 1008, 18):
# check that this potential solution uses all 10 digits
if final not in sq and len(set(str(final)) | used_set) == 10:
print('{:d}-{:s}-{:d}'.format(year, ltrs, final))
```

This site uses Akismet to reduce spam. Learn how your comment data is processed.