def build_qaoa_ansatz_circuit( ansatz_specs: Specs, cost_hamiltonian: Union[str, List], mixer_hamiltonian: Union[str, List] = None, params: Optional[Union[str, List]] = None, ): if isinstance(ansatz_specs, str): DeprecationWarning( "Loading ansatz_specs as a string will be depreciated in future, please change it to a dictionary." ) ansatz_specs = json.loads(ansatz_specs) cost_hamiltonian = load_qubit_operator(cost_hamiltonian) if mixer_hamiltonian: mixer_hamiltonian = load_qubit_operator(mixer_hamiltonian) ansatz_specs["cost_hamiltonian"] = cost_hamiltonian ansatz_specs["mixer_hamiltonian"] = mixer_hamiltonian ansatz = load_from_specs(ansatz_specs) if params is not None: if isinstance(params, str): params = load_circuit_template_params(params) else: params = np.array(params) circuit = ansatz.get_executable_circuit(params) elif ansatz.supports_parametrized_circuits: circuit = ansatz.parametrized_circuit else: raise (Exception( "Ansatz is not parametrizable and no parameters has been provided." )) save_circuit(circuit, "circuit.json")
def interpolate_qubit_operators( reference_qubit_operator: Union[InteractionOperator, str], target_qubit_operator: Union[InteractionOperator, str], epsilon: float = 0.5, ): """Produce a qubit operator which is the interpolation of two operators through the function: epsilon * target_qubit_operator + (1.0 - epsilon) * reference_qubit_operator. Outputs are serialized to JSON under the file: "qubit-operator.json" Args: reference_qubit_operator: The initial operator target_qubit_operator: The target operator epsilon: The parameterization between the two operators. Default value is 0.5 """ reference_qubit_operator = load_qubit_operator(reference_qubit_operator) target_qubit_operator = load_qubit_operator(target_qubit_operator) if epsilon > 1.0 or epsilon < 0.0: raise ValueError("epsilon must be in the range [0.0, 1.0]") output_qubit_operator = ( epsilon * target_qubit_operator + (1.0 - epsilon) * reference_qubit_operator ) save_qubit_operator(output_qubit_operator, "qubit-operator.json")
def get_expectation_values_for_qubit_operator( backend_specs: Specs, circuit: Union[str, Circuit], qubit_operator: Union[str, SymbolicOperator], ): """Measure the expection values of the terms in an input operator with respect to the state prepared by the input circuit on the backend described by the backend_specs. The results are serialized into a JSON under the file: "expectation-values.json" ARGS: backend_specs (Union[dict, str]): The backend on which to run the quantum circuit circuit (Union[str, Circuit]): The circuit that prepares the state to be measured qubit_operator (Union[str, SymbolicOperator]): The operator to measure """ if isinstance(circuit, str): circuit = load_circuit(circuit) if isinstance(qubit_operator, str): qubit_operator = load_qubit_operator(qubit_operator) if isinstance(backend_specs, str): backend_specs = json.loads(backend_specs) backend = create_object(backend_specs) expectation_values = backend.get_expectation_values( circuit, qubit_operator) save_expectation_values(expectation_values, "expectation-values.json")
def get_expectation_values_for_qubit_operator( backend_specs: Specs, circuit: Union[str, Circuit, Dict], qubit_operator: Union[str, SymbolicOperator, Dict], ): """Measure the expectation values of the terms in an input operator with respect to the state prepared by the input circuit on the backend described by the `backend_specs`. The results are serialized into a JSON under the file: "expectation-values.json" Args: backend_specs: The backend on which to run the quantum circuit circuit: The circuit that prepares the state to be measured qubit_operator: The operator to measure """ if isinstance(circuit, str): circuit = load_circuit(circuit) elif isinstance(circuit, dict): circuit = circuit_from_dict(circuit) if isinstance(qubit_operator, str): qubit_operator = load_qubit_operator(qubit_operator) elif isinstance(qubit_operator, dict): qubit_operator = convert_dict_to_qubitop(qubit_operator) if isinstance(backend_specs, str): backend_specs = json.loads(backend_specs) backend = cast(QuantumBackend, create_object(backend_specs)) estimation_tasks = [ EstimationTask(qubit_operator, circuit, backend.n_samples) ] expectation_values = estimate_expectation_values_by_averaging( backend, estimation_tasks) save_expectation_values(expectation_values[0], "expectation-values.json")
def expectation_values_from_rdms( interactionrdm: str, qubit_operator: str, sort_terms: bool = False, ): operator = load_qubit_operator(qubit_operator) rdms = load_interaction_rdm(interactionrdm) expecval = get_expectation_values_from_rdms(rdms, operator, sort_terms=sort_terms) save_expectation_values(expecval, "expectation_values.json")
def group_comeasureable_terms_greedy( qubit_operator: Union[str, QubitOperator], sort_terms: bool = False ): if isinstance(qubit_operator, str): qubit_operator = load_qubit_operator(qubit_operator) groups = _group_comeasurable_terms_greedy(qubit_operator, sort_terms=sort_terms) save_qubit_operator_set(groups, "grouped-operator.json")
def get_ground_state_rdm_from_qubit_operator( qubit_operator: Union[str, QubitOperator], n_particles: int): """Diagonalize operator and compute the ground state 1- and 2-RDM ARGS: qubit_operator (Union[str, QubitOperator]): The openfermion operator to diagonalize n_particles (int): number of particles in the target ground state """ qubit_operator = load_qubit_operator(qubit_operator) rdm = _get_ground_state_rdm_from_qubit_op(qubit_operator, n_particles) save_interaction_rdm(rdm, "rdms.json")
def evaluate_operator_for_parameter_grid( ansatz_specs: Specs, backend_specs: Specs, grid: Union[str, ParameterGrid], operator: Union[str, SymbolicOperator], fixed_parameters: Union[List[float], np.ndarray, str] = None, ): """Measure the expection values of the terms in an input operator with respect to the states prepared by the input ansatz circuits when set to the different parameters in the input parameter grid on the backend described by the backend_specs. The results are serialized into a JSON under the files: "parameter-grid-evaluation.json" and "optimal-parameters.json" ARGS: ansatz_specs (Union[dict, str]): The ansatz producing the parameterized quantum circuits backend_specs (Union[dict, str]): The backend on which to run the quantum circuit grid (Union[str, ParameterGrid]): The parameter grid describing the different ansatz parameters to use operator (Union[str, SymbolicOperator]): The operator to measure fixed_parameters (Union[List[float], np.ndarray, str]): Any fixed parameter values that the ansatz should be evaluated to that are not described by the parameter grid """ if isinstance(ansatz_specs, str): ansatz_specs = json.loads(ansatz_specs) ansatz = create_object(ansatz_specs) if isinstance(backend_specs, str): backend_specs = json.loads(backend_specs) backend = create_object(backend_specs) if isinstance(grid, str): grid = load_parameter_grid(grid) if isinstance(operator, str): operator = load_qubit_operator(operator) if fixed_parameters is not None: if isinstance(fixed_parameters, str): fixed_parameters = load_circuit_template_params(fixed_parameters) else: fixed_parameters = [] ( parameter_grid_evaluation, optimal_parameters, ) = _evaluate_operator_for_parameter_grid( ansatz, grid, backend, operator, previous_layer_params=fixed_parameters) save_parameter_grid_evaluation(parameter_grid_evaluation, "parameter-grid-evaluation.json") save_circuit_template_params(optimal_parameters, "optimal-parameters.json")
def get_summed_expectation_values( operator: str, measurements: str, use_bessel_correction: Optional[bool] = True): if isinstance(operator, str): operator = load_qubit_operator(operator) operator = change_operator_type(operator, openfermion.IsingOperator) if isinstance(measurements, str): measurements = Measurements.load_from_file(measurements) expectation_values = measurements.get_expectation_values( operator, use_bessel_correction=use_bessel_correction) value_estimate = sum_expectation_values(expectation_values) save_value_estimate(value_estimate, "value-estimate.json")
def evaluate_ansatz_based_cost_function( ansatz_specs: Specs, backend_specs: Specs, cost_function_specs: Specs, ansatz_parameters: Specs, qubit_operator: str, noise_model: Optional[str] = None, device_connectivity: Optional[str] = None, prior_expectation_values: Optional[str] = None, ): ansatz_parameters = load_circuit_template_params(ansatz_parameters) # Load qubit op operator = load_qubit_operator(qubit_operator) if isinstance(ansatz_specs, str): ansatz_specs = json.loads(ansatz_specs) if ansatz_specs["function_name"] == "QAOAFarhiAnsatz": ansatz = create_object(ansatz_specs, cost_hamiltonian=operator) else: ansatz = create_object(ansatz_specs) if isinstance(backend_specs, str): backend_specs = json.loads(backend_specs) if noise_model is not None: backend_specs["noise_model"] = load_noise_model(noise_model) if device_connectivity is not None: backend_specs["device_connectivity"] = load_circuit_connectivity( device_connectivity) backend = create_object(backend_specs) if isinstance(cost_function_specs, str): cost_function_specs = json.loads(cost_function_specs) estimator_specs = cost_function_specs.pop("estimator-specs", None) if estimator_specs is not None: cost_function_specs["estimator"] = create_object(estimator_specs) cost_function_specs["target_operator"] = operator cost_function_specs["ansatz"] = ansatz cost_function_specs["backend"] = backend cost_function = create_object(cost_function_specs) if prior_expectation_values is not None: if isinstance(prior_expectation_values, str): cost_function.estimator.prior_expectation_values = load_expectation_values( prior_expectation_values) value_estimate = cost_function(ansatz_parameters) save_value_estimate(value_estimate, "value_estimate.json")
def hamiltonian_analysis( qubit_operator: str, decomposition_method: str = "greedy", expectation_values: Optional[str] = None, ): operator = load_qubit_operator(qubit_operator) if expectation_values is not None: expecval = load_expectation_values(expectation_values) else: expecval = None K_coeff, nterms, frame_meas = estimate_nmeas_for_operator( operator, decomposition_method, expecval) save_nmeas_estimate( nmeas=K_coeff, nterms=nterms, frame_meas=frame_meas, filename="hamiltonian_analysis.json", )
def jw_get_ground_state_at_particle_number( particle_number: int, qubit_operator: Union[str, SymbolicOperator]): """Get the ground state wavefunction of the operator for the input particle number. Outputs are serialized to JSON within the files: "ground-state.json" and "value-estimate.json" ARGS: particle_number (int): The given number of particles in the system qubit_operator (Union[str, SymbolicOperator]): The operator for which to find the ground state """ if isinstance(qubit_operator, str): qubit_operator = load_qubit_operator(qubit_operator) sparse_matrix = qubit_operator_sparse(qubit_operator) ground_energy, ground_state_amplitudes = _jw_get_ground_state_at_particle_number( sparse_matrix, particle_number) ground_state = Wavefunction(ground_state_amplitudes) value_estimate = ValueEstimate(ground_energy) save_wavefunction(ground_state, "ground-state.json") save_value_estimate(value_estimate, "value-estimate.json")
def test_get_one_qubit_hydrogen_hamiltonian(): # Define interaction hamiltonian h2_hamiltonian_int = InteractionOperator(constant=constant, one_body_tensor=one_body_tensor, two_body_tensor=two_body_tensor) save_interaction_operator(h2_hamiltonian_int, 'interaction-operator.json') get_one_qubit_hydrogen_hamiltonian('interaction-operator.json') h2_1qubit = load_qubit_operator('qubit-operator.json') h2_1qubit_sparse = get_sparse_operator(h2_1qubit, n_qubits=1) h2_1qubit_dense = h2_1qubit_sparse.toarray() #print(h2_1qubit_dense) e_1q = eigvalsh(h2_1qubit_dense) gs_4q = get_ground_state(get_sparse_operator(h2_hamiltonian_int)) os.remove('interaction-operator.json') os.remove('qubit-operator.json') assert isclose(e_1q[0], gs_4q[0])
def evaluate_ansatz_based_cost_function( ansatz_specs: Specs, backend_specs: Specs, cost_function_specs: Specs, ansatz_parameters: str, target_operator: Union[str, openfermion.SymbolicOperator], estimation_method_specs: Optional[Specs] = None, estimation_preprocessors_specs: Optional[List[Specs]] = None, noise_model: Optional[str] = None, device_connectivity: Optional[str] = None, prior_expectation_values: Optional[str] = None, estimation_tasks_transformations_kwargs: Optional[Dict] = None, ): # Empty dict as default is bad if estimation_tasks_transformations_kwargs is None: estimation_tasks_transformations_kwargs = {} ansatz_parameters = load_array(ansatz_parameters) # Load qubit op if isinstance(target_operator, str): operator = load_qubit_operator(target_operator) else: operator = target_operator if isinstance(ansatz_specs, str): ansatz_specs = json.loads(ansatz_specs) if ansatz_specs["function_name"] == "QAOAFarhiAnsatz": ansatz = create_object(ansatz_specs, cost_hamiltonian=operator) else: ansatz = create_object(ansatz_specs) if isinstance(backend_specs, str): backend_specs = json.loads(backend_specs) if noise_model is not None: backend_specs["noise_model"] = load_noise_model(noise_model) if device_connectivity is not None: backend_specs["device_connectivity"] = layouts.load_circuit_connectivity( device_connectivity ) backend = create_object(backend_specs) if isinstance(cost_function_specs, str): cost_function_specs = json.loads(cost_function_specs) if ( "estimator-specs" in cost_function_specs.keys() or "estimation-tasks-transformations-specs" in cost_function_specs.keys() ): raise RuntimeError( "Estimation-related specs should be separate arguments and not in " "cost_function_specs" ) if prior_expectation_values is not None: if isinstance(prior_expectation_values, str): prior_expectation_values = load_expectation_values(prior_expectation_values) if estimation_method_specs is not None: if isinstance(estimation_method_specs, str): estimation_method_specs = json.loads(estimation_method_specs) estimation_method = create_object(estimation_method_specs) else: estimation_method = estimate_expectation_values_by_averaging cost_function_specs["estimation_method"] = estimation_method if estimation_preprocessors_specs is not None: cost_function_specs["estimation_preprocessors"] = [] for estimation_tasks_transformation_specs in estimation_preprocessors_specs: if isinstance(estimation_tasks_transformation_specs, str): estimation_tasks_transformation_specs = json.loads( estimation_tasks_transformation_specs ) if prior_expectation_values is not None: # Since we don't know which estimation task transformation uses # prior_expectation_values, we add it to the kwargs of each one. If not # used by a particular transformer, it will be ignored. estimation_tasks_transformation_specs[ "prior_expectation_values" ] = prior_expectation_values cost_function_specs["estimation_preprocessors"].append( create_object( estimation_tasks_transformation_specs, **estimation_tasks_transformations_kwargs ) ) # cost_function.estimator.prior_expectation_values cost_function_specs["target_operator"] = operator cost_function_specs["ansatz"] = ansatz cost_function_specs["backend"] = backend cost_function = create_object(cost_function_specs) value_estimate = cost_function(ansatz_parameters) save_value_estimate(value_estimate, "value_estimate.json")
def evaluate_ansatz_based_cost_function( ansatz_specs: Specs, backend_specs: Specs, cost_function_specs: Specs, ansatz_parameters: str, qubit_operator: str, noise_model: Optional[str] = None, device_connectivity: Optional[str] = None, prior_expectation_values: Optional[str] = None, ): ansatz_parameters = load_circuit_template_params(ansatz_parameters) # Load qubit op operator = load_qubit_operator(qubit_operator) if isinstance(ansatz_specs, str): ansatz_specs = json.loads(ansatz_specs) if ansatz_specs["function_name"] == "QAOAFarhiAnsatz": ansatz = create_object(ansatz_specs, cost_hamiltonian=operator) else: ansatz = create_object(ansatz_specs) if isinstance(backend_specs, str): backend_specs = json.loads(backend_specs) if noise_model is not None: backend_specs["noise_model"] = load_noise_model(noise_model) if device_connectivity is not None: backend_specs["device_connectivity"] = load_circuit_connectivity( device_connectivity) backend = create_object(backend_specs) if isinstance(cost_function_specs, str): cost_function_specs = json.loads(cost_function_specs) if prior_expectation_values is not None: if isinstance(prior_expectation_values, str): prior_expectation_values = load_expectation_values( prior_expectation_values) estimator_specs = cost_function_specs.pop("estimator-specs", None) if estimator_specs is not None: if isinstance(estimator_specs, str): estimator_specs = json.loads(estimator_specs) cost_function_specs["estimator"] = create_object(estimator_specs) estimation_preprocessors_specs = cost_function_specs.pop( "estimation-tasks-transformations-specs", None) if estimation_preprocessors_specs is not None: cost_function_specs["estimation_preprocessors"] = [] for estimation_tasks_transformation_specs in estimation_preprocessors_specs: if isinstance(estimation_tasks_transformation_specs, str): estimation_tasks_transformation_specs = json.loads( estimation_tasks_transformation_specs) if prior_expectation_values is not None: # Since we don't know which estimation task transformation uses prior_expectation_values, # we add it to the kwargs of each one. If not used by a particular transformer, it will be ignored. estimation_tasks_transformation_specs[ "prior_expectation_values"] = prior_expectation_values cost_function_specs["estimation_preprocessors"].append( create_object(estimation_tasks_transformation_specs)) # cost_function.estimator.prior_expectation_values cost_function_specs["target_operator"] = operator cost_function_specs["ansatz"] = ansatz cost_function_specs["backend"] = backend cost_function = create_object(cost_function_specs) value_estimate = cost_function(ansatz_parameters) save_value_estimate(value_estimate, "value_estimate.json")
def optimize_variational_circuit( ansatz_specs, backend_specs, optimizer_specs, cost_function_specs, qubit_operator, initial_parameters="None", fixed_parameters="None", noise_model="None", device_connectivity="None", parameter_grid="None", constraint_operator="None", ): if initial_parameters != "None": initial_params = load_circuit_template_params(initial_parameters) else: initial_params = None if fixed_parameters != "None": fixed_params = load_circuit_template_params(fixed_parameters) else: fixed_params = None # Load qubit operator operator = load_qubit_operator(qubit_operator) if isinstance(ansatz_specs, str): ansatz_specs_dict = yaml.load(ansatz_specs, Loader=yaml.SafeLoader) else: ansatz_specs_dict = ansatz_specs if ansatz_specs_dict["function_name"] == "QAOAFarhiAnsatz": ansatz = create_object(ansatz_specs_dict, cost_hamiltonian=operator) else: ansatz = create_object(ansatz_specs_dict) # Load parameter grid if parameter_grid != "None": grid = load_parameter_grid(parameter_grid) else: grid = None # Load optimizer specs if isinstance(optimizer_specs, str): optimizer_specs_dict = yaml.load(optimizer_specs, Loader=yaml.SafeLoader) else: optimizer_specs_dict = optimizer_specs if (grid is not None and optimizer_specs_dict["function_name"] == "GridSearchOptimizer"): optimizer = create_object(optimizer_specs_dict, grid=grid) else: optimizer = create_object(optimizer_specs_dict) # Load backend specs if isinstance(backend_specs, str): backend_specs_dict = yaml.load(backend_specs, Loader=yaml.SafeLoader) else: backend_specs_dict = backend_specs if noise_model != "None": backend_specs_dict["noise_model"] = load_noise_model(noise_model) if device_connectivity != "None": backend_specs_dict["device_connectivity"] = load_circuit_connectivity( device_connectivity) backend = create_object(backend_specs_dict) # Load cost function specs if isinstance(cost_function_specs, str): cost_function_specs_dict = yaml.load(cost_function_specs, Loader=yaml.SafeLoader) else: cost_function_specs_dict = cost_function_specs estimator_specs = cost_function_specs_dict.pop("estimator-specs", None) if estimator_specs is not None: cost_function_specs_dict["estimator"] = create_object(estimator_specs) cost_function_specs_dict["target_operator"] = operator cost_function_specs_dict["ansatz"] = ansatz cost_function_specs_dict["backend"] = backend cost_function_specs_dict["fixed_parameters"] = fixed_params cost_function = create_object(cost_function_specs_dict) if constraint_operator != "None": constraint_op = load_qubit_operator(constraint_operator) constraints_cost_function_specs = yaml.load(cost_function_specs, Loader=yaml.SafeLoader) constraints_estimator_specs = constraints_cost_function_specs.pop( "estimator-specs", None) if constraints_estimator_specs is not None: constraints_cost_function_specs["estimator"] = create_object( constraints_estimator_specs) constraints_cost_function_specs["ansatz"] = ansatz constraints_cost_function_specs["backend"] = backend constraints_cost_function_specs["target_operator"] = constraint_op constraint_cost_function = create_object( constraints_cost_function_specs) constraint_cost_function_wrapper = ( lambda params: constraint_cost_function.evaluate(params).value) constraint_functions = ({ "type": "eq", "fun": constraint_cost_function_wrapper }, ) optimizer.constraints = constraint_functions opt_results = optimizer.minimize(cost_function, initial_params) save_optimization_results(opt_results, "optimization-results.json") save_circuit_template_params(opt_results.opt_params, "optimized-parameters.json")
def optimize_variational_circuit( ansatz_specs, backend_specs, optimizer_specs, cost_function_specs, qubit_operator, initial_parameters="None", fixed_parameters="None", noise_model="None", device_connectivity="None", parameter_grid="None", parameter_values_list=None, constraint_operator="None", prior_expectation_values: Optional[str] = None, keep_history=False, thetas=None, ): warnings.warn( "optimize_variational_circuit will be depreciated in favor of optimize_ansatz_based_cost_function in steps/optimize.py in z-quantum-core.", DeprecationWarning, ) if initial_parameters != "None": initial_params = load_array(initial_parameters) else: initial_params = None if fixed_parameters != "None": fixed_params = load_array(fixed_parameters) else: fixed_params = None # Load qubit operator operator = load_qubit_operator(qubit_operator) if isinstance(ansatz_specs, str): ansatz_specs_dict = yaml.load(ansatz_specs, Loader=yaml.SafeLoader) else: ansatz_specs_dict = ansatz_specs if "WarmStartQAOAAnsatz" in ansatz_specs_dict["function_name"]: thetas = np.array(load_list(thetas)) ansatz = create_object(ansatz_specs_dict, cost_hamiltonian=operator, thetas=thetas) elif "QAOA" in ansatz_specs_dict["function_name"]: ansatz = create_object(ansatz_specs_dict, cost_hamiltonian=operator) else: ansatz = create_object(ansatz_specs_dict) # Load parameter grid if parameter_grid != "None": grid = load_parameter_grid(parameter_grid) else: grid = None # Load parameter values list if parameter_values_list is not None: parameter_values_list = load_array(parameter_values_list) # Load optimizer specs if isinstance(optimizer_specs, str): optimizer_specs_dict = yaml.load(optimizer_specs, Loader=yaml.SafeLoader) else: optimizer_specs_dict = optimizer_specs if (grid is not None and optimizer_specs_dict["function_name"] == "GridSearchOptimizer"): optimizer = create_object(optimizer_specs_dict, grid=grid) elif (parameter_values_list is not None and optimizer_specs_dict["function_name"] == "SearchPointsOptimizer"): optimizer = create_object(optimizer_specs_dict, parameter_values_list=parameter_values_list) else: optimizer = create_object(optimizer_specs_dict) # Load backend specs if isinstance(backend_specs, str): backend_specs_dict = yaml.load(backend_specs, Loader=yaml.SafeLoader) else: backend_specs_dict = backend_specs if noise_model != "None": backend_specs_dict["noise_model"] = load_noise_model(noise_model) if device_connectivity != "None": backend_specs_dict["device_connectivity"] = load_circuit_connectivity( device_connectivity) backend = create_object(backend_specs_dict) # Load cost function specs if isinstance(cost_function_specs, str): cost_function_specs_dict = yaml.load(cost_function_specs, Loader=yaml.SafeLoader) else: cost_function_specs_dict = cost_function_specs estimation_method_specs = cost_function_specs_dict.pop( "estimation_method_specs", None) if estimation_method_specs is not None: if isinstance(estimation_method_specs, str): estimation_method_specs = yaml.loads(estimation_method_specs) estimation_method = create_object(estimation_method_specs) else: estimation_method = estimate_expectation_values_by_averaging cost_function_specs_dict["estimation_method"] = estimation_method estimation_preprocessors_specs_list = cost_function_specs_dict.pop( "estimation_preprocessors_specs", None) if estimation_preprocessors_specs_list is not None: estimation_preprocessors = [] for estimation_preprocessor_specs in estimation_preprocessors_specs_list: if isinstance(estimation_preprocessor_specs, str): estimation_preprocessor_specs = yaml.loads( estimation_preprocessor_specs) estimation_preprocessors.append( create_object(estimation_preprocessor_specs)) cost_function_specs_dict[ "estimation_preprocessors"] = estimation_preprocessors cost_function_specs_dict["target_operator"] = operator cost_function_specs_dict["ansatz"] = ansatz cost_function_specs_dict["backend"] = backend cost_function_specs_dict["fixed_parameters"] = fixed_params cost_function = create_object(cost_function_specs_dict) if prior_expectation_values is not None: if isinstance(prior_expectation_values, str): cost_function.estimator.prior_expectation_values = load_expectation_values( prior_expectation_values) if constraint_operator != "None": constraint_op = load_qubit_operator(constraint_operator) constraints_cost_function_specs = yaml.load(cost_function_specs, Loader=yaml.SafeLoader) constraints_estimator_specs = constraints_cost_function_specs.pop( "estimator-specs", None) if constraints_estimator_specs is not None: constraints_cost_function_specs["estimator"] = create_object( constraints_estimator_specs) constraints_cost_function_specs["ansatz"] = ansatz constraints_cost_function_specs["backend"] = backend constraints_cost_function_specs["target_operator"] = constraint_op constraint_cost_function = create_object( constraints_cost_function_specs) constraint_cost_function_wrapper = ( lambda params: constraint_cost_function.evaluate(params).value) constraint_functions = ({ "type": "eq", "fun": constraint_cost_function_wrapper }, ) optimizer.constraints = constraint_functions opt_results = optimizer.minimize(cost_function, initial_params, keep_history) save_optimization_results(opt_results, "optimization-results.json") save_array(opt_results.opt_params, "optimized-parameters.json")
def optimize_parametrized_circuit_for_ground_state_of_operator( optimizer_specs: Specs, target_operator: Union[SymbolicOperator, str], parametrized_circuit: Union[Circuit, str], backend_specs: Specs, estimation_method_specs: Optional[Specs] = None, estimation_preprocessors_specs: Optional[List[Specs]] = None, initial_parameters: Union[str, np.ndarray, List[float]] = None, fixed_parameters: Optional[Union[np.ndarray, str]] = None, parameter_precision: Optional[float] = None, parameter_precision_seed: Optional[int] = None, keep_history: bool = True, **kwargs, ): """Optimize the parameters of a parametrized quantum circuit to prepare the ground state of a target operator. Args: optimizer_specs: The specs of the optimizer to use to refine the parameter values target_operator: The operator of which to prepare the ground state parametrized_circuit: The parametrized quantum circuit that prepares trial states backend_specs: The specs of the quantum backend (or simulator) to use to run the circuits estimation_method_specs: A reference to a callable to use to estimate the expectation value of the operator. The default is the estimate_expectation_values_by_averaging function. estimation_preprocessors_specs: A list of Specs that describe callable functions that adhere to the EstimationPreprocessor protocol. initial_parameters: The initial parameter values to begin optimization fixed_parameters: values for the circuit parameters that should be fixed. parameter_precision: the standard deviation of the Gaussian noise to add to each parameter, if any. parameter_precision_seed: seed for randomly generating parameter deviation if using parameter_precision keep_history: flag indicating whether to store optimization history. kwargs: unused, exists for compatibility """ if isinstance(optimizer_specs, str): optimizer_specs = json.loads(optimizer_specs) optimizer = create_object(optimizer_specs) if isinstance(target_operator, str): target_operator = load_qubit_operator(target_operator) if isinstance(parametrized_circuit, str): with open(parametrized_circuit) as f: parametrized_circuit = new_circuits.circuit_from_dict(json.load(f)) if isinstance(backend_specs, str): backend_specs = json.loads(backend_specs) backend = create_object(backend_specs) if estimation_method_specs is not None: if isinstance(estimation_method_specs, str): estimation_method_specs = json.loads(estimation_method_specs) estimation_method = create_object(estimation_method_specs) else: estimation_method = estimate_expectation_values_by_averaging estimation_preprocessors = [] if estimation_preprocessors_specs is not None: for estimation_preprocessor_specs in estimation_preprocessors_specs: if isinstance(estimation_preprocessor_specs, str): estimation_preprocessor_specs = json.loads( estimation_preprocessor_specs) estimation_preprocessors.append( create_object(estimation_preprocessor_specs)) if initial_parameters is not None: if isinstance(initial_parameters, str): initial_parameters = load_array(initial_parameters) if fixed_parameters is not None: if isinstance(fixed_parameters, str): fixed_parameters = load_array(fixed_parameters) cost_function = get_ground_state_cost_function( target_operator, parametrized_circuit, backend, estimation_method=estimation_method, estimation_preprocessors=estimation_preprocessors, fixed_parameters=fixed_parameters, parameter_precision=parameter_precision, parameter_precision_seed=parameter_precision_seed, ) optimization_results = optimizer.minimize(cost_function, initial_parameters, keep_history) save_optimization_results(optimization_results, "optimization-results.json") save_array(optimization_results.opt_params, "optimized-parameters.json")
def optimize_ansatz_based_cost_function( optimizer_specs: Specs, target_operator: Union[SymbolicOperator, str], ansatz_specs: Specs, backend_specs: Specs, estimation_method_specs: Optional[Specs] = None, estimation_preprocessors_specs: Optional[List[Specs]] = None, initial_parameters: Union[str, np.ndarray, List[float]] = None, fixed_parameters: Optional[Union[np.ndarray, str]] = None, parameter_precision: Optional[float] = None, parameter_precision_seed: Optional[int] = None, keep_history: bool = False, **kwargs, ): """Optimize the parameters of an ansatz circuit to prepare the ground state of a target operator. Args: optimizer_specs: The specs of the optimizer to use to refine the parameter values target_operator: The operator of which to prepare the ground state ansatz_specs: The specs describing an Ansatz which will prepare the quantum circuit backend_specs: The specs of the quantum backend (or simulator) to use to run the circuits estimation_method_specs: A reference to a callable to use to estimate the expectation value of the operator. The default is the estimate_expectation_values_by_averaging function. estimation_preprocessors_specs: A list of Specs that describe callable functions that adhere to the EstimationPreprocessor protocol. initial_parameters: The initial parameter values to begin optimization fixed_parameters: values for the circuit parameters that should be fixed. parameter_precision: the standard deviation of the Gaussian noise to add to each parameter, if any. parameter_precision_seed: seed for randomly generating parameter deviation if using parameter_precision keep_history: flag indicating whether to store optimization history. kwargs: The following key word arguments are handled explicitly when appropriate: - thetas: A list of thetas used to initialize the WarmStartQAOAAnsatz """ if isinstance(optimizer_specs, str): optimizer_specs = json.loads(optimizer_specs) optimizer = create_object(optimizer_specs) if isinstance(target_operator, str): target_operator = load_qubit_operator(target_operator) if isinstance(ansatz_specs, str): ansatz_specs = json.loads(ansatz_specs) if "WarmStartQAOAAnsatz" in ansatz_specs["function_name"]: ansatz_specs["thetas"] = np.array(load_list(kwargs.pop("thetas"))) ansatz_specs["cost_hamiltonian"] = target_operator elif "QAOA" in ansatz_specs["function_name"]: ansatz_specs["cost_hamiltonian"] = target_operator ansatz = create_object(ansatz_specs) if isinstance(backend_specs, str): backend_specs = json.loads(backend_specs) backend = create_object(backend_specs) if estimation_method_specs is not None: if isinstance(estimation_method_specs, str): estimation_method_specs = json.loads(estimation_method_specs) estimation_method = create_object(estimation_method_specs) else: estimation_method = estimate_expectation_values_by_averaging estimation_preprocessors = [] if estimation_preprocessors_specs is not None: for estimation_preprocessor_specs in estimation_preprocessors_specs: if isinstance(estimation_preprocessor_specs, str): estimation_preprocessor_specs = json.loads( estimation_preprocessor_specs) estimation_preprocessors.append( create_object(estimation_preprocessor_specs)) if initial_parameters is not None: if isinstance(initial_parameters, str): initial_parameters = load_array(initial_parameters) if fixed_parameters is not None: if isinstance(fixed_parameters, str): fixed_parameters = load_array(fixed_parameters) cost_function = AnsatzBasedCostFunction( target_operator, ansatz, backend, estimation_method=estimation_method, estimation_preprocessors=estimation_preprocessors, fixed_parameters=fixed_parameters, parameter_precision=parameter_precision, parameter_precision_seed=parameter_precision_seed, ) optimization_results = optimizer.minimize(cost_function, initial_parameters, keep_history) save_optimization_results(optimization_results, "optimization-results.json") save_array(optimization_results.opt_params, "optimized-parameters.json")
def create_farhi_qaoa_circuit(number_of_layers, hamiltonian): hamiltonian_object = load_qubit_operator(hamiltonian) circuit = farhi_ansatz.create_farhi_qaoa_circuits([hamiltonian_object], number_of_layers)[0] save_circuit(circuit, "circuit.json")