Orbitals

The Orbitals class in QDK/Chemistry represents a set of molecular orbitals. This class stores orbital coefficients, energies, and other properties necessary for quantum chemical calculations.

Overview

Molecular orbitals are a fundamental concept in quantum chemistry. They are formed through linear combinations of atomic orbitals and provide a framework for understanding chemical bonding and electronic structure. In QDK/Chemistry, the Orbitals class encapsulates all relevant information about these orbitals, including their coefficients, energies, and occupation numbers.

Restricted vs. unrestricted calculations

The Orbitals class supports both restricted and unrestricted calculations:

Restricted

Alpha and beta electrons share the same spatial orbitals (RHF, RKS)

Unrestricted

Alpha and beta electrons have separate spatial orbitals (UHF, UKS)

For restricted calculations, the alpha and beta components are identical. The class maintains separate alpha and beta data internally, but they reference the same underlying data for restricted cases.

Model orbitals

ModelOrbitals are a simpler class in QDK/Chemistry, for model systems without any basis set information. This class allows to fully specify model Hamiltonians and Wavefunctions. Several properties present for the Orbitals subclass are missing for ModelOrbitals: coefficients, energies, etc. These are summarized in the properties table below.

Properties

The following table summarizes the properties available for the different orbital types:

Orbital Properties Availability

Property

Description

Orbitals

ModelOrbitals

Coefficients

Matrix of orbital coefficients [AO × MO] for alpha and beta spin channels

Energies

Vector of orbital energies for alpha and beta spin channels

Active space indices

Active space indices for alpha and beta spin channels

Inactive space indices

Inactive space indices for alpha and beta spin channels

Virtual space indices

Virtual space indices for alpha and beta spin channels

MO overlap

Overlap matrices between MO, for both spin channels

✓*

Basis Set

Comprehensive basis set information

AO overlap

Overlap matrices between AO, for both spin channels

Note

* For ModelOrbitals, MO overlap matrices return identity matrices since model systems assume orthonormal orbitals.

For detailed information about basis sets in QDK/Chemistry, including available basis sets, creation, manipulation, and serialization, refer to the Basis Set documentation.

Usage

The Orbitals class is typically created as the output of an SCF calculation (Self-consistent field (SCF) solver) or orbital transformation. It serves as input to various post-HF methods such as active space selection and Hamiltonian construction.

Orbital Localization

Transform delocalized SCF orbitals into localized representations for better chemical interpretation and more efficient correlation methods. See Localizer for details.

Active Space Selection

Automatically identify important orbitals for multi-reference calculations based on various criteria. See ActiveSpaceSelector for details.

Hamiltonian Construction

Build electronic Hamiltonians for post-HF methods using the orbital information. See HamiltonianConstructor for details.

The below example illustrates the typical access to Orbitals (via a SCF):

#include <iostream>
#include <qdk/chemistry.hpp>
#include <string>
using namespace qdk::chemistry::data;
using namespace qdk::chemistry::algorithms;

int main() {
  // Obtain orbitals from a SCF calculation
  // Load H2 molecule from XYZ file
  auto structure = Structure::from_xyz_file("../data/h2.structure.xyz");

  // Obtain orbitals from a SCF calculation
  auto scf_solver = ScfSolverFactory::create();
  scf_solver->settings().set("basis_set", "sto-3g");
  auto [E_scf, wfn] = scf_solver->run(structure, 0, 1);
  std::shared_ptr<Orbitals> orbitals = wfn.get_orbitals();
# Load H2 molecule from XYZ file
structure = Structure.from_xyz_file(Path(__file__).parent / "../data/h2.structure.xyz")

# Obtain orbitals from a SCF calculation
scf_solver = create("scf_solver")
E_scf, wfn = scf_solver.run(
    structure, charge=0, spin_multiplicity=1, basis_or_guess="sto-3g"
)
orbitals = wfn.get_orbitals()

Similar patterns are described below for ModelOrbitals.

  // Set basis set size
  size_t basis_size = 6;

  // Set active orbitals
  std::vector<size_t> alpha_active = {1, 2};
  std::vector<size_t> beta_active = {2, 3, 4};
  std::vector<size_t> alpha_inactive = {0, 3, 4, 5};
  std::vector<size_t> beta_inactive = {0, 1, 5};

  ModelOrbitals model_orbitals(
      basis_size, std::make_tuple(alpha_active, beta_active, alpha_inactive,
                                  beta_inactive));

  // We can then pass this object to a custom Hamiltonian constructor
# Set basis set size
basis_size = 6

# Set active orbitals
alpha_active = [1, 2]
beta_active = [2, 3, 4]
alpha_inactive = [0, 3, 4, 5]
beta_inactive = [0, 1, 5]

model_orbitals = ModelOrbitals(
    basis_size, (alpha_active, beta_active, alpha_inactive, beta_inactive)
)

# We can then pass this object to a custom Hamiltonian constructor

Accessing Orbital data

The Orbitals class provides methods to access orbital coefficients, energies, and other properties. Following the immutable design principle used throughout QDK/Chemistry, all getter methods return const references or copies of the data. For spin-dependent properties, methods return pairs of (alpha, beta) data.

  // Access orbital coefficients (returns std::pair<const Eigen::MatrixXd&,
  // const Eigen::MatrixXd&>)
  auto [coeffs_alpha, coeffs_beta] = orbitals->get_coefficients();

  // Access orbital energies (returns std::pair<const Eigen::VectorXd&, const
  // Eigen::VectorXd&>)
  auto [energies_alpha, energies_beta] = orbitals->get_energies();

  // Get active space indices
  auto [active_indices_alpha, active_indices_beta] =
      orbitals->get_active_space_indices();

  // Access atomic orbital overlap matrix (returns const Eigen::MatrixXd&)
  const auto& ao_overlap = orbitals->get_overlap_matrix();

  // Access basis set information (returns const BasisSet&)
  const auto& basis_set = orbitals->get_basis_set();

  // Check calculation type
  bool is_restricted = orbitals->is_restricted();

  // Get size information
  size_t num_molecular_orbitals = orbitals->get_num_molecular_orbitals();
  size_t num_atomic_orbitals = orbitals->get_num_atomic_orbitals();

  std::string summary = orbitals->get_summary();
  std::cout << summary << std::endl;
# Access orbital coefficients (alpha, beta)
coeffs_alpha, coeffs_beta = orbitals.get_coefficients()

# Access orbital energies
energies_alpha, energies_beta = orbitals.get_energies()
# Get active space indices
active_indices_alpha, active_indices_beta = orbitals.get_active_space_indices()

# Access atomic orbital overlap matrix
ao_overlap = orbitals.get_overlap_matrix()

# Access basis set information
basis_set = orbitals.get_basis_set()

# Check calculation type
is_restricted = orbitals.is_restricted()

# Get size information
num_molecular_orbitals = orbitals.get_num_molecular_orbitals()
num_atomic_orbitals = orbitals.get_num_atomic_orbitals()

summary = orbitals.get_summary()
print(summary)

Orbital transformations and applications

The Orbitals class serves as a foundation for several important quantum chemical applications and transformations:

Orbital Localization

Transform delocalized SCF orbitals into localized representations for better chemical interpretation and more efficient correlation methods. See Localizer for details.

Active Space Selection

Automatically identify important orbitals for multi-reference calculations based on various criteria. See ActiveSpaceSelector for details.

Hamiltonian Construction

Build electronic Hamiltonians for post-HF methods using the orbital information. Both restricted and unrestricted Hamiltonians are automatically constructed based on the matching orbital type (restricted or unrestricted). See HamiltonianConstructor and Hamiltonian (including the Unrestricted Hamiltonians section) for details.

Further reading