def test_ququart_pair(): """ Tests working for ququart entangled pair LC classes """ # Tests first equivalence class edges = [((0, 0), (1, 0), 1), ((0, 1), (1, 1), 1)] graph = create_prime_power_graph(edges, 2, 2) class_graph = explore_lc_orbit(graph, verbose=False) register = set( tuple(map(tuple, attrs['edges'])) for node, attrs in class_graph.node.iteritems()) target = \ [(((0, 1), (1, 0), 1), ((0, 0), (1, 1), 1)), (((0, 1), (1, 0), 1), ((0, 1), (1, 1), 1), ((0, 0), (1, 1), 1)), (((0, 1), (1, 0), 1), ((1, 0), (0, 0), 1), ((0, 0), (1, 1), 1)), (((0, 1), (1, 1), 1), ((1, 0), (0, 0), 1)), (((0, 1), (1, 1), 1), ((1, 0), (0, 0), 1), ((0, 0), (1, 1), 1))] target = set(target) assert register == target # Tests second equivalence class edges = [((0, 0), (1, 0), 1)] graph = create_prime_power_graph(edges, 2, 2) class_graph = explore_lc_orbit(graph, verbose=False) register = set( tuple(map(tuple, attrs['edges'])) for node, attrs in class_graph.node.iteritems()) target = \ [(((0, 1), (1, 0), 1),), (((0, 1), (1, 0), 1), ((0, 1), (1, 1), 1)), (((0, 1), (1, 0), 1), ((0, 1), (1, 1), 1), ((1, 0), (0, 0), 1), ((0, 0), (1, 1), 1)), (((0, 1), (1, 0), 1), ((1, 0), (0, 0), 1)), (((0, 1), (1, 1), 1),), (((1, 0), (0, 0), 1),)] target = set(target) assert register == target
def test_explore_lc_orbit(): """ Generates class graphs for random graphs """ for _ in range(10): # Creates a random NetworkX graph and it's equivalent GraphState g = gen_random_connected_graph(7) class_graph = explore_lc_orbit(g, verbose=False) orbit_hashes = set( [graph['hash'] for graph in class_graph.node.values()]) assert len(class_graph.node) == len(orbit_hashes) graphs = [graph['nx_graph'] for graph in class_graph.node.values()] for i in range(10): graph_a = random.choice(graphs) graph_b = random.choice(graphs) lc_equiv, lc_ops = are_lc_equiv(graph_a, graph_b) assert lc_equiv
def test_LC_explore_example(): # Create the input graph edges = [(0, 1), (1, 2), (2, 3), (3, 4)] graph = nx.Graph() graph.add_edges_from(edges) # Find the class graph class_graph = explore_lc_orbit(graph) # Export class graph to JSON file file_prefix = 'L5_class_graph' cg_data = export_class_graph(class_graph, file_prefix) # Removes hashes (these may not be the same on a different system) for node in cg_data['nodes']: node.pop('hash') data = { 'nodes': [{ 'edges': [(0, 1, 1), (1, 2, 1), (2, 3, 1), (3, 4, 1)], 'id': 0 }, { 'edges': [(0, 1, 1), (0, 2, 1), (1, 2, 1), (2, 3, 1), (3, 4, 1)], 'id': 1 }, { 'edges': [(0, 1, 1), (1, 2, 1), (1, 3, 1), (2, 3, 1), (3, 4, 1)], 'id': 2 }, { 'edges': [(0, 1, 1), (0, 2, 1), (0, 3, 1), (1, 2, 1), (1, 3, 1), (3, 4, 1)], 'id': 3 }, { 'edges': [(0, 2, 1), (0, 3, 1), (1, 2, 1), (1, 3, 1), (3, 4, 1)], 'id': 4 }, { 'edges': [(0, 2, 1), (0, 3, 1), (0, 4, 1), (1, 2, 1), (1, 3, 1), (1, 4, 1), (3, 4, 1)], 'id': 5 }, { 'edges': [(0, 2, 1), (0, 3, 1), (0, 4, 1), (1, 2, 1), (1, 3, 1), (1, 4, 1), (2, 3, 1), (2, 4, 1)], 'id': 6 }, { 'edges': [(0, 1, 1), (0, 2, 1), (0, 3, 1), (0, 4, 1), (1, 2, 1), (1, 3, 1), (1, 4, 1), (3, 4, 1)], 'id': 7 }, { 'edges': [(0, 1, 1), (0, 2, 1), (0, 3, 1), (0, 4, 1), (2, 3, 1), (2, 4, 1)], 'id': 8 }, { 'edges': [(0, 1, 1), (0, 2, 1), (1, 2, 1), (2, 3, 1), (2, 4, 1), (3, 4, 1)], 'id': 9 }], 'links': [{ 'source': 0, 'equivs': [[1, 3]], 'target': 1, 'ops': ['LC'] }, { 'source': 0, 'equivs': [[2]], 'target': 2, 'ops': ['LC'] }, { 'source': 1, 'equivs': [[2]], 'target': 8, 'ops': ['LC'] }, { 'source': 1, 'equivs': [[0, 1, 3, 4]], 'target': 9, 'ops': ['LC'] }, { 'source': 2, 'equivs': [[1, 3]], 'target': 3, 'ops': ['LC'] }, { 'source': 3, 'equivs': [[2]], 'target': 4, 'ops': ['LC'] }, { 'source': 3, 'equivs': [[3]], 'target': 5, 'ops': ['LC'] }, { 'source': 4, 'equivs': [[3, 4]], 'target': 8, 'ops': ['LC'] }, { 'source': 4, 'equivs': [[3, 4]], 'target': 7, 'ops': ['LC'] }, { 'source': 5, 'equivs': [[0, 1]], 'target': 6, 'ops': ['LC'] }, { 'source': 5, 'equivs': [[2]], 'target': 7, 'ops': ['LC'] }, { 'source': 6, 'equivs': [[2]], 'target': 9, 'ops': ['LC'] }, { 'source': 7, 'equivs': [[0, 1]], 'target': 8, 'ops': ['LC'] }] } assert data == cg_data
def find_all_classes(directory, power, prime): """ Finds all members of all classes """ # Gets edge indices and state params and generates edge map filename = directory + '/edge_index.csv' with open(filename, 'r') as file: reader = csv.reader(file) edge_index = [tuple(map(int, edge)) for edge in reader] filename = directory + '/state_params.csv' with open(filename, 'r') as file: reader = csv.reader(file) p, m, n = map(int, next(reader)) c_map = gen_psuedo_graph_edge_map(p, m) # Creates function to produce config isomorphs isomorph_configs = make_isomorph_func(edge_index, n) pprint(c_map) pprint(edge_index) # Initialises progress bar rg_file = directory + '/remaining_graphs.csv' rem_graphs_size = os.path.getsize(rg_file) pbar = tqdm(total=rem_graphs_size) while True: rem_update = rem_graphs_size - os.path.getsize(rg_file) if rem_update >= 0: pbar.update(rem_update) rem_graphs_size = os.path.getsize(rg_file) # Waits until a graph is available to process edge_config = get_next_graph(directory) if not edge_config: break tqdm.write("Psuedo edge config: %s" % (edge_config, )) # Create initial graph c_edges = [(u, v, w) for (u, v), w in zip(edge_index, edge_config)] init_graph = create_psuedo_graph(c_edges, p, m, c_map) # Checks if graph is connected if not nx.is_connected(init_graph.to_undirected()): tqdm.write("Disconnected. Removing isomorphs... ") # Removes any isomorphic graphs from remaining remove_disconnected_configs(directory, edge_config, isomorph_configs) tqdm.write("Done") continue init_graph = psuedo_to_real(init_graph) # Check if graph has already been found for hash test graph_hash = hash_graph(init_graph) if found_hash(directory, graph_hash): tqdm.write("Already found %d" % graph_hash) iso_configs = isomorph_configs(edge_config) remove_found_graphs(directory, iso_configs) continue # Explore class graph tqdm.write("Exploring class...") class_graph = explore_lc_orbit(init_graph, False, False) class_register = [[ node, attrs['edges'], attrs['hash'], attrs['nx_graph'] ] for node, attrs in class_graph.node.iteritems()] nodes, edges, hashes, graphs = zip(*class_register) # Formats edge list based on state parameters if power == 1: edges = [[(u, v, c) for (u, i), (v, j), c in edge_set] for edge_set in edges] if prime == 2: edges = [[(u, v) for u, v, c in edge_set] for edge_set in edges] # Exports class_register to file tqdm.write("Writing register to file...") class_register = zip(nodes, edges, hashes) config_label = '_'.join(map(str, edge_config)) filename = directory + '/classes/' + config_label + '.csv' with open(filename, 'w') as csvfile: writer = csv.writer(csvfile) writer.writerows(class_register) # Finds and removes any isomorphs tqdm.write("Removing isomorphs...") psu_edges = [ real_graph_to_psu_edges(graph, c_map, edge_index) for graph in graphs ] edge_configs = [[c for u, v, c in w_edges] for w_edges in psu_edges] iso_configs = [ iso_config for config in edge_configs for iso_config in isomorph_configs(config) ] remove_found_graphs(directory, iso_configs) # Adds hashes to found hash directory write_hashes(directory, hashes) tqdm.write("Done") pbar.close()
def test_prime_dimension_explore_example(): # Create the input graph prime = 3 w_edges = [(0, 1, 1), (1, 2, 2)] qutrit_g = create_prime_graph(w_edges, prime) # Find the class graph class_graph = explore_lc_orbit(qutrit_g) # Export class graph to JSON file filename = 'qutrit_class_graph' cg_data = \ export_class_graph(class_graph, filename) # Removes hashes (these may not be the same on a different system) for node in cg_data['nodes']: node.pop('hash') data = { 'nodes': [{ 'edges': [(0, 1, 1), (1, 2, 2)], 'id': 0 }, { 'edges': [(0, 1, 2), (1, 2, 2)], 'id': 1 }, { 'edges': [(0, 1, 1), (0, 2, 2), (1, 2, 2)], 'id': 2 }, { 'edges': [(0, 1, 1), (0, 2, 1), (1, 2, 2)], 'id': 3 }, { 'edges': [(0, 1, 1), (1, 2, 1)], 'id': 4 }, { 'edges': [(0, 1, 1), (0, 2, 1), (1, 2, 1)], 'id': 5 }, { 'edges': [(0, 1, 2), (0, 2, 2), (1, 2, 2)], 'id': 6 }], 'links': [{ 'source': 0, 'equivs': [[1]], 'target': 0, 'ops': ['EM2'] }, { 'source': 0, 'equivs': [[0]], 'target': 1, 'ops': ['EM2'] }, { 'source': 0, 'equivs': [[1], [1, 0]], 'target': 2, 'ops': ['LC1', 'LC2'] }, { 'source': 0, 'equivs': [[1], [1, 2]], 'target': 3, 'ops': ['LC2', 'LC1'] }, { 'source': 0, 'equivs': [[2]], 'target': 4, 'ops': ['EM2'] }, { 'source': 1, 'equivs': [[2], [1]], 'target': 2, 'ops': ['LC2', 'LC1'] }, { 'source': 1, 'equivs': [[1]], 'target': 4, 'ops': ['EM2'] }, { 'source': 1, 'equivs': [[1, 0, 2], [1]], 'target': 6, 'ops': ['LC1', 'LC2'] }, { 'source': 2, 'equivs': [[1, 0]], 'target': 2, 'ops': ['EM2'] }, { 'source': 2, 'equivs': [[1, 2], [1, 0]], 'target': 3, 'ops': ['LC2', 'LC1'] }, { 'source': 2, 'equivs': [[1, 0, 2]], 'target': 5, 'ops': ['EM2'] }, { 'source': 2, 'equivs': [[1, 0, 2], [2]], 'target': 6, 'ops': ['LC2', 'LC1'] }, { 'source': 3, 'equivs': [[1, 2]], 'target': 3, 'ops': ['EM2'] }, { 'source': 3, 'equivs': [[1], [0]], 'target': 4, 'ops': ['LC2', 'LC1'] }, { 'source': 3, 'equivs': [[1, 0, 2], [0]], 'target': 5, 'ops': ['LC1', 'LC2'] }, { 'source': 3, 'equivs': [[0]], 'target': 6, 'ops': ['EM2'] }, { 'source': 4, 'equivs': [[1], [1, 0, 2]], 'target': 5, 'ops': ['LC1', 'LC2'] }] } assert data == cg_data