CUDA-Q Solvers Python API
- cudaq_solvers.jordan_wigner(*args, **kwargs)
Overloaded function.
jordan_wigner(hpq: Buffer, hpqrs: Buffer, core_energy: float = 0.0) -> SpinOperator
Perform the Jordan-Wigner transformation on fermionic operators.
This function applies the Jordan-Wigner transformation to convert fermionic operators (represented by one- and two-body integrals) into qubit operators.
Parameters:
- hpqnumpy.ndarray
A 2D complex numpy array representing the one-body integrals. Shape should be (N, N) where N is the number of spin molecular orbitals.
- hpqrsnumpy.ndarray
A 4D complex numpy array representing the two-body integrals. Shape should be (N, N, N, N) where N is the number of spin molecular orbitals.
- core_energyfloat, optional
The core energy of the system when using active space Hamiltonian, nuclear energy otherwise. Default is 0.0.
Returns:
- cudaq.SpinOperator
A qubit operator (spin operator) resulting from the Jordan-Wigner transformation.
Raises:
- ValueError
If the input arrays have incorrect shapes or types.
- RuntimeError
If the Jordan-Wigner transformation fails for any reason.
Examples:
>>> import numpy as np >>> h1 = np.array([[0, 1], [1, 0]], dtype=np.complex128) >>> h2 = np.zeros((2, 2, 2, 2), dtype=np.complex128) >>> h2[0, 1, 1, 0] = h2[1, 0, 0, 1] = 0.5 >>> qubit_op = jordan_wigner(h1, h2, core_energy=0.1)
Notes:
The input arrays
hpq
andhpqrs
must be contiguous and in row-major order.This function uses the “jordan_wigner” fermion compiler internally to perform the transformation.
The resulting qubit operator can be used directly in quantum algorithms or further manipulated using CUDA Quantum operations.
jordan_wigner(hpq: Buffer, core_energy: float = 0.0) -> SpinOperator
Perform the Jordan-Wigner transformation on fermionic operators.
This function applies the Jordan-Wigner transformation to convert fermionic operators (represented by either one-body or two-body integrals) into qubit operators.
Parameters:
- hpqnumpy.ndarray
A complex numpy array representing either: - One-body integrals: 2D array with shape (N, N) - Two-body integrals: 4D array with shape (N, N, N, N) where N is the number of orbitals.
- core_energyfloat, optional
The core energy of the system. Default is 0.0.
Returns:
- cudaq.SpinOperator
A qubit operator (spin operator) resulting from the Jordan-Wigner transformation.
Raises:
- ValueError
If the input array has an incorrect shape or type.
- RuntimeError
If the Jordan-Wigner transformation fails for any reason.
Examples:
>>> import numpy as np >>> # One-body integrals >>> h1 = np.array([[0, 1], [1, 0]], dtype=np.complex128) >>> qubit_op1 = jordan_wigner(h1, core_energy=0.1)
>>> # Two-body integrals >>> h2 = np.zeros((2, 2, 2, 2), dtype=np.complex128) >>> h2[0, 1, 1, 0] = h2[1, 0, 0, 1] = 0.5 >>> qubit_op2 = jordan_wigner(h2)
Notes:
The input array must be contiguous and in row-major order.
This function automatically detects whether the input represents one-body or two-body integrals based on its shape.
For one-body integrals input, a zero-initialized two-body tensor is used internally.
For two-body integrals input, a zero-initialized one-body tensor is used internally.
This function uses the “jordan_wigner” fermion compiler internally to perform the transformation.
The resulting qubit operator can be used directly in quantum algorithms or further manipulated using CUDA Quantum operations.
- class cudaq_solvers.MolecularHamiltonian
- property energies
Dictionary of energies from classical computation.
- property hamiltonian
The qubit representation of the molecular Hamiltonian.
This is the full electronic Hamiltonian of the molecule, transformed into qubit operators using a specific mapping (e.g., Jordan-Wigner).
- Type:
- property hpq
One-electron integrals.
A 2D complex array of shape (n_orbitals, n_orbitals), where n_orbitals is the number of spin molecular orbitals, representing the one-electron integrals in the molecular orbital basis. These include kinetic energy and electron-nuclear attraction terms.
- Type:
- property hpqrs
Two-electron integrals.
A 4D complex array of shape (n_orbitals, n_orbitals, n_orbitals, n_orbitals), where n_orbitals is the number of spin molecular orbitals, representing the two-electron integrals in the molecular orbital basis. These describe electron-electron interactions.
- Type:
- property n_electrons
The number of electrons in the molecule.
This represents the total number of electrons in the molecular system, which is crucial for determining the filling of orbitals and the overall electronic structure.
- Type:
- cudaq_solvers.get_operator_pool(arg0: str, **kwargs) list[SpinOperator]
Get and generate an operator pool based on the specified name and configuration.
This function retrieves an operator pool implementation by name and generates a set of operators using the provided configuration.
Parameters:
- namestr
The name of the operator pool implementation to use.
- configdict
Keyword arguments representing the configuration for operator pool generation. Supported value types: - int: Converted to std::size_t in C++. - list: Converted to std::vector<double> in C++.
Returns:
- list
A list of generated operators (
cudaq.SpinOperator
objects).
Raises:
- RuntimeError
If the specified operator pool implementation is not found.
- TypeError
If an unsupported configuration value type is provided.
Examples:
>>> ops = get_operator_pool("uccsd", n_qubits=4, n_electrons=2) >>> ops = get_operator_pool("custom_pool", cutoff=1e-5, parameters=[0.1, 0.2, 0.3])
Notes:
The function internally converts Python types to C++ types and uses the cudaq::operator_pool extension point system to retrieve and generate the operator pool. Only integer and list configuration values are currently supported.
- cudaq_solvers.optim.optimize(function: Callable, initial_parameters: list[float], method: str = 'cobyla', **kwargs) tuple[float, list[float]]
Optimize a given objective function using various optimization methods.
This function performs optimization on a user-provided objective function using the specified optimization method. It supports both gradient-based and gradient-free optimization algorithms.
Parameters:
- functioncallable
The objective function to be minimized. It should take a list of parameters as input and return either: - A single float value (for gradient-free methods) - A tuple (float, list[float]) where the first element is the function value and the second is the gradient (for gradient-based methods)
- initial_parameterslist[float]
Initial guess for the parameters to be optimized.
- methodstr, optional
The optimization method to use. Default is ‘cobyla’. Must be a valid, registered cudaq-x optimizer.
- optionsdict
Additional options for the optimizer. These are method-specific.
Returns:
- OptimizationResult
An object containing the results of the optimization process.
Raises:
- RuntimeError
If an invalid optimization method is specified or if the objective function returns an incorrect format for gradient-based optimizers.
Examples:
>>> def objective(x): ... return sum([xi**2 for xi in x]), [2*xi for xi in x] >>> result = optimize(objective, [1.0, 2.0, 3.0], method='l-bfgs-b') >>> print(result.optimal_parameters) [0.0, 0.0, 0.0]
>>> def simple_objective(x): ... return sum([xi**2 for xi in x]) >>> result = optimize(simple_objective, [1.0, 2.0, 3.0], method='cobyla') >>> print(result.optimal_value) 0.0
Notes:
The function automatically detects whether the optimization method requires gradients and expects the objective function to return the appropriate format.
For gradient-based methods, the objective function must return a tuple of (value, gradient).
For gradient-free methods, the objective function should return only the value.
The optimization process uses the cudaq-x backend, which must be properly set up and have the specified optimization method registered.
- class cudaq_solvers.ObserveExecutionType
An enumeration representing different types of execution in an optimization process.
This enum defines the various types of operations that can occur during an optimization iteration, specifically distinguishing between function evaluations and gradient computations.
Usage:
This enum is typically used in conjunction with optimization algorithms and observation mechanisms to indicate the nature of a particular step or evaluation in the optimization process.
Examples:
>>> def callback(iteration): ... if iteration.type == ObserveExecutionType.function: ... print("Function evaluation") ... elif iteration.type == ObserveExecutionType.gradient: ... print("Gradient computation")
>>> # In an optimization loop >>> for step in optimization_steps: ... if step.type == ObserveExecutionType.function: ... # Process function evaluation ... elif step.type == ObserveExecutionType.gradient: ... # Process gradient information
Notes:
The distinction between function evaluations and gradient computations is particularly important for gradient-based optimization methods.
Some optimization algorithms may only use function evaluations (gradient-free methods), while others rely heavily on gradient information.
This enum can be used for logging, debugging, or implementing custom behaviors based on the type of operation being performed during optimization.
Members:
function : Represents a standard function evaluation of the objective function.
This typically involves computing the value of the objective function at a given point in the parameter space.
gradient : Represents a gradient computation.
This involves calculating the partial derivatives of the objective
- function = <ObserveExecutionType.function: 0>
- gradient = <ObserveExecutionType.gradient: 1>
- property name
- property value
- class cudaq_solvers.ObserveIteration
A class representing a single iteration of an optimization process.
This class encapsulates the state of an optimization iteration, including the current parameter values, the result of the objective function evaluation, and the type of iteration
- property parameters
The current values of the optimization parameters at this iteration. These represent the point in the parameter space being evaluated.
- property result
The value of the objective function evaluated at the current parameters. For minimization problems, lower values indicate better solutions.
- property type
A string indicating the type or purpose of this iteration. Common types might include: - ‘function’: A standard function evaluation - ‘gradient’: An iteration where gradients were computed The exact set of possible types may depend on the specific optimization algorithm used.
- cudaq_solvers.vqe(kernel: Callable, spin_op: SpinOperator, initial_parameters: list[float], **kwargs) tuple
Execute the Variational Quantum Eigensolver (VQE) algorithm.
This function implements the VQE algorithm, a hybrid quantum-classical algorithm used to find the ground state energy of a given Hamiltonian using a parameterized quantum circuit.
Parameters:
- kernelcallable
A function representing the parameterized quantum circuit (ansatz). It should take a list of parameters as input and prepare the quantum state.
- spin_opcudaq.SpinOperator
The Hamiltonian operator for which to find the ground state energy.
- initial_parametersList[float]
Initial values for the variational parameters of the quantum circuit.
- optionsdict
Additional options for the VQE algorithm. Supported options include: - shots : int, optional, Number of measurement shots. Default is -1 (use maximum available). - max_iterations : int, optional Maximum number of optimization iterations. Default is -1 (no limit). - verbose : bool, optional Whether to print verbose output. Default is False. - optimizer : str, optional Name of the classical optimizer to use. Default is ‘cobyla’. - gradient : str, optional Method for gradient computation (for gradient-based optimizers). Default is ‘parameter_shift’.
Returns:
- Tuple[float, List[float], List[ObserveIteration]]
A tuple containing: 1. The optimized ground state energy. 2. The optimal variational parameters. 3. A list of ObserveIteration objects containing data from each iteration.
Raises:
- RuntimeError
If an invalid optimizer or gradient method is specified.
Examples:
>>> def ansatz(params): ... # Define your quantum circuit here ... pass >>> hamiltonian = cudaq.SpinOperator(...) # Define your Hamiltonian >>> initial_params = [0.1, 0.2, 0.3] >>> energy, opt_params, iterations = vqe(ansatz, hamiltonian, initial_params, ... optimizer='cobyla', shots=1000) >>> print(f"Ground state energy: {energy}") >>> print(f"Optimal parameters: {opt_params}")
Notes:
The function automatically selects between gradient-free and gradient-based optimization based on the chosen optimizer.
For gradient-based optimization, the ‘parameter_shift’ method is used by default, but can be changed using the ‘gradient’ option.
The ObserveIteration objects in the returned list contain detailed information about each optimization step, useful for analysis and visualization.
The performance of VQE heavily depends on the choice of ansatz, initial parameters, and optimization method.
- cudaq_solvers.adapt_vqe(arg0: object, arg1: SpinOperator, arg2: list[SpinOperator], **kwargs) tuple[float, list[float], list[SpinOperator]]
Perform ADAPT-VQE (Adaptive Derivative-Assembled Pseudo-Trotter Variational Quantum Eigensolver) optimization.
- Parameters:
initialStateKernel (object) – Python object representing the initial state kernel.
op (cudaq.SpinOperator) – The Hamiltonian operator to be optimized.
pool (list of cudaq.SpinOperator) – Pool of operators for ADAPT-VQE.
options – Additional options for the optimization process.
- Keyword Arguments:
- Returns:
The result of the ADAPT-VQE optimization.
Note
This function wraps the C++ implementation of ADAPT-VQE in CUDA-QX. It compiles and registers the initial state kernel, sets up the optimizer, and performs the ADAPT-VQE optimization using the provided parameters.
- cudaq_solvers.stateprep.uccsd(arg0: cudaq::qview<2ul>, arg1: list[float], arg2: int, arg3: int) None
Unitary Coupled Cluster Singles Doubles Ansatz. Takes as input the qubits to apply the ansatz on, the rotational parameters, the number of electrons in the system, and the total spin (the number of unpaired electrons).
- cudaq_solvers.stateprep.single_excitation(arg0: cudaq::qview<2ul>, arg1: float, arg2: int, arg3: int) None
Perform a single fermionic excitation.
- cudaq_solvers.stateprep.double_excitation(arg0: cudaq::qview<2ul>, arg1: float, arg2: int, arg3: int, arg4: int, arg5: int) None
Perform a double fermionic excitation.
- cudaq_solvers.stateprep.get_num_uccsd_parameters(num_electrons: int, num_qubits: int, spin: int = 0) int
Calculate the number of UCCSD parameters