Commit f94dd54a authored by Adam P. Goucher's avatar Adam P. Goucher

Hexagonal rules

parent 1c11ea07
Pipeline #55075413 passed with stages
in 8 minutes and 26 seconds
......@@ -48,27 +48,31 @@ def hexlord():
return lord
def tab2str(lord2):
lord = squarelord()
def tab2str(lord2, hexagonal):
rule_letters = {}
rule_letters[1] = "ce" ;
rule_letters[2] = "ceaikn" ;
rule_letters[3] = "ceaiknjqry" ;
rule_letters[4] = "ceaiknjqrytwz" ;
rule_letters[5] = "ceaiknjqry" ;
rule_letters[6] = "ceaikn" ;
rule_letters[7] = "ce" ;
if hexagonal:
lord = hexlord()
rule_letters[2] = "omp"
rule_letters[3] = "omp"
rule_letters[4] = "omp"
else:
lord = squarelord()
rule_letters[1] = "ce"
rule_letters[2] = "ceaikn"
rule_letters[3] = "ceaiknjqry"
rule_letters[4] = "ceaiknjqrytwz"
rule_letters[5] = "ceaiknjqry"
rule_letters[6] = "ceaikn"
rule_letters[7] = "ce"
popcounts = [0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2, 3, 2, 3, 3, 4]
canonicals = [['' for i in range(9)] for j in range(2)]
canstring = ''
for i in range(512):
centre = (i >> 4) & 1
ncount = popcounts[i & 15] + popcounts[i >> 5]
ncount = masked_popcount(i, hexagonal)
if (lord2[i] == 1):
canonicals[centre][ncount] += lord[i]
......@@ -87,12 +91,27 @@ def tab2str(lord2):
continue
elif (len(b) < len(a)):
canstring += b
else:
elif (len(a) < len(b)):
canstring += a
else:
canstring += (b if hexagonal else a)
if hexagonal:
canstring += 'h'
return canstring
def masked_popcount(i, hexagonal):
popcounts = [0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2, 3, 2, 3, 3, 4]
if hexagonal:
i = i & 443
return popcounts[i & 15] + popcounts[i >> 5]
def str2tab(rulestring, hexagonal='unknown'):
if (hexagonal == 'unknown'):
......@@ -131,17 +150,13 @@ def str2tab(rulestring, hexagonal='unknown'):
raise ValueError('Error: "%s" does not match the regex "%s"' % (rulestring, regex))
popcounts = [0, 1, 1, 2, 1, 2, 2, 3, 1, 2, 2, 3, 2, 3, 3, 4]
lord2 = []
for i in range(512):
centre = (i >> 4) & 1
if hexagonal:
ncount = popcounts[(i & 443) & 15] + popcounts[(i & 443) >> 5]
else:
ncount = popcounts[i & 15] + popcounts[i >> 5]
ncount = masked_popcount(i, hexagonal)
if (centre, ncount) in isotrans:
fragment = isotrans[(centre, ncount)]
......@@ -156,10 +171,7 @@ def str2tab(rulestring, hexagonal='unknown'):
else:
lord2.append(0)
if hexagonal:
return lord2
canstring = tab2str(lord2)
canstring = tab2str(lord2, hexagonal)
if (rulestring != canstring):
raise NonCanonicalError('%s is a non-canonical version of %s' % (rulestring, canstring))
......
......@@ -182,9 +182,11 @@ def ReadRuleTree(list_of_lines):
chebyshev_range = max([abs(x) for y in nhood for x in y])
if (chebyshev_range <= 1):
rarray = TreeToArray(nhood, list_of_nodes)
rstring = tab2str(rarray)
if (rarray == str2tab(rstring)):
raise SurplusTreeError(rstring)
for hexagonal in [False, True]:
rstring = tab2str(rarray, hexagonal)
if (rarray == str2tab(rstring)):
raise SurplusTreeError(rstring)
# Serialise tree to an array:
num_nodes = len(list_of_nodes)
......
......@@ -9,10 +9,14 @@ class TestSanirule(unittest.TestCase):
def test_goltree(self):
filename = os.path.join(lifelib.lifelib_dir, 'rules', 'source', 'Life.tree')
srule = sanirule(filename)
self.assertEqual(srule, 'b3s23')
def test_hextree(self):
filename = os.path.join(lifelib.lifelib_dir, 'rules', 'source', 'Hex-B2omS2.tree')
srule = sanirule(filename)
self.assertEqual(srule, 'b2-ps2h')
if __name__ == '__main__':
unittest.main()
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment