Skip to content

Instantly share code, notes, and snippets.

@robertcampion
Created May 24, 2016 20:22
Show Gist options
  • Save robertcampion/055996196e83cef1e361b8cf04e865ad to your computer and use it in GitHub Desktop.
Save robertcampion/055996196e83cef1e361b8cf04e865ad to your computer and use it in GitHub Desktop.
#!/usr/bin/env python3
import itertools
import operator
tips = [[1, 4, 9], [5, 1, 6], [6, 4, 5], [7, 2, 4]]
vertices = [[8, 3, 5], [2, 9, 8], [5, 3, 7], [3, 8, 9]]
corner_faces = [[1, 2, 3], [1, 2, 4], [2, 3, 4], [1, 3, 4]]
edges = [[4, 7], [9, 1], [6, 3], [2, 6], [8, 2], [7, 1]]
edge_faces = [[1, 2], [1, 3], [1, 4], [2, 3], [2, 4], [3, 4]]
def to_corner_faces(pieces):
return [[pieces[0][0], pieces[1][0], pieces[3][0]],
[pieces[0][1], pieces[1][1], pieces[2][0]],
[pieces[0][2], pieces[2][1], pieces[3][1]],
[pieces[1][2], pieces[2][2], pieces[3][2]]]
def to_edge_faces(pieces):
return [[pieces[0][0], pieces[1][0], pieces[2][0]],
[pieces[0][1], pieces[3][0], pieces[4][0]],
[pieces[1][1], pieces[3][1], pieces[5][0]],
[pieces[2][1], pieces[4][1], pieces[5][1]]]
def rotations(l):
return [l[i:] + l[:i] for i in range(len(l))]
def no_duplicates(l):
return all(len(subl) == len(set(subl)) for subl in l)
def construct_corner_states(pieces):
return filter(no_duplicates,
map(to_corner_faces,
itertools.product(*map(rotations, pieces))
)
)
tip_states = construct_corner_states(tips)
vertex_states = construct_corner_states(vertices)
edge_flips = [f for f in itertools.product([0, 1], repeat=6) if sum(f) % 2 == 0]
edge_orientations = [[list(reversed(x)) if r else x for x, r in zip(edges, f)]
for f in edge_flips]
#http://code.activestate.com/recipes/578227-generate-the-parity-or-sign-of-a-permutation/
def perm_parity(l):
lst = list(l)
parity = 1
for i in range(0,len(lst)-1):
if lst[i] != i:
parity *= -1
mn = min(range(i,len(lst)), key=lst.__getitem__)
lst[i],lst[mn] = lst[mn],lst[i]
return parity
def permute(l, p):
return [l[i] for i in p]
edge_permutations = [p for p in itertools.permutations(range(6)) if perm_parity(p) == 1]
edge_states = filter(no_duplicates,
map(to_edge_faces,
itertools.starmap(permute,
itertools.product(edge_orientations, edge_permutations)
)
)
)
def combine_states(*args):
return filter(no_duplicates, map(lambda x: list(map(operator.concat, *x)), itertools.product(*args)))
#filter(no_duplicates, map(lambda x: map(operator.concat, *x), itertools.product(*args)))
corner_states = combine_states(tip_states, vertex_states)
states = combine_states(corner_states, edge_states)
format_str = r'''
D----------------- A -----------------D
\ ? / \ ? / \ ? // \\ ? / \ ? / \ ? /
\ / ? \ / ? \ // ? \\ / ? \ / ? \ /
\----(1)----//-----\\----(3)----/
\ ? / \ ? // \ ? / \\ ? / \ ? /
\ / ? \ // ? \ / ? \\ / ? \ /
\-----//----(2)----\\-----/
\ ? // \ ? / \ ? / \\ ? /
\ // ? \ / ? \ / ? \\ /
B ----------------- C
B-----------------C
\ ? / \ ? / \ ? /
\ / ? \ / ? \ /
\----(4)----/
\ ? / \ ? /
\ / ? \ /
\-----/
\ ? /
\ /
D
'''
format_str = format_str.replace('?', '{}')
for s in states:
print(format_str.format(s[0][2], s[0][7], s[0][0], s[2][0], s[2][6], s[2][2], s[0][5], s[0][3], s[1][0], s[2][3], s[2][5], s[0][8], s[0][6], s[1][3], s[2][7], s[2][8], s[0][4], s[1][6], s[1][7], s[2][4], s[0][1], s[1][4], s[1][5], s[2][1], s[1][1], s[1][8], s[1][2], s[3][0], s[3][7], s[3][1], s[3][3], s[3][4], s[3][6], s[3][8], s[3][5], s[3][2]))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment