def solve_qa(self, verbose=True, num_reads=100): assert self.token is not None assert self.mode == "bqm" if self.qubo is None: self.pre_process() if verbose: print(f"Solving SMTI with: {SOLVER}") print(f"Optimal Solution: {-(len(self.encoding) * self.p2 + self.matching.size * self.p1)}") chain_strength = self.get_chain_stength() + 1 # max element in qubo matrix + epsilon solver_limit = len(self.encoding) # solver_limit => size of qubo matrix G = nx.complete_graph(solver_limit) dw_solver = DWaveSampler(solver=SOLVER, token=self.token, endpoint=ENDPOINT) embedding = minorminer.find_embedding(G.edges, dw_solver.edgelist) fixed_embedding = FixedEmbeddingComposite(dw_solver, embedding) result = fixed_embedding.sample(self.qubo, num_reads=num_reads, chain_strength=chain_strength) dw_solver.client.close() # clean up all the thread mess the client creates so it does not block my code if verbose: print(result) for index, (sample, energy, occ, chain) in enumerate(result.record): match_, _ = self.encode_qa(sample.tolist()) stable_, size_ = Solution(self.matching, match_).is_stable() print(f"{index}: ", match_, size_, stable_) samples = pd.DataFrame() for sample, energy, occ, chain in result.record: match, valid = self.encode_qa(sample.tolist()) stable, size = Solution(self.matching, match).is_stable() samples = samples.append({"match": match, "sample": sample.tolist(), "energy": energy, "occ": occ, "chain": chain, "valid": valid, "stable": stable, "size": size}, ignore_index=True) return samples
def test_problem_label_in_sampleset(self): """All data adapters should propagate problem label.""" # sample bqm -> sampleset qpu = DWaveSampler() sampler = FixedEmbeddingComposite(qpu, self.embedding) sampleset = sampler.sample(self.bqm, label=self.label, **self.params) # ensure `from_bqm_sampleset` adapter propagates label data = from_bqm_sampleset(self.bqm, sampleset, sampler, params=self.params) self.assertEqual(data['details']['label'], self.label)
def test_sampler_graph_validation(self): """All data adapters should fail on non-Chimera/Pegasus solvers.""" # sample qpu = DWaveSampler() sampler = FixedEmbeddingComposite(qpu, self.embedding) sampleset = sampler.sample(self.bqm, return_embedding=True, **self.params) # resolve it before we mangle with it sampleset.info['problem_id'] # change solver topology to non-chimera/pegasus to test solver validation sampler.child.solver.properties['topology']['type'] = 'unknown' # ensure `from_bqm_sampleset` adapter fails on unstructured solver with self.assertRaises(TypeError): from_bqm_sampleset(self.bqm, sampleset, sampler, params=self.params)
def test_sampler_type_validation(self): """All data adapters should fail on non-StructuredSolvers.""" # sample qpu = DWaveSampler() sampler = FixedEmbeddingComposite(qpu, self.embedding) sampleset = sampler.sample(self.bqm, return_embedding=True, **self.params) # resolve it before we mangle with it sampleset.info['problem_id'] # change solver to unstructured to test solver validation sampler.child.solver = unstructured_solver_mock # ensure `from_bqm_sampleset` adapter fails on unstructured solver with self.assertRaises(TypeError): from_bqm_sampleset(self.bqm, sampleset, sampler, params=self.params)
def _test_from_bqm_sampleset(self, bqm): # sample qpu = DWaveSampler() sampler = FixedEmbeddingComposite(qpu, self.embedding) sampleset = sampler.sample(bqm, return_embedding=True, chain_strength=self.chain_strength, **self.params) # convert data = from_bqm_sampleset(bqm, sampleset, sampler, params=self.params) # construct (unembedded) response with chain breaks resolved # NOTE: for bqm/sampleset adapter, this is the best we can expect :( # inverse the embedding var_to_idx = {var: idx for idx, var in enumerate(sampleset.variables)} unembedding = { q: var_to_idx[v] for v, qs in self.embedding.items() for q in qs } # embed sampleset solutions_without_chain_breaks = [[ int(sample[unembedding[q]]) if q in unembedding else val for q, val in enumerate(solution) ] for solution, sample in zip(self.response['solutions'], sampleset.record.sample)] with mock.patch.dict(self.response._result, {'solutions': solutions_without_chain_breaks}): # validate data encoding self.verify_data_encoding(problem=self.problem, response=self.response, solver=self.solver, params=self.params, data=data, embedding_context=self.embedding_context)
def test_transform_embedded(self): C = dnx.chimera_graph(1) nodelist = list(C.nodes()) edgelist = list(C.edges()) structsampler = dimod.StructureComposite(dimod.ExactSolver(), nodelist=nodelist, edgelist=edgelist) gauges_sampler = CheckerboardTransformComposite(structsampler, C, aggregate=True) sampler = FixedEmbeddingComposite(gauges_sampler, { 'a': [0, 4], 'b': [1, 5], 'c': [2, 6] }) h = {'a': .5, 'c': 0} J = {('a', 'c'): -1} response = sampler.sample_ising(h, J) # All 4 gauges must return same samples for datum in response.data(): self.assertEqual(datum.num_occurrences, 4) dit.assert_response_energies( response, dimod.BinaryQuadraticModel.from_ising(h, J))
def dwave_physical_DW_2000Q_5(self): print("\nD-wave quantum annealer....") from dwave.system import DWaveSampler, FixedEmbeddingComposite from dwave.embedding.chimera import find_clique_embedding qpu = DWaveSampler(token=self.token, endpoint=self.endpoint, solver=dict(name='DW_2000Q_5'), auto_scale=False) self.title = "D-Wave Quantum Annealer" embedding = find_clique_embedding( self.bqm.variables, 16, 16, 4, # size of the chimera lattice target_edges=qpu.edgelist) qpu_sampler = FixedEmbeddingComposite(qpu, embedding) print("Maximum chain length for minor embedding is {}.".format( max(len(x) for x in embedding.values()))) from hybrid.reference.kerberos import KerberosSampler kerberos_sampler = KerberosSampler() selected_features = np.zeros((len(self.features), len(self.features))) for k in range(1, len(self.features) + 1): print("Submitting for k={}".format(k)) kbqm = dimod.generators.combinations(self.features, k, strength=6) kbqm.update(self.bqm) kbqm.normalize() best = kerberos_sampler.sample(kbqm, qpu_sampler=qpu_sampler, num_reads=10, max_iter=1).first.sample for fi, f in enumerate(self.features): selected_features[k - 1, fi] = best[f] if self.is_notebook: from helpers.draw import plot_feature_selection plot_feature_selection(self.features, selected_features)
lmbd * D_b[i][j] * D_b[i][k]) S[(j, k)] = J[(j, k)] bqm = dimod.BinaryQuadraticModel(linear=h, quadratic=J, offset=0.0, vartype=dimod.BINARY) energy_true_z = get_energy(bqm, z_b) embedding = get_embedding_with_short_chain(S, tries=5, processor=hardware_sampler.edgelist, verbose=False) sampler = FixedEmbeddingComposite(hardware_sampler, embedding) solver_parameters = { 'num_reads': num_reads, 'auto_scale': True, 'annealing_time': annealing_time, # default: 20 us #'anneal_schedule': anneal_sched_custom(id=3), #'num_spin_reversal_transforms': 2, # default: 2 } # schedule = make_reverse_anneal_schedule(s_target=0.99, # hold_time=1, # ramp_up_slope=0.2) #schedule = [(0.0, 1.0), (1.0, 0.7), (7.0, 0.7), (10.0, 1.0)] #schedule = [(0.0, 1.0), (2.0, 0.7), (8.0, 0.7), (10.0, 1.0)] schedule = [(0.0, 1.0), (2.0, 0.7), (98.0, 0.7), (100.0, 1.0)]
def run_demo(): # Read the feature-engineered data into a pandas dataframe # Data obtained from http://biostat.mc.vanderbilt.edu/DataSets demo_path = os.path.dirname(os.path.abspath(__file__)) data_path = os.path.join(demo_path, 'data', 'formatted_titanic.csv') dataset = pd.read_csv(data_path) # Rank the MI between survival and every other variable scores = {} features = list(set(dataset.columns).difference(('survived', ))) for feature in features: scores[feature] = mutual_information( prob(dataset[['survived', feature]].values), 0) labels, values = zip( *sorted(scores.items(), key=lambda pair: pair[1], reverse=True)) # Plot the MI between survival and every other variable plt.figure() ax1 = plt.subplot(1, 2, 1) ax1.set_title("Mutual Information") ax1.set_ylabel('MI Between Survival and Feature') plt.xticks(np.arange(len(labels)), labels, rotation=90) plt.bar(np.arange(len(labels)), values) # The Titanic dataset provides a familiar, intuitive example available in the public # domain. In itself, however, it is not a good fit for solving by sampling. Run naively on # this dataset, it finds numerous good solutions but is unlikely to find the exact optimal solution. # There are many techniques for reformulating problems for the D-Wave system that can # improve performance on various metrics, some of which can help narrow down good solutions # to closer approach an optimal solution. # This demo solves the problem for just the highest-scoring features. # Select 8 features with the top MI ranking found above. keep = 8 sorted_scores = sorted(scores.items(), key=lambda pair: pair[1], reverse=True) dataset = dataset[[column[0] for column in sorted_scores[0:keep]] + ["survived"]] features = list(set(dataset.columns).difference(('survived', ))) # Build a QUBO that maximizes MI between survival and a subset of features bqm = dimod.BinaryQuadraticModel.empty(dimod.BINARY) # Add biases as (negative) MI with survival for each feature for feature in features: mi = mutual_information(prob(dataset[['survived', feature]].values), 1) bqm.add_variable(feature, -mi) # Add interactions as (negative) MI with survival for each set of 2 features for f0, f1 in itertools.combinations(features, 2): cmi_01 = conditional_mutual_information( prob(dataset[['survived', f0, f1]].values), 1, 2) cmi_10 = conditional_mutual_information( prob(dataset[['survived', f1, f0]].values), 1, 2) bqm.add_interaction(f0, f1, -cmi_01) bqm.add_interaction(f1, f0, -cmi_10) bqm.normalize() # Normalize biases & interactions to the range -1, 1 # Set up a QPU sampler with a fully-connected graph of all the variables qpu_sampler = DWaveSampler(solver={'qpu': True}) embedding = find_clique_embedding( bqm.variables, 16, 16, 4, # size of the chimera lattice target_edges=qpu_sampler.edgelist) sampler = FixedEmbeddingComposite(qpu_sampler, embedding) # For each number of features, k, penalize selection of fewer or more features selected_features = np.zeros((len(features), len(features))) for k in range(1, len(features) + 1): kbqm = bqm.copy() kbqm.update(dimod.generators.combinations( features, k, strength=6)) # Determines the penalty sample = sampler.sample(kbqm, num_reads=10000).first.sample for fi, f in enumerate(features): selected_features[k - 1, fi] = sample[f] # Plot the best feature set per number of selected features ax2 = plt.subplot(1, 2, 2) ax2.set_title("Best Feature Selection") ax2.set_ylabel('Number of Selected Features') ax2.set_xticks(np.arange(len(features))) ax2.set_xticklabels(features, rotation=90) ax2.set_yticks(np.arange(len(features))) ax2.set_yticklabels(np.arange(1, len(features) + 1)) # Set a grid on minor ticks ax2.set_xticks(np.arange(-0.5, len(features)), minor=True) ax2.set_yticks(np.arange(-0.5, len(features)), minor=True) ax2.grid(which='minor', color='black') ax2.imshow(selected_features, cmap=colors.ListedColormap(['white', 'red'])) plots_path = os.path.join(demo_path, "plots.png") plt.savefig(plots_path, bbox_inches="tight") print("Your plots are saved to {}".format(plots_path))
def annealing(instance, TEST, prob=0.25, seed=42, K=1, overwrite_pickles=False, draw_figures=False, annealing_time=[2, 20, 200], # Microseconds chain_strengths=[0.1, 0.2, 0.5, 1, 2, 5, 10], penalties=[1.0, 2.0, 5.0], samples=100, sampler='Advantage_system1.1'): if sampler == 'Advantage_system1.1': chip = 'pegasus' else: chip = 'chimera' # Store the results in csv files dir_path = os.path.dirname(os.path.abspath(__file__)) embedding_path = os.path.join(dir_path, "results/embedding/") if sampler == 'DW_2000Q_6': results_path = os.path.join(dir_path, "results/dwave_chimera/") elif sampler == 'Advantage_system1.1': results_path = os.path.join(dir_path, "results/dwave_pegasus/") if instance == 'spreadsheet': # spreadsheet_name = "erdos_" + \ # str(int(100*prob)) + '_graphs_with_opt.xlsx' # spreadsheet_name = "erdos_" + \ # str(int(100*prob)) + '_graphs.xlsx' # spreadsheet_name = "erdos_" + \ # str(int(100*prob)) + '_graphs_' + str(K) + '.xlsx' spreadsheet_name = instance + \ str(int(100*prob)) + '_embedding_' + chip + '_' + str(K) + '.xlsx' spreadsheet_name = os.path.join(embedding_path, spreadsheet_name) input_data = pd.read_excel(spreadsheet_name) n0 = 0 N = input_data.shape[0] file_name = instance + str(int(100*prob)) + '_annealing' + str(K) K = 1 elif instance == 'erdos': # Parameters for random graphs N = 51 n0 = 3 K = 5 # number of graphs seed = 1 instance = "erdos_" + str(int(100*prob)) file_name = instance + '_embedding' elif instance == 'cycle': # Parameters for cycles N = 200 n0 = 100 file_name = instance + '_embedding' elif instance == 'devil': # Parameters for devil graphs N = 10 n0 = 8 file_name = instance + '_embedding' else: print("Graph type not implemented") return() # If results directory does not exist, we create it if not(os.path.exists(results_path)): print('Results directory ' + results_path + ' does not exist. We will create it.') os.makedirs(results_path) file_name = os.path.join(results_path, file_name) # time horizons and time limit in seconds if TEST: random.seed(seed) # Graph corresponding to D-Wave 2000Q or Pegasus qpu = DWaveSampler(solver=sampler) qpu_edges = qpu.edgelist qpu_nodes = qpu.nodelist X = nx.Graph() X.add_nodes_from(qpu_nodes) X.add_edges_from(qpu_edges) # nx.write_edgelist(X, os.path.join(results_path,"X.edgelist")) # X = dnx.chimera_graph(16, node_list=qpu_nodes, edge_list=qpu_edges) # X = dnx.pegasus_graph(16, node_list=qpu_nodes, edge_list=qpu_edges) if 'opt_obj_k_1' in input_data.columns: opt_sols = True else: opt_sols = False columns = ['formulation', 'chain_strength', 'embedding', 'chain_breaks', 'chain_breaks_err', 'opt_fraction', 'embedding_fixed', 'chain_breaks_fixed', 'chain_breaks_err_fixed', 'opt_fraction_fixed' ] solution = pd.DataFrame(columns=columns) for k in range(K): for n in range(n0, N): print(n) # Graph generation if instance == "spreadsheet": # Generate graph from spreadsheet Input = nx.Graph() edges = ast.literal_eval(input_data.edges[n]) Input.add_edges_from(edges) alpha = 0 elif instance == "cycle": # Cycle graphs Input = nx.cycle_graph(n) temp['id'] = "cycle_" + str(n) alpha = np.floor(n / 2) elif instance == "devil": # Devil graphs Input, alpha = devil_graphs(n) temp['id'] = "devil_rank_" + str(n) else: # Random graphs Input = nx.erdos_renyi_graph(n, prob) temp['id'] = "random_" + \ str(n) + "_" + str(prob) + "_" + str(k) alpha = 0 # Input graph parameters # Define samplers: simulated annealing or Dwave (with automatic embedding) samplers = dict() samplers['simann'] = neal.SimulatedAnnealingSampler() samplers['dwave_embed'] = EmbeddingComposite(qpu) if DRY_RUN: pass else: # Problem reformulations # Nonlinear and Linear (Laserre) reformulation reforms = ['n', 'l'] embeddable = dict.fromkeys(reforms, True) # Import embeddings best_embed = False if best_embed: best_embedding = dict.fromkeys(reforms, {}) best_embedding['n'] = ast.literal_eval( input_data.heur_best_embed_n[n]) if len(best_embedding['n']) == 0: embeddable['n'] = False print('No embedding available for nonlinear reformulation') best_embedding['l'] = ast.literal_eval( input_data.heur_best_embed_l[n]) if len(best_embedding['l']) == 0: embeddable['l'] = False print('No embedding available for linear reformulation') experiments = ['', '_fixed'] else: experiments = [''] embeddable_reforms = ( reform for reform in reforms if embeddable[reform]) for reform in embeddable_reforms: for rho in penalties: opt_matrix = np.zeros( [len(annealing_time), len(chain_strengths), len(experiments)]) if reform == 'n': Q, offset = nonlinear(Input, M=rho, draw=False) elif reform == 'l': Q, offset = linear(Input, M=rho, draw=False) bqm = dimod.BinaryQuadraticModel.from_qubo( Q, offset=offset) edges = list(itertools.chain( bqm.quadratic, ((v, v) for v in bqm.linear))) G = nx.Graph() G.add_edges_from(edges) # Add fixed embedding sampler if allowed if best_embed: # fail = 0 # min_length = X.number_of_nodes() # for n_h in range(n_heur): # h_embed = mm.find_embedding( # G, X, timeout=time_limit, random_seed=n_h) # count = 0 # for _, value in h_embed.items(): # count += len(value) # if count == 0: # fail += 1 # elif count < min_length: # best_embed = h_embed # min_length = count # samplers['dwave'] = FixedEmbeddingComposite( # DWaveSampler(), embedding=best_embed) # else: # samplers.pop('dwave', None) samplers['dwave'] = FixedEmbeddingComposite( qpu, embedding=best_embedding[reform]) pickle_path = os.path.join( results_path, file_name, str(n), reform) if not(os.path.exists(pickle_path)): print('Pickled results directory ' + pickle_path + ' does not exist. We will create it.') os.makedirs(pickle_path) idx_i = 0 for ann_time in annealing_time: results = pd.DataFrame(columns=columns) results_name = instance + '_chains_' + \ reform + '_' + str(ann_time) + '.csv' results_name = os.path.join( results_path, results_name) temp = dict() idx_j = 0 for c in chain_strengths: # Identification temp['formulation'] = reform temp['penalty'] = rho if c == "d": from dwave.embedding.chain_strength import uniform_torque_compensation chain_strength = uniform_torque_compensation( bqm) temp['chain_strength'] = chain_strength/max( abs(min(Q.values())), abs(max(Q.values()))) else: # chain_strength = max(Q.min(), Q.max(), key=abs)*c chain_strength = max( abs(min(Q.values())), abs(max(Q.values())))*c temp['chain_strength'] = c idx_k = 0 for kind in experiments: pickle_name = "chain_str_" + \ str(c) + "_" + str(ann_time) + \ "_" + str(int(rho)) + kind + ".p" pickle_name = os.path.join( pickle_path, pickle_name) if os.path.exists(pickle_name) and not overwrite_pickles: response = pickle.load( open(pickle_name, "rb")) if response is None: embeddable[reform] = False else: # Here is where the D-Wave run happens if kind == '_fixed' and best_embed: response = samplers['dwave'].sample( bqm, num_reads=samples, return_embedding=True, chain_strength=chain_strength, annealing_time=ann_time) elif kind == '': try: response = samplers['dwave_embed'].sample( bqm, num_reads=samples, return_embedding=True, chain_strength=chain_strength, annealing_time=ann_time) except ValueError as e: embeddable[reform] = False response = None print(pickle_name) print(e) print('error type: ', type(e)) pickle.dump(response, open( pickle_name, "wb"), protocol=pickle.HIGHEST_PROTOCOL) if embeddable[reform]: temp['embedding' + kind] = response.info['embedding_context']['embedding'] # plot_energies(response, title=pickle_name) if 'chain_break_fraction' in response.record.dtype.names: temp['chain_breaks' + kind] = np.mean(response.record.chain_break_fraction) temp['chain_breaks_err' + kind] = np.std(response.record.chain_break_fraction) energies = response.data_vectors['energy'] occurrences = response.data_vectors['num_occurrences'] counts = {} for index, energy in enumerate(energies): if energy in counts.keys(): counts[energy] += occurrences[index] else: counts[energy] = occurrences[index] total_counts = sum(occurrences) if opt_sols: temp['opt_fraction' + kind] = sum(counts[key] for key in [ -input_data.opt_obj_k_1[n]] if key in counts.keys())/total_counts opt_matrix[idx_i, idx_j, idx_k] = sum( counts[key] for key in [-input_data.opt_obj_k_1[n]] if key in counts.keys())/total_counts else: temp['opt_fraction' + kind] = sum( counts[key] for key in [min(energies)] if key in counts.keys())/total_counts opt_matrix[idx_i, idx_j, idx_k] = sum( counts[key] for key in [min(energies)] if key in counts.keys())/total_counts idx_k += 1 results = results.append( temp, ignore_index=True) solution = solution.append( temp, ignore_index=True) solution.to_csv(file_name + ".csv") idx_j += 1 if draw_figures: plt.figure() plt.errorbar(results.chain_strength, results.chain_breaks, yerr=results.chain_breaks_err, fmt='o', capsize=3) plt.errorbar(results.chain_strength, results.chain_breaks_fixed, yerr=results.chain_breaks_err_fixed, fmt='o', capsize=3) plt.legend( ['Random Embedding', 'Best Embedding']) plt.xscale('log') plt.ylabel('Chain break fraction') plt.xlabel( 'Chain strength (factor of maximum coefficient in Q)') plt.title( 'Chain break fraction vs. chain strength \n (ref = ' + reform + ', t_ann = ' + str(ann_time) + ', rho = ' + str(int(rho)) + ')') plt.figure() plt.plot(results.chain_strength, results.opt_fraction, 'o', linestyle='--') # plt.plot(results.chain_strength, # results.opt_fraction, 'o', linestyle='--') # plt.plot(results.chain_strength, # results.feas_fraction, 's', linestyle='--') plt.plot(results.chain_strength, results.opt_fraction_fixed, 'o', linestyle='-') # plt.plot(results.chain_strength, # results.opt_fraction_fixed, 'o', linestyle='-') # plt.plot(results.chain_strength, # results.feas_fraction_fixed, 's', linestyle='-') plt.ylim([0, 1]) plt.xscale('log') plt.ylabel('Optimal solution fraction') plt.xlabel( 'Chain strength (factor of maximum coefficient in Q)') plt.title( 'Solutions found fraction vs. chain strength \n (ref = ' + reform + ', t_ann = ' + str(ann_time) + ', rho = ' + str(int(rho)) + ')') plt.legend(['Random Embedding', 'Best Embedding']) idx_i += 1 if draw_figures: for k in range(len(experiments)): fig, ax = plt.subplots() colormesh = ax.imshow( opt_matrix[:, 4:, k], vmin=0, vmax=1 ) ax.set_title( 'Minimum solutions probability embedding' + experiments[k] + ' \n (ref=' + reform + ', ' + chip + ')') plt.xlabel( 'Chain strength (factor of maximum coefficient in Q)') plt.ylabel('Annealing time [microseconds]') fig.colorbar(colormesh, ax=ax) plt.yticks([0, 1, 2]) fig.canvas.draw() labels_x = [item.get_text() for item in ax.get_xticklabels()] labels_x = chain_strengths[3:] labels_y = [item.get_text() for item in ax.get_yticklabels()] labels_y = annealing_time ax.set_xticklabels(labels_x) ax.set_yticklabels(labels_y) plt.show() sol_total = pd.DataFrame.from_dict(solution) sol_total.to_excel(os.path.join(results_path, file_name + ".xlsx"))
def main(args): num_reads = int(args.nreads) dry_run = bool(args.dry_run) if dry_run: print("WARNING: dry run. There will be no results at the end.") # truth-level: x = [5, 8, 12, 6, 2] # response matrix: R = [[1, 2, 0, 0, 0], [1, 2, 1, 1, 0], [0, 1, 3, 2, 0], [0, 2, 2, 3, 2], [0, 0, 0, 1, 2]] # pseudo-data: d = [12, 32, 40, 15, 10] # convert to numpy arrays x = np.array(x, dtype='uint8') R = np.array(R, dtype='uint8') b = np.array(d, dtype='uint8') # closure test b = np.dot(R, x) n = 4 N = x.shape[0] print("INFO: N bins:", N) print("INFO: n-bits encoding:", n) lmbd = np.uint8(args.lmbd) # regularization strength D = laplacian(N) # convert to bits x_b = discretize_vector(x, n) b_b = discretize_vector(b, n) R_b = discretize_matrix(R, n) D_b = discretize_matrix(D, n) print("INFO: Truth-level x:") print(x, x_b) print("INFO: pseudo-data b:") print(b, b_b) print("INFO: Response matrix:") print(R) print(R_b) print("INFO: Laplacian operator:") print(D) print(D_b) print("INFO: regularization strength:", lmbd) # Create QUBO operator # linear constraints h = {} for j in range(n * N): idx = (j) h[idx] = 0 for i in range(N): h[idx] += (R_b[i][j] * R_b[i][j] - 2 * R_b[i][j] * b[i] + lmbd * D_b[i][j] * D_b[i][j]) # quadratic constraints J = {} for j in range(n * N): for k in range(j + 1, n * N): idx = (j, k) J[idx] = 0 for i in range(N): J[idx] += 2 * (R_b[i][j] * R_b[i][k] + lmbd * D_b[i][j] * D_b[i][k]) # QUBO bqm = dimod.BinaryQuadraticModel(linear=h, quadratic=J, offset=0.0, vartype=dimod.BINARY) print("INFO: solving the QUBO model...") print("INFO: running on QPU") hardware_sampler = DWaveSampler() print("INFO: finding optimal minor embedding...") embedding = get_embedding_with_short_chain( J, tries=1, processor=hardware_sampler.edgelist, verbose=True) if embedding is None: raise ValueError("ERROR: could not find embedding") sampler = FixedEmbeddingComposite(hardware_sampler, embedding) print("INFO: creating DWave sampler...") print("INFO: annealing (n_reads=%i) ..." % num_reads) print("INFO: Connected to", hardware_sampler.properties['chip_id']) print("INFO: max anneal schedule points: {}".format( hardware_sampler.properties["max_anneal_schedule_points"])) print("INFO: annealing time range: {}".format( hardware_sampler.properties["annealing_time_range"])) schedule = make_reverse_anneal_schedule(s_target=0.99, hold_time=1, ramp_up_slope=0.2) neal_sampler = neal.SimulatedAnnealingSampler() initial_result = sampler.sample(bqm, num_reads=num_reads).aggregate() neal_result = neal_sampler.sample(bqm, num_reads=num_reads).aggregate() reverse_anneal_params = dict(anneal_schedule=schedule, initial_state=initial_result.first.sample, reinitialize_state=True) solver_parameters = { 'num_reads': num_reads, 'auto_scale': True, **reverse_anneal_params } print(schedule) result = sampler.sample(bqm, **solver_parameters) reverse_anneal_params = dict(anneal_schedule=schedule, initial_state=neal_result.first.sample, reinitialize_state=True) solver_parameters = { 'num_reads': num_reads, 'auto_scale': True, **reverse_anneal_params } result2 = sampler.sample(bqm, **solver_parameters) print("Neal results") print_results(neal_result, n) print("Reverse annealing on Neal results") print_results(result2, n) print("QPU results") print_results(initial_result, n) print("Reverse annealing on QPU results") print_results(result, n)
Q[(i, i)] += -1 Q[(j, j)] += -1 Q[(i, j)] += 2 # ------- Run our QUBO on the QPU ------- # Set up QPU parameters chain_strength = 0.1 num_reads = 10 # Run the QUBO on a solver with the specified topology QPU = DWaveSampler(solver={'topology__type__eq': 'chimera'}) embedding = find_embedding(Q, QPU.edgelist) print("\nEmbedding found:\n", embedding) sampler = FixedEmbeddingComposite(QPU, embedding) response = sampler.sample_qubo(Q, chain_strength=chain_strength, num_reads=num_reads, label='Training - Embedding') print("\nSampleset:") print(response) # ------- Print results to user ------- print("\nSolutions:") print('-' * 60) print('{:>15s}{:>15s}{:^15s}{:^15s}'.format('Set 0', 'Set 1', 'Energy', 'Cut Size')) print('-' * 60) for sample, E in response.data(fields=['sample', 'energy']):
if run_dwave != 0: # Sampler/Annealing parameters params["chainstrength_P"] = float(0.5) params["chainstrength"] = float( params["chainstrength_P"] * params["max_bias_final"] ) # Default 1 | Good rule of thumb is to have the same order of magnitude as Qubo. params["numruns"] = 10 # Default 1000 params["anneal_time"] = 20 # Default 20 #----------------------------- print( f"Running D-Wave w/ chainstrength {params['chainstrength_P']:.2f}|{params['chainstrength']:.2f} (%|final) & numruns {params['numruns']:d} & anneal_time {params['anneal_time']:d}" ) composite = FixedEmbeddingComposite(sampler, embedding=embedding) response = composite.sample_qubo(Qubo, annealing_time=params["anneal_time"], chain_strength=params["chainstrength"], num_reads=params["numruns"]) print("Results:\n") print_result(response, params, time=0, mute=0, file=1) #dwave.inspector.show(response) # ---------------------- \| Utility Functions |/ ---------------------- # # minimum possible energy: -283987.43787980796 |\ 173.045734368 # maximum possible energy: -2466607.9822456012 |\ 480.1178932
def objective(args): lmdb = args['lmbd'] num_reads = args['num_reads'] n = args['num_bits'] annealing_time = args['annealing_time'] x_b = discretize_vector(x, n) z_b = discretize_vector(z, n) d_b = discretize_vector(d, n) R_b = discretize_matrix(R0, n) D_b = discretize_matrix(D, n) # Create QUBO operator #Q = np.zeros([n*N, n*N]) S = {} h = {} J = {} # linear constraints for j in range(n * N): h[(j)] = 0 for i in range(N): h[(j)] += (R_b[i][j] * R_b[i][j] - 2 * R_b[i][j] * d[i] + lmbd * D_b[i][j] * D_b[i][j]) S[(j, j)] = h[(j)] # quadratic constraints for j in range(n * N): for k in range(j + 1, n * N): J[(j, k)] = 0 for i in range(N): J[(j, k)] += 2 * (R_b[i][j] * R_b[i][k] + lmbd * D_b[i][j] * D_b[i][k]) S[(j, k)] = J[(j, k)] bqm = dimod.BinaryQuadraticModel(linear=h, quadratic=J, offset=0.0, vartype=dimod.BINARY) embedding = get_embedding_with_short_chain( S, tries=5, processor=hardware_sampler.edgelist, verbose=False) sampler = FixedEmbeddingComposite(hardware_sampler, embedding) solver_parameters = { 'num_reads': num_reads, 'auto_scale': True, 'annealing_time': annealing_time, # default: 20 us #'anneal_schedule': anneal_sched_custom(id=3), 'num_spin_reversal_transforms': 2, # default: 2 } results = sampler.sample(bqm, **solver_parameters).aggregate() best_fit = results.first energy_bestfit = best_fit.energy q = np.array(list(best_fit.sample.values())) y = compact_vector(q, n) dof = N - 1 chi2, p = stats.chisquare(y, z, dof) chi2dof = chi2 / float(dof) hamm = hamming(z_b, q) return { 'loss': hamm, # chi2dof, 'status': hp.STATUS_OK, 'diffxs': y, 'q': q, 'hamming': hamm, 'lmbd': lmbd, 'num_reads': num_reads, 'num_bits': n, 'annealing_time': annealing_time, }
def solve(self): self.n_bins_truth = self._data.x.shape[0] self.n_bins_reco = self._data.d.shape[0] if not self._data.R.shape[1] == self.n_bins_truth: raise Exception( "Number of bins at truth level do not match between 1D spectrum (%i) and response matrix (%i)" % (self.n_bins_truth, self._data.R.shape[1])) if not self._data.R.shape[0] == self.n_bins_reco: raise Exception( "Number of bins at reco level do not match between 1D spectrum (%i) and response matrix (%i)" % (self.n_bins_reco, self._data.R.shape[0])) self.convert_to_binary() print("INFO: N bins:", self._data.x.shape[0]) print("INFO: n-bits encoding:", self.rho) print("INFO: Signal truth-level x:") print(self._data.x) print("INFO: pseudo-data b:") print(self._data.d) print("INFO: Response matrix:") print(self._data.R) self.Q = self.make_qubo_matrix() self._bqm = dimod.BinaryQuadraticModel.from_numpy_matrix(self.Q) print("INFO: solving the QUBO model (size=%i)..." % len(self._bqm)) if self.backend in [Backends.cpu]: print("INFO: running on CPU...") self._results = dimod.ExactSolver().sample(self._bqm) self._status = StatusCode.success elif self.backend in [Backends.sim]: num_reads = self.solver_parameters['num_reads'] print("INFO: running on simulated annealer (neal), num_reads=", num_reads) sampler = neal.SimulatedAnnealingSampler() self._results = sampler.sample(self._bqm, num_reads=num_reads).aggregate() self._status = StatusCode.success elif self.backend in [ Backends.qpu, Backends.qpu_hinoise, Backends.qpu_lonoise, Backends.hyb, Backends.qsolv ]: print("INFO: running on QPU") config_file = self.get_config_file() self._hardware_sampler = DWaveSampler(config_file=config_file) print("INFO: QPU configuration file:", config_file) print("INFO: finding optimal minor embedding...") n_bits_avg = np.mean(self._encoder.rho) thr = 4. / float(self.n_bins_truth) n_tries = 5 if n_bits_avg < thr else 10 J = qubo_quadratic_terms_from_np_array(self.Q) embedding = self.find_embedding(J, n_tries) print("INFO: creating DWave sampler...") sampler = FixedEmbeddingComposite(self._hardware_sampler, embedding) if self.backend in [ Backends.qpu, Backends.qpu_hinoise, Backends.qpu_lonoise ]: print("INFO: Running on QPU") params = self.solver_parameters self._results = sampler.sample(self._bqm, **params).aggregate() self._status = StatusCode.success elif self.backend in [Backends.hyb]: print("INFO: hybrid execution") import hybrid num_reads = self.solver_parameters['num_reads'] # Define the workflow # hybrid.EnergyImpactDecomposer(size=len(bqm), rolling_history=0.15) iteration = hybrid.RacingBranches( hybrid.InterruptableTabuSampler(), hybrid.EnergyImpactDecomposer(size=len(self._bqm) // 2, rolling=True) | hybrid.QPUSubproblemAutoEmbeddingSampler( num_reads=num_reads) | hybrid.SplatComposer()) | hybrid.ArgMin() #workflow = hybrid.LoopUntilNoImprovement(iteration, convergence=3) workflow = hybrid.Loop(iteration, max_iter=20, convergence=3) init_state = hybrid.State.from_problem(self._bqm) self._results = workflow.run(init_state).result().samples self._status = StatusCode.success # show execution profile print("INFO: timing:") workflow.timers hybrid.print_structure(workflow) hybrid.profiling.print_counters(workflow) elif self.backend in [Backends.qsolv]: print("INFO: using QBsolve with FixedEmbeddingComposite") self._results = QBSolv().sample_qubo(S, solver=sampler, solver_limit=5) self._status = StatusCode.success else: raise Exception("ERROR: unknown backend", self.backend) print("DEBUG: status =", self._status) return self._status