Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- def generate_initial(level = 0):
- import random
- if random.random() > 0.8 ** level: # generate more branches near root
- return random.randint(1, 12) # limit amount of distinct keys for more interesting test cases
- else:
- return [generate_initial(level + 1), random.choice(["&", "|"]), generate_initial(level + 1)]
- def stringify_tree(tree = None):
- tree = tree if tree is not None else generate_clean()
- return str(tree) if isinstance(tree, (int, str, bool)) else "(" + "".join(map(stringify_tree, tree)) + ")"
- def get_keys(tree):
- return {tree} if isinstance(tree, int) else get_keys(tree[0]) | get_keys(tree[2])
- def powerset(iterable):
- import itertools
- s = list(iterable)
- return list(itertools.chain.from_iterable(itertools.combinations(s, r) for r in range(len(s) + 1)))
- def replace_keys(tree, keys, newkeys):
- if isinstance(tree, int):
- return newkeys[keys.index(tree)]
- return [replace_keys(tree[0], keys, newkeys), tree[1], replace_keys(tree[2], keys, newkeys)]
- def get_security(tree):
- keys = sorted(get_keys(tree))
- combs = powerset(keys)
- valid = []
- for comb in combs:
- newkeys = [key in comb for key in keys]
- modify = replace_keys(tree, keys, newkeys)
- if eval(stringify_tree(modify)):
- valid.append(comb[::-1])
- return sorted(valid)[0]
- trees = [generate_initial() for n in range(10)]
- keys = set()
- for tree in trees:
- keys |= get_keys(tree)
- keys = sorted(keys)
- for tree in trees:
- tree = replace_keys(tree, keys, range(1, len(keys) + 1))
- print(tree)
- print(get_security(tree))
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement