Skip to content

Instantly share code, notes, and snippets.

@wuurrd
Created September 28, 2012 14:21
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save wuurrd/3800151 to your computer and use it in GitHub Desktop.
Save wuurrd/3800151 to your computer and use it in GitHub Desktop.
This plaything finds the first way one can combine elements in S_4 to create the (12) permutation (group theory).
from itertools import combinations_with_replacement, chain, permutations
def flatten(l):
a = []
for b in l:
for c in b:
a.append(c)
return a
class PermutationElement(object):
def __init__(self, sequence):
self.sequence = sequence
self.permutation = False
for v in self.sequence:
if type(v) == PermutationElement:
self.permutation = True
break
def get_keys(self):
if not self.permutation:
return list(self.sequence)
return flatten([a.get_keys() for a in self.sequence])
def __mul__(self, other_permutation):
lists = []
if not len(self.sequence):
return other_permutation
data = {}
seq = self.get_keys() + other_permutation.get_keys()
for i in seq:
value = other_permutation(self(i))
data[i] = value
data = [(k,v) for k, v in data.items() if k!=v]
data_dict = dict(data)
if not len(data):
return PermutationElement([])
keys_left = len(data)
while keys_left:
current = data.pop(0)[0]
if current in flatten(lists):
keys_left = len(data)
continue
new_list = [current]
lists.append(new_list)
value = current
while True:
new_value = data_dict[value]
if new_value in new_list:
break
new_list.append(new_value)
value = new_value
keys_left = len(data)
if len(lists) > 1:
lists = [PermutationElement(l) for l in lists]
else:
lists = lists[0]
return self.__class__(lists)
def __call__(self, val):
if not len(self.sequence):
return val
if not self.permutation:
if val in self.sequence:
idx = self.sequence.index(val)
if idx == len(self.sequence)-1:
return self.sequence[0]
else:
return self.sequence[idx+1]
else:
return val
else:
for permutation in self.sequence:
val = permutation(val)
return val
def __str__(self):
if self.permutation:
return ''.join(str(s) for s in self.sequence)
return '(%s)' % (''.join([str(s) for s in self.sequence]))
__repr__ = __str__
def __pow__(self, a):
val = self
for i in range(a-1):
val *= self
return val
def all_subsets(ss, max_size = 15):
return chain(*map(lambda x: combinations_with_replacement(ss, x), range(1, max_size)))
if __name__ == '__main__':
a = PermutationElement([1,2,4,3])
b = PermutationElement([PermutationElement([1,2]), PermutationElement([3,4])])
c = PermutationElement([1,2,3,4])
def find():
count = 0
for k in all_subsets([a,b,c], 5):
for m in permutations(k):
count += 1
val = m[0]
for i, l in enumerate(m):
if i == 0:
continue
val *= l
if str(val) in ['(12)', '(21)']:
print 'FOUND', m
return
find()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment