qc2.algorithms.utils

qc2 utils package.

Submodules

Classes

ActiveSpace

A data class representing the active space.

OrbitalOptimization

A class to perform orbital optimization for quantum chemical systems.

FermionicToQubitMapper

Functions

get_active_space_idx(→ Tuple[numpy.ndarray, ...)

Calculates indices for occ, active, and virt orbitals in an active space.

vector_to_skew_symmetric(→ numpy.ndarray)

Map a vector to an anti-symmetric matrix with np.tril_indices.

get_non_redundant_indices(→ numpy.ndarray)

Calculates the non-redundant indices for orbital parameters.

Package Contents

qc2.algorithms.utils.get_active_space_idx(nao: int, nelectron: int | Tuple[int, int], n_active_orbitals: int, n_active_electrons: int | Tuple[int, int]) Tuple[numpy.ndarray, numpy.ndarray, numpy.ndarray][source]

Calculates indices for occ, active, and virt orbitals in an active space.

Parameters:
  • nao (int) – Total number of atomic orbitals.

  • nelectron (Union[int, Tuple[int, int]]) – A list representing the number of electrons in each atom.

  • n_active_orbitals (int) – Number of orbitals in the active space.

  • n_active_electrons (Union[int, Tuple[int, int]]) – A list representing the number of active electrons in each atom.

Returns:

Three numpy arrays representing the indices of occupied, active, and virtual orbitals, respectively.

Return type:

Tuple[np.ndarray, np.ndarray, np.ndarray]

Raises:

ValueError – If the number of core electrons is odd.

class qc2.algorithms.utils.ActiveSpace[source]

A data class representing the active space.

num_active_electrons: tuple[int, int]
num_active_spatial_orbitals: int
qc2.algorithms.utils.vector_to_skew_symmetric(vector: List[float] | numpy.ndarray) numpy.ndarray[source]

Map a vector to an anti-symmetric matrix with np.tril_indices.

Parameters:

vector (Union[List[float], np.ndarray]) – 1d tensor

Returns:

A skew-symmetric matrix corresponding to the input vector.

Return type:

np.ndarray

Example

The resulting matrix for np.array([1,2,3,4,5,6]) is:

\[\begin{split}\begin{pmatrix} 0 & -1 & -2 & -4\\ 1 & 0 & -3 & -5\\ 2 & 3 & 0 & -6\\ 4 & 5 & 6 & 0 \end{pmatrix}\end{split}\]
qc2.algorithms.utils.get_non_redundant_indices(occ_idx: numpy.ndarray, act_idx: numpy.ndarray, virt_idx: numpy.ndarray, freeze_active: bool) numpy.ndarray[source]

Calculates the non-redundant indices for orbital parameters.

Parameters:
  • occ_idx (np.ndarray) – Indices of occupied orbitals.

  • act_idx (np.ndarray) – Indices of active orbitals.

  • virt_idx (np.ndarray) – Indices of virtual orbitals.

  • freeze_active (bool) – If True, active orbitals are frozen.

Returns:

Indices of non-redundant orbital rotation parameters.

Return type:

np.ndarray

class qc2.algorithms.utils.OrbitalOptimization(qc2data: qc2.data.data.qc2Data, active_space: qc2.algorithms.utils.active_space.ActiveSpace, freeze_active: bool = False, mapper: qiskit_nature.second_q.mappers.QubitMapper = JordanWignerMapper(), format: str = 'qiskit')[source]

A class to perform orbital optimization for quantum chemical systems.

This class is responsible for setting up and managing the data related to orbital optimization part of the oo-VQE algorithm.

qc2data

An instance of qc2Data.

Type:

qc2Data

schema_dataclass

An instance of QCSchema.

Type:

QCSchema

es_problem

Instance of ElectronicStructureProblem in AO basis as processed from process_schema().

Type:

ElectronicStructureProblem

n_electrons

Number of alpha and beta electrons.

Type:

Tuple[int, int]

nao

Number of spatial orbitals.

Type:

int

n_active_orbitals

Number of active orbitals to consider.

Type:

int

n_active_electrons

Number of active electrons.

Type:

Tuple[int, int]

freeze_active

Determines if the active orbitals are frozen in the optimization process.

Type:

bool, optional

occ_idx

Indices of occupied molecular orbitals.

Type:

list

act_idx

Indices of active molecular orbitals.

Type:

list

virt_idx

Indices of virtual molecular orbitals.

Type:

list

params_idx

Indices for non-redundant orbital rotations.

Type:

list

n_kappa

Dimension of the kappa vector for orbital rotations.

Type:

int

mapper

The fermionic-to-qubit mapping algorithm.

Type:

QubitMapper

qc2data
schema_dataclass
es_problem
n_electrons
nao
n_active_orbitals
n_active_electrons
freeze_active = False
params_idx
n_kappa
mapper
format = 'qiskit'
orbital_optimization(rdm1: numpy.ndarray, rdm2: numpy.ndarray, kappa_init: List | None = None) Tuple[List, float][source]

Optimize orbital parameters.

Parameters:
  • rdm1 (np.array) – One-electron reduced density matrix.

  • rdm2 (np.array) – Two-electron reduced density matrix.

  • kappa_init (List, optional) – Initial orbital rotation parameters vector. If None, set guess as a zero vector.

Returns:

Optimized orbital rotation parameters and associated energy.

Return type:

Tuple[List, float]

Example

>>> from ase.build import molecule
>>> from qc2.ase import PySCF
>>> from qc2.data import qc2Data
>>> from qc2.algorithms.utils import OrbitalOptimization
>>> from qc2.algorithms.utils import ActiveSpace
>>>
>>> mol = molecule('H2O')
>>>
>>> hdf5_file = 'h2o.hdf5'
>>> qc2data = qc2Data(hdf5_file, mol, schema='qcschema')
>>> oo_problem = OrbitalOptimization(
...     qc2data=qc2data,
...     active_space=ActiveSpace(
...         num_active_electrons=(2, 2),
...         num_active_spatial_orbitals=4
...     ),
...     mapper=JordanWignerMapper(),
...     format="qiskit"
... )
>>> rdm1 = np.array(...)
>>> rdm2 = np.array(...)
>>> kappa_init = [0.0] * oo.n_kappa
>>> optimized_kappa, energy = oo.orbital_optimization(
...     rdm1, rdm2, kappa_init
... )
get_analytic_hessian(kappa: List, rdm1: numpy.ndarray, rdm2: numpy.ndarray) numpy.ndarray[source]

Calculate the analytic hessian for orbital optimization.

This method calculates the second derivative of the energy with respect to orbital rotation parameters.

Parameters:
  • kappa (List) – Orbital rotation parameters vector.

  • rdm1 (np.array) – One-electron reduced density matrix.

  • rdm2 (np.array) – Two-electron reduced density matrix.

Returns:

A (n_kappa, n_kappa) matrix containing analytic hessian.

Return type:

np.array

Notes

Based on the method outlined in: [1]. https://iopscience.iop.org/article/10.1088/2058-9565/abd334 [2]. https://doi.org/10.1038/s41534-023-00730-8 [3]. https://github.com/Emieeel/auto_oo

get_analytic_gradients(kappa: List, rdm1: numpy.ndarray, rdm2: numpy.ndarray) numpy.ndarray[source]

Calculates analytic gradients for orbital optimization.

This method calculates the first derivative of the energy with respect to orbital rotation parameters.

Parameters:
  • kappa (List) – Orbital rotation parameters vector.

  • rdm1 (np.array) – One-electron reduced density matrix.

  • rdm2 (np.array) – Two-electron reduced density matrix.

Returns:

A vector of len(kappa) containing analytic gradients.

Return type:

np.array

Notes

Based on the method outlined in: [4]. https://doi.org/10.1063/1.441359

get_fock_matrix(one_electron_integrals: numpy.array, two_electron_integrals: numpy.array, rdm1: numpy.array, rdm2: numpy.array) numpy.ndarray[source]

Constructs the Fock matrix for orbital optimization.

Parameters:
  • one_electron_integrals (np.array) – One-electron integrals.

  • two_electron_integrals (np.array) – Two-electron integrals.

  • rdm1 (np.array) – One-electron reduced density matrix.

  • rdm2 (np.array) – Two-electron reduced density matrix.

Returns:

The Fock matrix.

Return type:

np.array

Notes

Based on the method outlined in: [4]. https://doi.org/10.1063/1.441359

get_energy_from_kappa(kappa: List, rdm1: numpy.ndarray, rdm2: numpy.ndarray) float[source]

Gets total energy after transforming the MOs with kappa.

Parameters:
  • kappa (List) – Orbital rotation parameters vector.

  • rdm1 (np.array) – One-electron reduced density matrix.

  • rdm2 (np.array) – Two-electron reduced density matrix.

Returns:

Total ground-state energy.

Return type:

float

get_energy_from_mo_coeffs(mo_coeff_a: numpy.ndarray, mo_coeff_b: numpy.ndarray | None, rdm1: numpy.ndarray, rdm2: numpy.ndarray) float[source]

Get energy given one- and two-particle reduced density matrices.

Parameters:
  • mo_coeff_a (np.array) – Alpha MO coefficients vector.

  • mo_coeff_b (np.array, optional) – Beta MO coefficients vector.

  • rdm1 (np.array) – One-electron reduced density matrix.

  • rdm2 (np.array) – Two-electron reduced density matrix.

Returns:

Total ground-state energy.

Return type:

float

get_transformed_qubit_hamiltonian(kappa: List) Tuple[float, qiskit.quantum_info.SparsePauliOp | PennyLaneOperatorType][source]

Sets up the qubit Hamiltonian in the transformed MO basis.

Parameters:

kappa (List) – Orbital rotation parameters vector.

Returns:

  • core_energy (float): The core energy after active space and MO transformation.

  • qubit_op (Union[SparsePauliOp, Operator]): If the format is qiskit, it returns a SparsePauliOp representing the tranformed qubit Hamiltonian in the qiskit format. If the format is pennylane, it returns a Operator instance representing the qubit Hamiltonian in the PennyLane format.

Return type:

Tuple[float, SparsePauliOp]

get_transformed_mos(kappa: List) Tuple[numpy.ndarray, numpy.ndarray][source]

Transforms MO coefficients with orbital rotation parameters.

Parameters:

kappa (List) – Orbital rotation parameters vector.

Returns:

A tuple containing the transformed

MO coefficients.

Return type:

Tuple[np.ndarray, np.ndarray]

_get_rotation_matrix(kappa: List) numpy.ndarray[source]

Creates rotation matrix from kappa parameters.

_kappa_vector_to_matrix(kappa: List) numpy.ndarray[source]

Generates skew-symm. matrix from orbital rotation parameters.

_kappa_matrix_to_vector(kappa_matrix: numpy.ndarray) numpy.ndarray[source]

Generate orbital rotation parameters from a skew-symmetric matrix

_full_hessian_to_matrix(full_hess: numpy.ndarray) numpy.ndarray[source]

Convert the full Hessian to a matrix with only non-red. indices.

_get_mo_coeffs() Tuple[numpy.ndarray, numpy.ndarray | None][source]

Extracts molecular orbital coefficients.

_get_activate_space_integrals(mo_coeff_a: numpy.ndarray, mo_coeff_b: numpy.ndarray | None) Tuple[float, List, List][source]

Extracts activate space integrals in MO basis.

_get_full_space_integrals(mo_coeff_a: numpy.ndarray, mo_coeff_b: numpy.ndarray | None) Tuple[List, List][source]

Extracts full space one- and two-electron integrals in MO basis.

class qc2.algorithms.utils.FermionicToQubitMapper[source]
_mappers
classmethod register_mapper(key: str, mapper: qiskit_nature.second_q.mappers.QubitMapper)[source]

Register a new mapper class with a given key.

Parameters:
  • key (str) – The key (name) for the mapper.

  • mapper (QubitMapper) – The mapper class to be registered.

Raises:

ValueError – If the key is already registered.

Example

>>> from qiskit_nature.second_q.mappers import TaperedQubitMapper
>>> from qc2.algorithms.utils import FermionicToQubitMapper
>>>
>>> FermionicToQubitMapper.register_mapper('TQM', TaperedQubitMapper)
>>> mapper = FermionicToQubitMapper.from_string('tqm')
classmethod from_string(s)[source]

Retrieve the mapper class corresponding to the provided string.

Parameters:

s (str) – The string identifier of the mapper. Case-insensitive.

Returns:

The corresponding mapper class.

Return type:

QubitMapper

Raises:

ValueError – If the provided string does not correspond to any known mapper.

Example

>>> from qc2.algorithms.utils import FermionicToQubitMapper
>>> mapper = FermionicToQubitMapper.from_string('jw'))