def get_properties_and_solve(solver): # problem 1. h1 = [0] * solver.properties["num_qubits"] h1[solver.properties["qubits"][0]] = 1 J1 = {(i, j): -1 for i, j in solver.properties["couplers"]} # problem 2 h2 = [0] * solver.properties["num_qubits"] J2 = {(i, j): 1 for i, j in solver.properties["couplers"]} # get solver's properties print "Solver's properties: ", solver.properties print "Number of qubits: ", solver.properties["num_qubits"] print "Working qubits: ", solver.properties["qubits"] print "Working couplers: ", solver.properties["couplers"] # solve Ising problems asynchronously answer1 = async_solve_ising(solver, h1, J1, num_reads=10) if "num_spin_reversal_transforms" in solver.properties["parameters"]: if "postprocess" in solver.properties["parameters"]: answer2 = async_solve_ising(solver, h2, J2, num_reads=20, postprocess='sampling', num_spin_reversal_transforms=1) submitted_problems = [answer1, answer2] else: print "Solver does not support postprocessing" submitted_problems = [answer1] else: print "Solver does not support spin reversal transforms" submitted_problems = [answer1] # wait for 1 problem to finish, with a maximum timeout of 30 seconds done = await_completion(submitted_problems, 1, 30) # print completed problem results; cancel incomplete for problem in submitted_problems: if problem.done(): try: print "answer:", problem.result() except Exception as e: print e.message else: problem.cancel()
def test_await_completion_example(self): from dwave_sapi2.remote import RemoteConnection from dwave_sapi2.core import async_solve_ising, await_completion # get a solver solver = RemoteConnection().get_solver(solver_name) h = [1, -1, 1, 1, -1, 1, 1] J = {(0, 6): -10} p1 = async_solve_ising(solver, h, J, num_reads=10) p2 = async_solve_ising(solver, h, J, num_reads=20) min_done = 2 timeout = 1.0 done = await_completion([p1, p2], min_done, timeout) if done: self.is_answer(p1.result()) self.is_answer(p2.result())
def test_async_solve_ising_example(self): from dwave_sapi2.remote import RemoteConnection from dwave_sapi2.core import async_solve_ising, await_completion # get a solver solver = RemoteConnection().get_solver(solver_name) h = [1, -1, 1, 1, -1, 1, 1] J = {(0, 6): -10} submitted_problem = async_solve_ising(solver, h, J, num_reads=10) # Wait until solved await_completion([submitted_problem], 1, float('inf')) # display result self.is_answer(submitted_problem.result())
def test_async_solve_ising(): h = [0, 1, -1, 0, 1] j = {(0, 1): -1, (1, 2): 1, (2, 4): -1} problem = { (0, 1): -1, (1, 1): 1, (1, 2): 1, (2, 2): -1, (2, 4): -1, (4, 4): 1 } params = {'param': 'yes', 'another': 'sure'} ret = 'submitted-problem' solver = flexmock(properties={}) solver.should_receive('submit').with_args('ising', problem, params).and_return(ret) assert async_solve_ising(solver, h, j, param='yes', another='sure') == ret
def submit_dwave_problem(verbosity, physical, samples, anneal_time, spin_revs, postproc, discard): "Submit a QMI to the D-Wave." # Map abbreviated to full names for postprocessing types. postproc = { "none": "", "opt": "optimization", "sample": "sampling" }[postproc] # Determine the annealing time to use. if anneal_time == None: anneal_time = get_default_annealing_time() # Compute a list of the number of samples to take each iteration # and the number of spin reversals to perform. samples_list = compute_sample_counts(samples, anneal_time) spin_rev_list = compute_spin_rev_counts(spin_revs, samples_list) nqmis = len(samples_list) # Number of (non-unique) QMIs to submit # Submit one or more QMIs to the D-Wave. problems = [] for i in range(nqmis): solver_params = dict(chains=physical.embedding, num_reads=samples_list[i], annealing_time=anneal_time, num_spin_reversal_transforms=spin_rev_list[i], postprocess=postproc) unused_params = dict() while True: # Repeatedly remove parameters the particular solver doesn't like # until it actually works -- or fails for a different reason. try: weight_list = qmasm.dict_to_list(physical.weights) p = async_solve_ising(qmasm.solver, weight_list, physical.strengths, **solver_params) problems.append(p) break except ValueError as e: # Is there a better way to extract the failing symbol than a # regular expression match? bad_name_match = re.match(r'"(.*?)"', str(e)) if bad_name_match == None: raise e bad_name = bad_name_match.group(1) unused_params[bad_name] = solver_params[bad_name] del solver_params[bad_name] except RuntimeError as e: qmasm.abend(e) if verbosity >= 2: report_parameters_used(solver_params, unused_params) # Output problem IDs as soon as they become available. if verbosity >= 1: try: while any([ problems[i].status()["problem_id"] == "" for i in range(nqmis) ]): await_completion(problems, nqmis, 1) report_subproblems_submitted(nqmis, problems, samples_list, spin_rev_list) except KeyError: pass # Not all solvers support "problem_id". # Wait for the solver to complete. if verbosity >= 2: sys.stderr.write("Number of subproblems completed:\n\n") cdigits = len(str(nqmis)) # Digits in the number of completed QMIs tdigits = len(str(nqmis * 5)) # Estimate 5 seconds per QMI submission start_time = time.time() done = False while not done: done = await_completion(problems, nqmis, 10) if verbosity >= 2: ncomplete = sum([ problems[i].status()["state"] == "DONE" for i in range(nqmis) ]) sys.stderr.write( " %*d of %d (%3.0f%%) after %*.0f seconds\n" % (cdigits, ncomplete, nqmis, 100.0 * float(ncomplete) / float(nqmis), tdigits, time.time() - start_time)) if verbosity >= 2: sys.stderr.write("\n") answers = [p.result() for p in problems] # Tally the occurrences of each solution answer = merge_answers(answers) solutions = answer["solutions"] semifinal_answer = unembed_answer(solutions, physical.embedding, broken_chains="minimize_energy", h=physical.weights, j=physical.strengths) try: num_occurrences = { tuple(k): v for k, v in zip(semifinal_answer, answer["num_occurrences"]) } except KeyError: num_occurrences = {tuple(a): 1 for a in semifinal_answer} # Discard solutions with broken pins or broken chains unless instructed # not to. valid_solns = [s for s in solutions if solution_is_intact(physical, s)] num_not_broken = len(valid_solns) if discard in ["yes", "maybe"]: final_answer = unembed_answer(valid_solns, physical.embedding, broken_chains="discard", h=physical.weights, j=physical.strengths) if discard == "no" or (discard == "maybe" and len(final_answer) == 0): final_answer = semifinal_answer return answer, final_answer, num_occurrences, num_not_broken
def runDW(h, J, embedding, stop_point=0.25, num_reads=1000, coupling_init=1.0, coupling_increment=0.1, min_solver_calls=1, max_solver_calls=1000, method='vote', last=True, num_gauges=1, solver_name='NASA', annealing_time=20): ''' Submits an instance to DW. Parameters ----- h : list, a list of fields J : a dictionary, where keys are a tuple corresponding to the coupling embedding : a list of lists. Can use DW sapi to generate stop_point :float, default: 0.25. Stop increasing coupling strength when returns at least this fraction of solutions are unbroken. num_reads: int, default: 1000. The number of reads. coupling_init: float, default: 1.0. The initial value of coupling, the value of the ferromagnetic coupling between physical qubits. If number of unbroken of solutions is not at least stop_point, then the magnitude of coupling is incremented by coupling_increment. Note however, that the though we specify coupling_init as positive, the coupling is negative. For example, Suppose coupling_init=1.0, coupling_increment (defined below) is 0.1, and stop_point = 0.25. The initial physical ferromagnetic coupling strength will be -1.0. If stop_point isn't reached, coupling is incremented by 0.1, or in other words, the new chain strength is -1.1. coupling is incremented by coupling_increment until stop_point is reached. coupling_increment: float, default: 0.1. Increment of coupling strength, min_solver_calls: int, default: 1. The minimum number of solver calls. max_solver_calls: int, default: 1000. The maximum number of solver calls. method: str, 'minimize_energy', 'vote', or 'discard', default: 'minimize_energy' How to deal with broken chains. 'minimize_energy' uses the energy minimization decoding. 'vote' uses majority vote decoding. 'discard' discard broken chains. last: bool, default: True If True, return the last num_reads solutions. If False, return the first num_reads solutions. num_gauges: int, default: 1 Number of gauge transformations. solver_name: str, 'NASA', 'ISI', or 'DW', default: 'NASA' Which solver to use. 'NASA' uses NASA's DW2000Q. 'ISI' uses ISI's DW2X. 'DW' uses DW's DW2000Q. Returns ------- A tuple of sols, c, ratio sols: numpy ndarray, shape = [num_reads, num_spins] Solutions where each row is a set of spins (num_spins dependent on solver) c: float The final value of the coupling strength used ratio: float The final fraction of unbroken solutions returned at coupling_strength c ''' meths = ['discard', 'vote', 'minimize_energy'] assert (method in meths) solver = connectSolver(solver_name) A = get_hardware_adjacency(solver) # embed problem (h0, j0, jc, new_emb) = embed_problem(h, J, embedding, A) # scale problem maxjh = max(max(np.abs(h0)), max(np.abs(j0.values()))) h0 = [el / maxjh for el in h0] j0 = {ij: v / maxjh for ij, v in zip(j0.keys(), j0.values())} ratio = 0 sols = [] ncalls = 0 l = coupling_init print coupling_init jc = dict.fromkeys(jc, -l) emb_j = j0.copy() emb_j.update(jc) kwargs = { 'num_reads': num_reads, 'num_spin_reversal_transforms': num_gauges, 'answer_mode': 'raw', 'annealing_time': annealing_time } # iteratively increase ferromagentic strength until returns a certain ratio # of solutions where there are no broken chains while ratio <= stop_point and ncalls < max_solver_calls: jc = dict.fromkeys(jc, -l) emb_j = j0.copy() emb_j.update(jc) if solver_name == 'ISI': _check_wait() problem = async_solve_ising(solver, h0, emb_j, **kwargs) await_completion([problem], 1, 50000) answer = problem.result() result = unembed_answer(answer['solutions'], new_emb, broken_chains='discard', h=h, j=J) sols += result nSols = len(result) l = l + coupling_increment ratio = nSols / float(len(answer['solutions'])) ncalls = ncalls + 1 print ratio # Don't remember why do this. Maybe for good measure if method == 'discard': nAdd = int(1 / ratio) + 1 else: nAdd = 1 l = l - coupling_increment for n in range(nAdd): if solver_name == 'ISI': _check_wait() problem = async_solve_ising(solver, h0, emb_j, **kwargs) await_completion([problem], 1, 50000) answer = problem.result() result = unembed_answer(answer['solutions'], new_emb, broken_chains=method, h=h, j=J) sols += result if len(sols) < num_reads: # try one more time problem = async_solve_ising(solver, h0, emb_j, **kwargs) await_completion([problem], 1, 50000) answer = problem.result() result = unembed_answer(answer['solutions'], new_emb, broken_chains=method, h=h, j=J) sols += result if last: if len(sols) >= num_reads: sols = sols[-num_reads:] else: print 'WARNING! DID NOT COLLECT ENOUGH READS...continuing' else: sols = sols[:num_reads] return (np.array(sols, dtype=np.int8), l, ratio)
def runDW_batch(h, J, embedding, stop_point=0.25, num_reads=1000, coupling_init=1.0, coupling_increment=0.1, min_solver_calls=1, max_solver_calls=1000, method='vote', last=True, num_gauges=1, solver_name='NASA', returnProblems=True): ''' Submits an instance to DW as a batch. Note that when used, sometimes the solutions are markedly different than when use runDW (no batch). Generally using run_DW() seems to be a better idea Parameters ----- h : list of lists, with each list is a list of fields J : a list of dictionary, where keys are a tuple corresponding to the coupling. Should be the same length as h. embedding : a list of lists. Can use DW sapi to generate stop_point :float, default: 0.25. Stop increasing coupling strength when returns at least this fraction of solutions are unbroken. num_reads: int, default: 1000. The number of reads. coupling_init: float, default: 1.0. The initial value of coupling, the value of the ferromagnetic coupling between physical qubits. If number of unbroken of solutions is not at least stop_point, then the magnitude of coupling is incremented by coupling_increment. Note however, that the though we specify coupling_init as positive, the coupling is negative. For example, Suppose coupling_init=1.0, coupling_increment (defined below) is 0.1, and stop_point = 0.25. The initial physical ferromagnetic coupling strength will be -1.0. If stop_point isn't reached, coupling is incremented by 0.1, or in other words, the new chain strength is -1.1. coupling is incremented by coupling_increment until stop_point is reached. coupling_increment: float, default: 0.1. Increment of coupling strength, min_solver_calls: int, default: 1. The minimum number of solver calls. max_solver_calls: int, default: 1000. The maximum number of solver calls. method: str, 'minimize_energy', 'vote', or 'discard', default: 'minimize_energy' How to deal with broken chains. 'minimize_energy' uses the energy minimization decoding. 'vote' uses majority vote decoding. 'discard' discard broken chains. last: bool, default: True If True, return the last num_reads solutions. If False, return the first num_reads solutions. num_gauges: int, default: 1 Number of gauge transformations. solver_name: str, 'NASA', 'ISI', or 'DW', default: 'NASA' Which solver to use. 'NASA' uses NASA's DW2000Q. 'ISI' uses ISI's DW2X. 'DW' uses DW's DW2000Q. returnProblems: bool Determines what it returns. If True, return problems, new_emb. If False return solutions only Returns ------- if returnProblems is True, returns problems, new_emb (to be used with get_async_sols) problems: list list of problems from async_solve_ising new_emb: list list of embeddings returned from embed_problem if returnProblems is False, returns solutions sols: np array Array of solutions ''' meths = ['discard', 'vote', 'minimize_energy'] assert (method in meths) if solver_name == 'NASA': url = 'https://qfe.nas.nasa.gov/sapi' token = 'NASA-870f7ee194d029923ad8f9cd063de357ba53b838' remote_connection = RemoteConnection(url, token) solver = remote_connection.get_solver('C16') elif solver_name == 'ISI': url = 'https://usci.qcc.isi.edu/sapi' token = 'QUCB-089028555cb44b4f3da34cd4c6dd4a73ec859bc8' remote_connection = RemoteConnection(url, token) solver = remote_connection.get_solver('DW2X') elif solver_name == 'DW': url = 'https://cloud.dwavesys.com/sapi' token = 'usc-171bafd63a1b07635fd696db283ad4c28b820d14' remote_connection = RemoteConnection(url, token) solver = remote_connection.get_solver('DW_2000Q_2_1') else: NameError('Unrecognized solver name') A = get_hardware_adjacency(solver) h0 = [] j0 = [] jc = [] new_emb = [] for n in range(len(h)): (h0t, j0t, jct, new_embt) = embed_problem(h[0], J[0], embedding, A) maxjh = max(max(np.abs(h0t)), max(np.abs(j0t.values()))) h0t = [el / maxjh for el in h0t] j0t = {ij: v / maxjh for ij, v in zip(j0t.keys(), j0t.values())} h0.append(h0t) j0.append(j0t) jc.append(jct) new_emb.append(new_embt) ncalls = 0 sols = np.empty(len(h0), dtype=object) if isinstance(coupling_init, list): l = coupling_init else: l = [coupling_init] * len(h) print np.unique(l) kwargs = { 'num_reads': num_reads, 'num_spin_reversal_transforms': num_gauges, 'answer_mode': 'raw' } problem = [] for n in range(len(h0)): jct = dict.fromkeys(jc[n], -l[n]) emb_j = j0[n].copy() emb_j.update(jct) if solver_name == 'ISI': _check_wait() problem.append(async_solve_ising(solver, h0[n], emb_j, **kwargs)) await_completion(problem, len(h), 50000) if returnProblems: return problem, new_emb for n in range(len(h0)): answer = problem[n].result() sols[n] = np.array(unembed_answer(answer['solutions'], new_emb[n], broken_chains=method, h=h[n], j=J[n]), dtype=np.int8) # return problem,new_emb return np.array(sols)
def main(args): if args.input_file == None: data = json.load(sys.stdin) else: with open(args.input_file) as file: data = json.load(file) bqpjson.validate(data) if data['variable_domain'] != 'spin': print_err('only spin domains are supported. Given %s' % data['variable_domain']) quit() if data['scale'] != 1.0: print_err('A non-one scaling value is not yet supported. Given %s' % data['scale']) quit() if data['offset'] != 0.0: print_err('A non-zero offset value is not yet supported. Given %s' % data['offset']) quit() # A core assumption of this solver is that the given bqpjson data will magically be compatable with the given D-Wave QPU dw_url = args.dw_url dw_tokens = [args.dw_token] dw_solver_name = args.dw_solver_name dw_chip_id = None if 'dw_url' in data['metadata']: dw_url = data['metadata']['dw_url'].encode('ascii', 'ignore') print_err('using d-wave url provided in data file: %s' % dw_url) if 'dw_solver_name' in data['metadata']: dw_solver_name = data['metadata']['dw_solver_name'].encode( 'ascii', 'ignore') print_err('using d-wave solver name provided in data file: %s' % dw_solver_name) if 'dw_chip_id' in data['metadata']: dw_chip_id = data['metadata']['dw_chip_id'].encode('ascii', 'ignore') print_err('found d-wave chip id in data file: %s' % dw_chip_id) if hasattr(args, 'dw_tokens') and args.dw_tokens != None: dw_tokens = args.dw_tokens if dw_url is None or dw_tokens[0] is None or dw_solver_name is None: print_err('d-wave solver parameters not found') quit() remote_connections = [] for dw_token in dw_tokens: if args.dw_proxy is None: remote_connections.append(RemoteConnection(dw_url, dw_token)) else: remote_connections.append( RemoteConnection(dw_url, dw_token, args.dw_proxy)) solvers = [rc.get_solver(dw_solver_name) for rc in remote_connections] if not dw_chip_id is None: if solvers[0].properties['chip_id'] != dw_chip_id: print_err( 'WARNING: chip ids do not match. data: %s hardware: %s' % (dw_chip_id, solvers[0].properties['chip_id'])) solution_metadata = { 'dw_url': dw_url, 'dw_solver_name': dw_solver_name, 'dw_chip_id': solvers[0].properties['chip_id'], } h = [0] * (max(data['variable_ids']) + 1) for lt in data['linear_terms']: i = lt['id'] assert (i < len(h)) h[i] = lt['coeff'] J = {} for qt in data['quadratic_terms']: i = qt['id_tail'] j = qt['id_head'] assert (not (i, j) in J) J[(i, j)] = qt['coeff'] params = { 'auto_scale': False, 'annealing_time': args.annealing_time, 'num_reads': args.solve_num_reads } if args.spin_reversal_transform_rate != None: params[ 'num_spin_reversal_transforms'] = args.solve_num_reads / args.spin_reversal_transform_rate print_err('') print_err('total num reads: {}'.format(args.num_reads)) print_err('d-wave parameters:') for k, v in params.items(): print_err(' {} - {}'.format(k, v)) print_err('') print_err('starting collection:') submitted_problems = [] num_reads_remaining = args.num_reads problem_index = 0 while num_reads_remaining > 0: num_reads = min(args.solve_num_reads, num_reads_remaining) params['num_reads'] = num_reads print_err(' submit {} of {} remaining'.format(num_reads, num_reads_remaining)) solver_index = problem_index % len(solvers) submitted_problems.append({ 'problem': async_solve_ising(solvers[solver_index], h, J, **params), 'start_time': datetime.datetime.utcnow(), 'params': {k: v for k, v in params.items()} }) num_reads_remaining -= num_reads problem_index += 1 #answers = solve_ising(solver, h, J, **params) print_err(' waiting...') solutions_all = None for i, submitted_problem in enumerate(submitted_problems): problem = submitted_problem['problem'] await_completion([problem], 1, float('inf')) print_err(' collect {} of {} solves'.format(i + 1, len(submitted_problems))) answers = problem.result() solutions = answers_to_solutions(answers, data['variable_ids'], submitted_problem['start_time'], datetime.datetime.utcnow(), submitted_problem['params'], solution_metadata) if solutions_all != None: combis.combine_solution_data(solutions_all, solutions) else: solutions_all = solutions combis.merge_solution_counts(solutions_all) print_err('') total_collected = sum(solution['num_occurrences'] for solution in solutions_all['solutions']) print_err('total collected: {}'.format(total_collected)) for i, solution in enumerate(solutions_all['solutions']): print_err(' %f - %d' % (solution['energy'], solution['num_occurrences'])) if i >= 50: print_err(' first 50 of {} solutions'.format( len(solutions_all['solutions']))) break assert (total_collected == args.num_reads) print_err('') solutions_all['collection_start'] = solutions_all[ 'collection_start'].strftime(combis.TIME_FORMAT) solutions_all['collection_end'] = solutions_all['collection_end'].strftime( combis.TIME_FORMAT) if args.pretty_print: print(json.dumps(solutions_all, **json_dumps_kwargs)) else: print(json.dumps(solutions_all))
#!/usr/bin/env python3 # -*- coding: utf-8 -*- # https://docs.dwavesys.com/docs/latest/c_timing_6.html from dwave_sapi2.local import local_connection from dwave_sapi2.core import async_solve_ising, await_completion import datetime h, J = build_hamiltonian() solver = local_connection.get_solver('example_solver') submitted_qmi = async_solve_ising(solver, h, J, num_reads=100) await_completion([submitted_qmi], min_done=2, timeout=1.0) # QPU and PP times result = submitted_qmi.result() timing = result['timing'] # Service time time_format = "%Y-%m-%dT%H:%M:%S.%fZ" status = submitted_qmi.status() start_time = datetime.datetime.strptime(status['time_received'], time_format) finish_time = datetime.datetime.strptime(status['time_solved'], time_format) service_time = finish_time - start_time
def dwave(pot, states): if pot['num vars'] > 0: solved = False const = 0 h_ = [] J_ = {} state = [] free_state = [] embedding = [] while not solved: try: #global solver #global adj #if solver == 0: sign_in() #should try to make it so there is a pool of pool_size connections that the various threads can use remote_connection = RemoteConnection(url, token) solver = remote_connection.get_solver(solver_name) adj = list(get_hardware_adjacency(solver)) if 'embedding' in pot: const, h_, j, prob_adj = dwave_prepare(pot) embedding = pot['embedding'] else: # if we're doing a new embedding for each f -> v in state i message, then we'll have frozen a variable # so we need to remap the variables, since otherwise the h will have a 0 for this variable, but the embedding won't consider it map_vars(pot) const, h_, j, prob_adj = dwave_prepare(pot) while len(embedding) == 0: embedding = find_embedding(prob_adj, adj).values() [h, J, chains, embedding] = embed_problem(h_, j, embedding, adj) s = 0.50 h = [a * s for a in h] for k in J: J[k] = J[k] * s for k in chains: if k in J: J[k] += chains[k] else: J[k] = chains[k] # Submit problem #print('submitting problem') submitted_problems = [ async_solve_ising(solver, h, J, num_reads=10000, num_spin_reversal_transforms=5, answer_mode='histogram', auto_scale=True) ] await_completion(submitted_problems, len(submitted_problems), float('180')) res = unembed_answer( submitted_problems[0].result()['solutions'], embedding, 'discard') if len(res) > 0: state = array(res[0]) solved = True except Exception as err: print(err) solved = False #sleep(30) # wait 30 seconds and retry if len(h_) != len(state): print(h_, len(h_)) print(state, len(state)) print(pot) J_, _ = dict_2_mat(j, len(h_)) energy = h_.dot(state) + state.dot(J_.dot(state.transpose())) + const #for v in sorted(free_state): # energy += pot[v]*free_state[v] # state = append(state, free_state[v]) return energy, state else: if 'const' in pot: return pot['const'], states[0] else: return 0, states[0]
def submit_dwave_problem(verbosity, physical, samples, anneal_time, spin_revs, postproc): "Submit a QMI to the D-Wave." # Map abbreviated to full names for postprocessing types. postproc = {"none": "", "opt": "optimization", "sample": "sampling"}[postproc] # Determine the annealing time to use. if anneal_time == None: anneal_time = get_default_annealing_time() # Compute a list of the number of samples to take each iteration # and the number of spin reversals to perform. samples_list = compute_sample_counts(samples, anneal_time) spin_rev_list = compute_spin_rev_counts(spin_revs, samples_list) nqmis = len(samples_list) # Number of (non-unique) QMIs to submit # Submit one or more QMIs to the D-Wave. problems = [] for i in range(nqmis): solver_params = dict(chains=physical.embedding, num_reads=samples_list[i], annealing_time=anneal_time, num_spin_reversal_transforms=spin_rev_list[i], postprocess=postproc) unused_params = dict() while True: # Repeatedly remove parameters the particular solver doesn't like # until it actually works -- or fails for a different reason. try: weight_list = qmasm.dict_to_list(physical.weights) p = async_solve_ising(qmasm.solver, weight_list, physical.strengths, **solver_params) problems.append(p) break except ValueError as e: # Is there a better way to extract the failing symbol than a # regular expression match? bad_name_match = re.match(r'"(.*?)"', str(e)) if bad_name_match == None: raise e bad_name = bad_name_match.group(1) unused_params[bad_name] = solver_params[bad_name] del solver_params[bad_name] except RuntimeError as e: qmasm.abend(e) if verbosity >= 2: report_parameters_used(solver_params, unused_params) # Output problem IDs as soon as they become available. if verbosity >= 1: try: while any([problems[i].status()["problem_id"] == "" for i in range(nqmis)]): await_completion(problems, nqmis, 1) report_subproblems_submitted(nqmis, problems, samples_list, spin_rev_list) except KeyError: pass # Not all solvers support "problem_id". # Wait for the solver to complete. if verbosity >= 2: sys.stderr.write("Number of subproblems completed:\n\n") cdigits = len(str(nqmis)) # Digits in the number of completed QMIs tdigits = len(str(nqmis*5)) # Estimate 5 seconds per QMI submission start_time = time.time() done = False while not done: done = await_completion(problems, nqmis, 10) if verbosity >= 2: ncomplete = sum([problems[i].status()["state"] == "DONE" for i in range(nqmis)]) sys.stderr.write(" %*d of %d (%3.0f%%) after %*.0f seconds\n" % (cdigits, ncomplete, nqmis, 100.0*float(ncomplete)/float(nqmis), tdigits, time.time() - start_time)) if verbosity >= 2: sys.stderr.write("\n") answers = [p.result() for p in problems] # Merge the result of seperate runs into a composite answer. answer = merge_answers(answers) # Return a Solutions object for further processing. return qmasm.Solutions(answer, physical, verbosity >= 2)