Welcome to the docs¶
 Contents
 Tutorial: Introduction & Installation
 Examples: Code examples
 Code Documentation: The code documentation of OpenFermion.
Tutorial¶
Getting started with OpenFermion¶
Installing OpenFermion requires pip. Make sure that you are using an uptodate version of it by running:
python m pip upgrade pip
To install the latest development version of OpenFermion, clone this git repo, change directory to the top level folder and run:
python m pip install e .
Alternatively, if using OpenFermion as a library, one can install the last official PyPI release with:
python m pip install pre user openfermion
For further information about how to get started please see intro and code examples. Also take a look at the the ipython notebook demo in the examples folder of this repository as well as our detailed code documentation.
Basic OpenFermion example¶
To see a basic example with both fermion and qubit operators as well as whether the installation worked, try to run the following code.
from openfermion.ops import FermionOperator, hermitian_conjugated
from openfermion.transforms import jordan_wigner, bravyi_kitaev
from openfermion.utils import eigenspectrum
# Initialize an operator.
fermion_operator = FermionOperator('2^ 0', 3.17)
fermion_operator += hermitian_conjugated(fermion_operator)
print(fermion_operator)
# Transform to qubits under the JordanWigner transformation and print its spectrum.
jw_operator = jordan_wigner(fermion_operator)
jw_spectrum = eigenspectrum(jw_operator)
print(jw_operator)
print(jw_spectrum)
# Transform to qubits under the BravyiKitaev transformation and print its spectrum.
bk_operator = bravyi_kitaev(fermion_operator)
bk_spectrum = eigenspectrum(bk_operator)
print(bk_operator)
print(bk_spectrum)
This code creates the fermionic operator \(a^\dagger_2 a_0\) and adds its Hermitian conjugate \(a^\dagger_0 a_2\) to it. It then maps the resulting fermionic operator to qubit operators using two transforms included in OpenFermion, the JordanWigner and BravyiKitaev transforms. Despite the different representations, these operators are isospectral. The example also shows some of the intuitive string methods included in OpenFermion.
Further examples can be found in the docs (Examples in the panel on the left) and in the OpenFermion examples folder on GitHub.
Plugins¶
In order to simulate and compile quantum circuits or perform other complicated electronic structure calculations, one can install OpenFermion plugins. We currently support a circuit simulation plugin for ProjectQ, which you can find at OpenFermionProjectQ. We also support electronic structure plugins for Psi4, which you can find at OpenFermionPsi4 (recommended), and for PySCF, which you can find at OpenFermionPySCF.
Examples¶
All of these examples (and more!) are explained in detail in the ipython notebook openfermion_demo.ipynb located at GitHub. Note these examples demonstrate only a few (introductory) aspects of OpenFermion’s full functionality. To get the most out of OpenFermion, one must also install some of our plugins. We currently support a circuit simulation plugin for ProjectQ, which you can find at OpenFermionProjectQ. We also support electronic structure plugins for Psi4, which you can find at OpenFermionPsi4 (recommended), and for PySCF, which you can find at OpenFermionPySCF.
Fermionic Operators¶
Fermionic systems are often treated in second quantization, where arbitrary operators can be expressed using the fermionic creation and annihilation operators, \(a_k^\dagger\) and \(a_k\). Any weighted sum of products of these operators can be represented with the FermionOperator data structure in OpenFermion.
from openfermion.ops import FermionOperator
my_term = FermionOperator(((3, 1), (1, 0)))
print(my_term)
my_term = FermionOperator('3^ 1')
print(my_term)
These two examples yield the same fermionic operator, \(a_3^\dagger a_1\).
The preferred way to specify the coefficient in OpenFermion is to provide an optional coefficient argument. If not provided, the coefficient defaults to 1. In the code below, the first method is preferred. The multiplication in the last method actually creates a copy of the term, which introduces some additional cost. All inplace operands (such as +=) modify classes whereas binary operands such as + create copies. Important caveats are that the empty tuple FermionOperator(()) and the empty string FermionOperator(‘’) initialize identity. The empty initializer FermionOperator() initializes the zero operator. We demonstrate some of these below.
from openfermion.ops import FermionOperator
good_way_to_initialize = FermionOperator('3^ 1', 1.7)
print(good_way_to_initialize)
bad_way_to_initialize = 1.7 * FermionOperator('3^ 1')
print(bad_way_to_initialize)
identity = FermionOperator('')
print(identity)
zero_operator = FermionOperator()
print(zero_operator)
This creates the previous FermionOperator with a coefficient 1.7, as well as the identity and zero operators.
FermionOperator has only one attribute: .terms. This attribute is the dictionary which stores the term tuples.
from openfermion.ops import FermionOperator
my_operator = FermionOperator('4^ 1^ 3 9', 1. + 2.j)
print(my_operator)
print(my_operator.terms)
FermionOperator supports a wide range of builtins including str(), repr(), =, , /, /=, +, +=, , =,  and **. Note that instead of supporting != and ==, we have the method .isclose(), since FermionOperators involve floats.
Qubit Operators¶
The QubitOperator data structure is another essential part of OpenFermion. As the name suggests, QubitOperator is used to store qubit operators in almost exactly the same way that FermionOperator is used to store fermion operators. For instance \(X_0 Z_3 Y_4\) is a QubitOperator. The internal representation of this as a terms tuple would be \(((0, X),(3, Z),(4, Y))\). Note that one important difference between QubitOperator and FermionOperator is that the terms in QubitOperator are always sorted in order of tensor factor. In some cases, this enables faster manipulation. We initialize some QubitOperators below.
from openfermion.ops import QubitOperator
my_first_qubit_operator = QubitOperator('X1 Y2 Z3')
print(my_first_qubit_operator)
print(my_first_qubit_operator.terms)
operator_2 = QubitOperator('X3 Z4', 3.17)
operator_2 = 77. * my_first_qubit_operator
print(operator_2)
Transformations¶
OpenFermion also provides functions for mapping FermionOperators to QubitOperators, including the JordanWigner and BravyiKitaev transforms.
from openfermion.ops import FermionOperator, hermitian_conjugated
from openfermion.transforms import jordan_wigner, bravyi_kitaev
from openfermion.utils import eigenspectrum
# Initialize an operator.
fermion_operator = FermionOperator('2^ 0', 3.17)
fermion_operator += hermitian_conjugated(fermion_operator)
print(fermion_operator)
# Transform to qubits under the JordanWigner transformation and print its spectrum.
jw_operator = jordan_wigner(fermion_operator)
jw_spectrum = eigenspectrum(jw_operator)
print(jw_operator)
print(jw_spectrum)
# Transform to qubits under the BravyiKitaev transformation and print its spectrum.
bk_operator = bravyi_kitaev(fermion_operator)
bk_spectrum = eigenspectrum(bk_operator)
print(bk_operator)
print(bk_spectrum)
We see that despite the different representation, these operators are isospectral. We can also apply the JordanWigner transform in reverse to map arbitrary QubitOperators to FermionOperators. Note that we also demonstrate the .compress() method (a method on both FermionOperators and QubitOperators) which removes zero entries.
from openfermion.ops import QubitOperator
from openfermion.transforms import jordan_wigner, reverse_jordan_wigner
# Initialize QubitOperator.
my_operator = QubitOperator('X0 Y1 Z2', 88.)
my_operator += QubitOperator('Z1 Z4', 3.17)
print(my_operator)
# Map QubitOperator to a FermionOperator.
mapped_operator = reverse_jordan_wigner(my_operator)
print(mapped_operator)
# Map the operator back to qubits and make sure it is the same.
back_to_normal = jordan_wigner(mapped_operator)
back_to_normal.compress()
print(back_to_normal)
Sparse matrices and the Hubbard model¶
Often, one would like to obtain a sparse matrix representation of an operator which can be analyzed numerically. There is code in both openfermion.transforms and openfermion.utils which facilitates this. The function get_sparse_operator converts either a FermionOperator, a QubitOperator or other more advanced classes such as InteractionOperator to a scipy.sparse.csc matrix. There are numerous functions in openfermion.utils which one can call on the sparse operators such as “get_gap”, “get_hartree_fock_state”, “get_ground_state”, ect. We show this off by computing the ground state energy of the Hubbard model. To do that, we use code from the openfermion.hamiltonians module which constructs lattice models of fermions such as Hubbard models.
from openfermion.hamiltonians import fermi_hubbard
from openfermion.transforms import get_sparse_operator, jordan_wigner
from openfermion.utils import get_ground_state
# Set model.
x_dimension = 2
y_dimension = 2
tunneling = 2.
coulomb = 1.
magnetic_field = 0.5
chemical_potential = 0.25
periodic = 1
spinless = 1
# Get fermion operator.
hubbard_model = fermi_hubbard(
x_dimension, y_dimension, tunneling, coulomb, chemical_potential,
magnetic_field, periodic, spinless)
print(hubbard_model)
# Get qubit operator under JordanWigner.
jw_hamiltonian = jordan_wigner(hubbard_model)
jw_hamiltonian.compress()
print(jw_hamiltonian)
# Get scipy.sparse.csc representation.
sparse_operator = get_sparse_operator(hubbard_model)
print(sparse_operator)
print('\nEnergy of the model is {} in units of T and J.'.format(
get_ground_state(sparse_operator)[0]))
Basics of MolecularData class¶
Data from electronic structure calculations can be saved in a OpenFermion data structure called MolecularData, which makes it easy to access within our library. Often, one would like to analyze a chemical series or look at many different Hamiltonians and sometimes the electronic structure calculations are either expensive to compute or difficult to converge (e.g. one needs to mess around with different types of SCF routines to make things converge). Accordingly, we anticipate that users will want some way to automatically database the results of their electronic structure calculations so that important data (such as the SCF intergrals) can be looked up onthefly if the user has computed them in the past. OpenFermion supports a data provenance strategy which saves key results of the electronic structure calculation (including pointers to files containing large amounts of data, such as the molecular integrals) in an HDF5 container.
The MolecularData class stores information about molecules. One initializes a MolecularData object by specifying parameters of a molecule such as its geometry, basis, multiplicity, charge and an optional string describing it. One can also initialize MolecularData simply by providing a string giving a filename where a previous MolecularData object was saved in an HDF5 container. One can save a MolecularData instance by calling the class’s .save() method. This automatically saves the instance in a data folder specified during OpenFermion installation. The name of the file is generated automatically from the instance attributes and optionally provided description. Alternatively, a filename can also be provided as an optional input if one wishes to manually name the file.
When electronic structure calculations are run, the data files for the molecule can be automatically updated. If one wishes to later use that data they either initialize MolecularData with the instance filename or initialize the instance and then later call the .load() method.
Basis functions are provided to initialization using a string such as “631g”. Geometries can be specified using a simple txt input file (see geometry_from_file function in molecular_data.py) or can be passed using a simple python list format demonstrated below. Atoms are specified using a string for their atomic symbol. Distances should be provided in atomic units (Bohr). Below we initialize a simple instance of MolecularData without performing any electronic structure calculations.
from openfermion.hamiltonians import MolecularData
# Set parameters to make a simple molecule.
diatomic_bond_length = .7414
geometry = [('H', (0., 0., 0.)), ('H', (0., 0., diatomic_bond_length))]
basis = 'sto3g'
multiplicity = 1
charge = 0
description = str(diatomic_bond_length)
# Make molecule and print out a few interesting facts about it.
molecule = MolecularData(geometry, basis, multiplicity,
charge, description)
print('Molecule has automatically generated name {}'.format(
molecule.name))
print('Information about this molecule would be saved at:\n{}\n'.format(
molecule.filename))
print('This molecule has {} atoms and {} electrons.'.format(
molecule.n_atoms, molecule.n_electrons))
for atom, atomic_number in zip(molecule.atoms, molecule.protons):
print('Contains {} atom, which has {} protons.'.format(
atom, atomic_number))
If we had previously computed this molecule using an electronic structure package, we can call molecule.load() to populate all sorts of interesting fields in the data structure. Though we make no assumptions about what electronic structure packages users might install, we assume that the calculations are saved in Fermilib’s MolecularData objects. There may be plugins available in future. For the purposes of this example, we will load data that ships with OpenFermion to make a plot of the energy surface of hydrogen. Note that helper functions to initialize some interesting chemical benchmarks are found in openfermion.utils.
# Set molecule parameters.
basis = 'sto3g'
multiplicity = 1
bond_length_interval = 0.1
n_points = 25
# Generate molecule at different bond lengths.
hf_energies = []
fci_energies = []
bond_lengths = []
for point in range(3, n_points + 1):
bond_length = bond_length_interval * point
bond_lengths += [bond_length]
description = str(round(bond_length,2))
print(description)
geometry = [('H', (0., 0., 0.)), ('H', (0., 0., bond_length))]
molecule = MolecularData(
geometry, basis, multiplicity, description=description)
# Load data.
molecule.load()
# Print out some results of calculation.
print('\nAt bond length of {} Bohr, molecular hydrogen has:'.format(
bond_length))
print('HartreeFock energy of {} Hartree.'.format(molecule.hf_energy))
print('MP2 energy of {} Hartree.'.format(molecule.mp2_energy))
print('FCI energy of {} Hartree.'.format(molecule.fci_energy))
print('Nuclear repulsion energy between protons is {} Hartree.'.format(
molecule.nuclear_repulsion))
for orbital in range(molecule.n_orbitals):
print('Spatial orbital {} has energy of {} Hartree.'.format(
orbital, molecule.orbital_energies[orbital]))
hf_energies += [molecule.hf_energy]
fci_energies += [molecule.fci_energy]
InteractionOperator and InteractionRDM for efficient numerical representations¶
Fermion Hamiltonians can be expressed as \(H=h_0+\sum_{pq} h_{pq} a^\dagger_p a_q + \frac12 \sum_{pqrs} h_{pqrs} a^\dagger_p a^\dagger_q a_r a_s\), where \(h_0\) is a constant shift due to the nuclear repulsion and \(h_{pq}\) and \(h_{pqrs}\) are the famous molecular integrals. Since fermions interact pairwise, their energy is thus a unique function of the oneparticle and twoparticle reduced density matrices which are expressed in second quantization as \(\rho_{pq} = \langle p  a^\dagger_p a_q  q\rangle\) and \(\rho_{pqrs} = \langle pq  a^\dagger_p a^\dagger_q a_r a_s  rs \rangle\), respectively.
Because the RDMs and molecular Hamiltonians are both compactly represented and manipulated as 2 and 4 index tensors, we can represent them in a particularly efficient form using similar data structures. The InteractionOperator data structure can be initialized for a Hamiltonian by passing the constant h0h0 (or 0), as well as numpy arrays representing \(h_{pq}\) (or \(\rho_{pq}\)) and \(h_{pqrs}\) (or \(\rho_{pqrs}\)). Importantly, InteractionOperators can also be obtained by calling MolecularData.get_molecular_hamiltonian() or by calling the function get_interaction_operator() (found in openfermion.transforms) on a FermionOperator. The InteractionRDM data structure is similar but represents RDMs. For instance, one can get a molecular RDM by calling MolecularData.get_molecular_rdm(). When generating Hamiltonians from the MolecularData class, one can choose to restrict the system to an active space.
These classes inherit from the same base class, PolynomialTensor. This data structure overloads the slice operator [] so that one can get or set the key attributes of the InteractionOperator: .constant, .one_body_coefficients and .two_body_coefficients. For instance, InteractionOperator[(p, 1), (q, 1), (r, 0), (s, 0)] would return \(h_{pqrs}\) and InteractionRDM would return \(\rho_{pqrs}\). Importantly, the class supports fast basis transformations using the method PolynomialTensor.rotate_basis(rotation_matrix). But perhaps most importantly, one can map the InteractionOperator to any of the other data structures we’ve described here.
Below, we load MolecularData from a saved calculation of LiH. We then obtain an InteractionOperator representation of this system in an active space. We then map that operator to qubits. We then demonstrate that one can rotate the orbital basis of the InteractionOperator using random angles to obtain a totally different operator that is still isospectral.
from openfermion.hamiltonians import MolecularData
from openfermion.transforms import get_fermion_operator, get_sparse_operator, jordan_wigner
from openfermion.utils import get_ground_state
import numpy
import scipy
import scipy.linalg
# Load saved file for LiH.
diatomic_bond_length = 1.45
geometry = [('Li', (0., 0., 0.)), ('H', (0., 0., diatomic_bond_length))]
basis = 'sto3g'
multiplicity = 1
# Set Hamiltonian parameters.
active_space_start = 1
active_space_stop = 3
# Generate and populate instance of MolecularData.
molecule = MolecularData(geometry, basis, multiplicity, description=\"1.45\")
molecule.load()
# Get the Hamiltonian in an active space.
molecular_hamiltonian = molecule.get_molecular_hamiltonian(
occupied_indices=range(active_space_start),
active_indices=range(active_space_start, active_space_stop))
# Map operator to fermions and qubits.
fermion_hamiltonian = get_fermion_operator(molecular_hamiltonian)
qubit_hamiltonian = jordan_wigner(fermion_hamiltonian)
qubit_hamiltonian.compress()
print('The JordanWigner Hamiltonian in canonical basis follows:\n{}'.format(qubit_hamiltonian))
# Get sparse operator and ground state energy.
sparse_hamiltonian = get_sparse_operator(qubit_hamiltonian)
energy, state = get_ground_state(sparse_hamiltonian)
print('Ground state energy before rotation is {} Hartree.\n'.format(energy))
# Randomly rotate.
n_orbitals = molecular_hamiltonian.n_qubits // 2
n_variables = int(n_orbitals * (n_orbitals  1) / 2)
random_angles = numpy.pi * (1.  2. * numpy.random.rand(n_variables))
kappa = numpy.zeros((n_orbitals, n_orbitals))
index = 0
for p in range(n_orbitals):
for q in range(p + 1, n_orbitals):
kappa[p, q] = random_angles[index]
kappa[q, p] = numpy.conjugate(random_angles[index])
index += 1
# Build the unitary rotation matrix.
difference_matrix = kappa + kappa.transpose()
rotation_matrix = scipy.linalg.expm(kappa)
# Apply the unitary.
molecular_hamiltonian.rotate_basis(rotation_matrix)
# Get qubit Hamiltonian in rotated basis.
qubit_hamiltonian = jordan_wigner(molecular_hamiltonian)
qubit_hamiltonian.compress()
print('The JordanWigner Hamiltonian in rotated basis follows:\n{}'.format(qubit_hamiltonian))
# Get sparse Hamiltonian and energy in rotated basis.
sparse_hamiltonian = get_sparse_operator(qubit_hamiltonian)
energy, state = get_ground_state(sparse_hamiltonian)
print('Ground state energy after rotation is {} Hartree.'.format(energy))
Code Documentation¶
openfermion.hamiltonians¶

class
openfermion.hamiltonians.
MolecularData
(geometry=None, basis=None, multiplicity=None, charge=0, description='', filename='', data_directory=None)¶ Class for storing molecule data from a fixed basis set at a fixed geometry that is obtained from classical electronic structure packages. Not every field is filled in every calculation. All data that can (for some instance) exceed 10 MB should be saved separately. Data saved in HDF5 format.

geometry
¶ A list of tuples giving the coordinates of each atom. An example is [(‘H’, (0, 0, 0)), (‘H’, (0, 0, 0.7414))]. Distances in angstrom. Use atomic symbols to specify atoms.

basis
¶ A string giving the basis set. An example is ‘ccpvtz’.

charge
¶ An integer giving the total molecular charge. Defaults to 0.

multiplicity
¶ An integer giving the spin multiplicity.

description
¶ An optional string giving a description. As an example, for dimers a likely description is the bond length (e.g. 0.7414).

name
¶ A string giving a characteristic name for the instance.

filename
¶ The name of the file where the molecule data is saved.

n_atoms
¶ Integer giving the number of atoms in the molecule.

n_electrons
¶ Integer giving the number of electrons in the molecule.

atoms
¶ List of the atoms in molecule sorted by atomic number.

protons
¶ List of atomic charges in molecule sorted by atomic number.

hf_energy
¶ Energy from open or closed shell HartreeFock.

nuclear_repulsion
¶ Energy from nucleinuclei interaction.

canonical_orbitals
¶ numpy array giving canonical orbital coefficients.

n_orbitals
¶ Integer giving total number of spatial orbitals.

n_qubits
¶ Integer giving total number of qubits that would be needed.

orbital_energies
¶ Numpy array giving the canonical orbital energies.

fock_matrix
¶ Numpy array giving the Fock matrix.

overlap_integrals
¶ Numpy array of AO overlap integrals

one_body_integrals
¶ Numpy array of oneelectron integrals

two_body_integrals
¶ Numpy array of twoelectron integrals

mp2_energy
¶ Energy from MP2 perturbation theory.

cisd_energy
¶ Energy from configuration interaction singles + doubles.

cisd_one_rdm
¶ Numpy array giving 1RDM from CISD calculation.

cisd_two_rdm
¶ Numpy array giving 2RDM from CISD calculation.

fci_energy
¶ Exact energy of molecule within given basis.

fci_one_rdm
¶ Numpy array giving 1RDM from FCI calculation.

fci_two_rdm
¶ Numpy array giving 2RDM from FCI calculation.

ccsd_energy
¶ Energy from coupled cluster singles + doubles.

ccsd_single_amps
¶ Numpy array holding single amplitudes

ccsd_double_amps
¶ Numpy array holding double amplitudes

general_calculations
¶ A dictionary storing general calculation results for this system annotated by the key.

__init__
(geometry=None, basis=None, multiplicity=None, charge=0, description='', filename='', data_directory=None)¶ Initialize molecular metadata which defines class.
Parameters:  geometry – A list of tuples giving the coordinates of each atom. An example is [(‘H’, (0, 0, 0)), (‘H’, (0, 0, 0.7414))]. Distances in angstrom. Use atomic symbols to specify atoms. Only optional if loading from file.
 basis – A string giving the basis set. An example is ‘ccpvtz’. Only optional if loading from file.
 charge – An integer giving the total molecular charge. Defaults to 0. Only optional if loading from file.
 multiplicity – An integer giving the spin multiplicity. Only optional if loading from file.
 description – A optional string giving a description. As an example, for dimers a likely description is the bond length (e.g. 0.7414).
 filename – An optional string giving name of file. If filename is not provided, one is generated automatically.
 data_directory – Optional data directory to change from default data directory specified in config file.

get_active_space_integrals
(occupied_indices=None, active_indices=None)¶ Restricts a molecule at a spatial orbital level to an active space
 This active space may be defined by a list of active indices and
 doubly occupied indices. Note that one_body_integrals and two_body_integrals must be defined n an orthonormal basis set.
Parameters:  occupied_indices – A list of spatial orbital indices indicating which orbitals should be considered doubly occupied.
 active_indices – A list of spatial orbital indices indicating which orbitals should be considered active.
Returns: tuple – Tuple with the following entries:
core_constant: Adjustment to constant shift in Hamiltonian from integrating out core orbitals
one_body_integrals_new: oneelectron integrals over active space.
two_body_integrals_new: twoelectron integrals over active space.

get_from_file
(property_name)¶ Helper routine to reopen HDF5 file and pull out single property
Parameters: property_name – Property name to load from self.filename Returns:  The data located at file[property_name] for the HDF5 file at
 self.filename. Returns None if the key is not found in the file.

get_integrals
()¶ Method to return 1electron and 2electron integrals in MO basis.
Returns: one_body_integrals –  An array of the oneelectron integrals having
 shape of (n_orbitals, n_orbitals).
 two_body_integrals: An array of the twoelectron integrals having
 shape of (n_orbitals, n_orbitals, n_orbitals, n_orbitals).
Raises: MisissingCalculationError
– If integrals are not calculated.

get_molecular_hamiltonian
(occupied_indices=None, active_indices=None)¶ Output arrays of the second quantized Hamiltonian coefficients.
Parameters:  occupied_indices (list) – A list of spatial orbital indices indicating which orbitals should be considered doubly occupied.
 active_indices (list) – A list of spatial orbital indices indicating which orbitals should be considered active.
Returns: molecular_hamiltonian – An instance of the MolecularOperator class.

get_molecular_rdm
(use_fci=False)¶ Method to return 1RDM and 2RDMs from CISD or FCI.
Parameters: use_fci – Boolean indicating whether to use RDM from FCI calculation. Returns: rdm – An instance of the MolecularRDM class. Raises: MisissingCalculationError
– If the CI calculation has not been performed.

get_n_alpha_electrons
()¶ Return number of alpha electrons.

get_n_beta_electrons
()¶ Return number of beta electrons.

init_lazy_properties
()¶ Initializes properties loaded on demand to None

save
()¶ Method to save the class under a systematic name.


openfermion.hamiltonians.
down_index
(index)¶ Function to return downorbital index given a spatial orbital index.
Parameters: index (Int) – spatial orbital index

openfermion.hamiltonians.
dual_basis_external_potential
(grid, geometry, spinless)¶ Return the external potential in the dual basis of arXiv:1706.00023.
Parameters:  grid (Grid) – The discretization to use.
 geometry – A list of tuples giving the coordinates of each atom. example is [(‘H’, (0, 0, 0)), (‘H’, (0, 0, 0.7414))]. Distances in atomic units. Use atomic symbols to specify atoms.
 spinless (bool) – Whether to use the spinless model or not.
Returns: FermionOperator – The dual basis operator.

openfermion.hamiltonians.
dual_basis_jellium_model
(grid, spinless=False, kinetic=True, potential=True, include_constant=False)¶ Return jellium Hamiltonian in the dual basis of arXiv:1706.00023
Parameters:  grid (Grid) – The discretization to use.
 spinless (bool) – Whether to use the spinless model or not.
 kinetic (bool) – Whether to include kinetic terms.
 potential (bool) – Whether to include potential terms.
 include_constant (bool) – Whether to include the Madelung constant.
Returns: operator (FermionOperator)

openfermion.hamiltonians.
dual_basis_kinetic
(grid, spinless=False)¶ Return the kinetic operator in the dual basis of arXiv:1706.00023.
Parameters:  grid (Grid) – The discretization to use.
 spinless (bool) – Whether to use the spinless model or not.
Returns: operator (FermionOperator)

openfermion.hamiltonians.
dual_basis_potential
(grid, spinless=False)¶ Return the potential operator in the dual basis of arXiv:1706.00023
Parameters:  grid (Grid) – The discretization to use.
 spinless (bool) – Whether to use the spinless model or not.
Returns: operator (FermionOperator)

openfermion.hamiltonians.
fermi_hubbard
(x_dimension, y_dimension, tunneling, coulomb, chemical_potential=0.0, magnetic_field=0.0, periodic=True, spinless=False, particle_hole_symmetry=False, up_map=<function up_index>, down_map=<function down_index>)¶ Return symbolic representation of a FermiHubbard Hamiltonian.
The idea of this model is that some fermions move around on a grid and the energy of the model depends on where the fermions are. The Hamiltonians of this model live on a grid of dimensions x_dimension x y_dimension. The grid can have periodic boundary conditions or not. In the standard FermiHubbard model (which we call the “spinful” model), there is room for an “up” fermion and a “down” fermion at each site on the grid. In this model, there are a total of 2N spinorbitals, where N = x_dimension * y_dimension is the number of sites. In the spinless model, there is only one spinorbital per site for a total of N.
The Hamiltonian for the spinful model has the form
\[\begin{split}\begin{align} H = & t \sum_{\langle i,j \rangle} \sum_{\sigma} (a^\dagger_{i, \sigma} a_{j, \sigma} + a^\dagger_{j, \sigma} a_{i, \sigma}) + U \sum_{i} a^\dagger_{i, \uparrow} a_{i, \uparrow} a^\dagger_{j, \downarrow} a_{j, \downarrow} \\ & \mu \sum_i \sum_{\sigma} a^\dagger_{i, \sigma} a_{i, \sigma}  h \sum_i (a^\dagger_{i, \uparrow} a_{i, \uparrow}  a^\dagger_{i, \downarrow} a_{i, \downarrow}) \end{align}\end{split}\]where
 The indices \(\langle i, j \rangle\) run over pairs \(i\) and \(j\) of sites that are connected to each other in the grid
 \(\sigma \in \{\uparrow, \downarrow\}\) is the spin
 \(t\) is the tunneling amplitude
 \(U\) is the Coulomb potential
 \(\mu\) is the chemical potential
 \(h\) is the magnetic field
One can also construct the Hamiltonian for the spinless model, which has the form
\[H =  t \sum_{k=1}^{N1} (a_k^\dagger a_{k + 1} + a_{k+1}^\dagger a_k) + U \sum_{k=1}^{N1} a_k^\dagger a_k a_{k+1}^\dagger a_{k+1}  \mu \sum_{k=1}^N a_k^\dagger a_k.\]Parameters:  x_dimension (int) – The width of the grid.
 y_dimension (int) – The height of the grid.
 tunneling (float) – The tunneling amplitude \(t\).
 coulomb (float) – The attractive local interaction strength \(U\).
 chemical_potential (float, optional) – The chemical potential \(\mu\) at each site. Default value is 0.
 magnetic_field (float, optional) – The magnetic field \(h\) at each site. Default value is 0. Ignored for the spinless case.
 periodic (bool, optional) – If True, add periodic boundary conditions. Default is True.
 spinless (bool, optional) – If True, return a spinless FermiHubbard model. Default is False.
 particle_hole_symmetry (bool, optional) –
If False, the repulsion term corresponds to:
\[U \sum_{k=1}^{N1} a_k^\dagger a_k a_{k+1}^\dagger a_{k+1}\]If True, the repulsion term is replaced by:
\[U \sum_{k=1}^{N1} (a_k^\dagger a_k  \frac12) (a_{k+1}^\dagger a_{k+1}  \frac12)\]which is unchanged under a particlehole transformation. Default is False
Returns: hubbard_model – An instance of the FermionOperator class.

openfermion.hamiltonians.
jellium_model
(grid, spinless=False, plane_wave=True, include_constant=False, e_cutoff=None)¶ Return jellium Hamiltonian as FermionOperator class.
Parameters:  grid (openfermion.utils.Grid) – The discretization to use.
 spinless (bool) – Whether to use the spinless model or not.
 plane_wave (bool) – Whether to return in momentum space (True) or position space (False).
 include_constant (bool) – Whether to include the Madelung constant.
 e_cutoff (float) – Energy cutoff.
Returns: FermionOperator – The Hamiltonian of the model.

openfermion.hamiltonians.
jordan_wigner_dual_basis_hamiltonian
(grid, geometry=None, spinless=False, include_constant=False)¶ Return the dual basis Hamiltonian as QubitOperator.
Parameters:  grid (Grid) – The discretization to use.
 geometry – A list of tuples giving the coordinates of each atom. example is [(‘H’, (0, 0, 0)), (‘H’, (0, 0, 0.7414))]. Distances in atomic units. Use atomic symbols to specify atoms.
 spinless (bool) – Whether to use the spinless model or not.
 include_constant (bool) – Whether to include the Madelung constant.
Returns: hamiltonian (QubitOperator)

openfermion.hamiltonians.
jordan_wigner_dual_basis_jellium
(grid, spinless=False, include_constant=False)¶ Return the jellium Hamiltonian as QubitOperator in the dual basis.
Parameters:  grid (Grid) – The discretization to use.
 spinless (bool) – Whether to use the spinless model or not.
 include_constant (bool) – Whether to include the Madelung constant.
Returns: hamiltonian (QubitOperator)

openfermion.hamiltonians.
majorana_operator
(term=None, coefficient=1.0)¶ Initialize a Majorana operator.
Parameters:  term (tuple) –
The first element of the tuple indicates the mode on which the Majorana operator acts, starting from zero. The second element of the tuple is an integer, either 1 or 0, indicating which type of Majorana operator it is:
Type 1: \(\frac{1}{\sqrt{2}} (a^\dagger_p + a_p)\)Type 0: \(\frac{i}{\sqrt{2}} (a^\dagger_p  a_p)\)
where the \(a^\dagger_p\) and \(a_p\) are the usual fermionic ladder operators. Default will result in the zero operator.
 coefficient (complex or float, optional) – The coefficient of the term. Default value is 1.0.
Returns: FermionOperator
 term (tuple) –

openfermion.hamiltonians.
make_atom
(atom_type, basis, filename='')¶ Prepare a molecular data instance for a single element.
Parameters:  atom_type – Float giving atomic symbol.
 basis – The basis in which to perform the calculation.
Returns: atom – An instance of the MolecularData class.

openfermion.hamiltonians.
make_atomic_lattice
(nx_atoms, ny_atoms, nz_atoms, spacing, basis, atom_type='H', charge=0, filename='')¶ Function to create atomic lattice with n_atoms.
Parameters:  nx_atoms – Integer, the length of lattice (in number of atoms).
 ny_atoms – Integer, the width of lattice (in number of atoms).
 nz_atoms – Integer, the depth of lattice (in number of atoms).
 spacing – The spacing between atoms in the lattice in Angstroms.
 basis – The basis in which to perform the calculation.
 atom_type – String, the atomic symbol of the element in the ring. this defaults to ‘H’ for Hydrogen.
 charge – An integer giving the total molecular charge. Defaults to 0.
 filename – An optional string to give a filename for the molecule.
Returns: molecule – A an instance of the MolecularData class.
Raises: MolecularLatticeError
– If lattice specification is invalid.

openfermion.hamiltonians.
make_atomic_ring
(n_atoms, spacing, basis, atom_type='H', charge=0, filename='')¶ Function to create atomic rings with n_atoms.
Note that basic geometry suggests that for spacing L between atoms the radius of the ring should be L / (2 * cos (pi / 2  theta / 2))
Parameters:  n_atoms – Integer, the number of atoms in the ring.
 spacing – The spacing between atoms in the ring in Angstroms.
 basis – The basis in which to perform the calculation.
 atom_type – String, the atomic symbol of the element in the ring. this defaults to ‘H’ for Hydrogen.
 charge – An integer giving the total molecular charge. Defaults to 0.
 filename – An optional string to give a filename for the molecule.
Returns: molecule – A an instance of the MolecularData class.

openfermion.hamiltonians.
mean_field_dwave
(x_dimension, y_dimension, tunneling, sc_gap, chemical_potential=0.0, periodic=True, up_map=<function up_index>, down_map=<function down_index>)¶ Return symbolic representation of a BCS meanfield dwave Hamiltonian.
The Hamiltonians of this model live on a grid of dimensions x_dimension x y_dimension. The grid can have periodic boundary conditions or not. Each site on the grid can have an “up” fermion and a “down” fermion. Therefore, there are a total of 2N spinorbitals, where N = x_dimension * y_dimension is the number of sites.
The Hamiltonian for this model has the form
\[\begin{split}\begin{align} H = & t \sum_{\langle i,j \rangle} \sum_\sigma (a^\dagger_{i, \sigma} a_{j, \sigma} + a^\dagger_{j, \sigma} a_{i, \sigma})  \mu \sum_i \sum_{\sigma} a^\dagger_{i, \sigma} a_{i, \sigma} \\ & \sum_{\langle i,j \rangle} \Delta_{ij} (a^\dagger_{i, \uparrow} a^\dagger_{j, \downarrow}  a^\dagger_{i, \downarrow} a^\dagger_{j, \uparrow} + a_{j, \downarrow} a_{i, \uparrow}  a_{j, \uparrow} a_{i, \downarrow}) \end{align}\end{split}\]where
 The indices \(\langle i, j \rangle\) run over pairs \(i\) and \(j\) of sites that are connected to each other in the grid
 \(\sigma \in \{\uparrow, \downarrow\}\) is the spin
 \(t\) is the tunneling amplitude
 \(\Delta_{ij}\) is equal to \(+\Delta/2\) for horizontal edges and \(\Delta/2\) for vertical edges, where \(\Delta\) is the superconducting gap.
 \(\mu\) is the chemical potential
Parameters:  x_dimension (int) – The width of the grid.
 y_dimension (int) – The height of the grid.
 tunneling (float) – The tunneling amplitude \(t\).
 sc_gap (float) – The superconducting gap \(\Delta\)
 chemical_potential (float, optional) – The chemical potential \(\mu\) at each site. Default value is 0.
 periodic (bool, optional) – If True, add periodic boundary conditions. Default is True.
Returns: mean_field_dwave_model – An instance of the FermionOperator class.

openfermion.hamiltonians.
number_operator
(n_orbitals, orbital=None, coefficient=1.0)¶ Return a number operator.
Parameters:  n_orbitals (int) – The number of spinorbitals in the system.
 orbital (int, optional) – The orbital on which to return the number operator. If None, return total number operator on all sites.
 coefficient (float) – The coefficient of the term.
Returns: operator (FermionOperator)

openfermion.hamiltonians.
plane_wave_external_potential
(grid, geometry, spinless, e_cutoff=None)¶ Return the external potential operator in plane wave basis.
Parameters:  grid (Grid) – The discretization to use.
 geometry – A list of tuples giving the coordinates of each atom. example is [(‘H’, (0, 0, 0)), (‘H’, (0, 0, 0.7414))]. Distances in atomic units. Use atomic symbols to specify atoms.
 spinless – Bool, whether to use the spinless model or not.
 e_cutoff (float) – Energy cutoff.
Returns: FermionOperator – The plane wave operator.

openfermion.hamiltonians.
plane_wave_hamiltonian
(grid, geometry=None, spinless=False, plane_wave=True, include_constant=False, e_cutoff=None)¶ Returns Hamiltonian as FermionOperator class.
Parameters:  grid (Grid) – The discretization to use.
 geometry – A list of tuples giving the coordinates of each atom. example is [(‘H’, (0, 0, 0)), (‘H’, (0, 0, 0.7414))]. Distances in atomic units. Use atomic symbols to specify atoms.
 spinless (bool) – Whether to use the spinless model or not.
 plane_wave (bool) – Whether to return in plane wave basis (True) or plane wave dual basis (False).
 include_constant (bool) – Whether to include the Madelung constant.
 e_cutoff (float) – Energy cutoff.
Returns: FermionOperator – The hamiltonian.

openfermion.hamiltonians.
plane_wave_kinetic
(grid, spinless=False, e_cutoff=None)¶ Return the kinetic energy operator in the plane wave basis.
Parameters:  grid (openfermion.utils.Grid) – The discretization to use.
 spinless (bool) – Whether to use the spinless model or not.
 e_cutoff (float) – Energy cutoff.
Returns: FermionOperator – The kinetic momentum operator.

openfermion.hamiltonians.
plane_wave_potential
(grid, spinless=False, e_cutoff=None)¶ Return the potential operator in the plane wave basis.
Parameters:  grid (Grid) – The discretization to use.
 spinless (bool) – Whether to use the spinless model or not.
 e_cutoff (float) – Energy cutoff.
Returns: operator (FermionOperator)

openfermion.hamiltonians.
s_minus_operator
(n_spatial_orbitals, up_map=<function up_index>, down_map=<function down_index>)¶ Return the s+ operator.
\[\begin{align} S^{} = \sum_{i=1}^{n} a_{i, \beta}^{\dagger}a_{i, \alpha} \end{align}\]Parameters:  n_spatial_orbitals – number of spatial orbitals (n_qubits + 1 // 2).
 up_map – function mapping a spatial index to a spinorbital index. Default is the canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals
 down_map – function mapping spatial index to spinorbital index. Default is canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals.
Returns: operator (FermionOperator) – corresponding to the s operator over n_spatial_orbitals.
Warning
Default assumes a number occupation vector representation with even spinless fermions corresponding to spinup (alpha) and odd spinless fermions corresponding to spindown (beta).

openfermion.hamiltonians.
s_plus_operator
(n_spatial_orbitals, up_map=<function up_index>, down_map=<function down_index>)¶ Return the s+ operator.
\[\begin{align} S^{+} = \sum_{i=1}^{n} a_{i, \alpha}^{\dagger}a_{i, \beta} \end{align}\]Parameters:  n_spatial_orbitals – number of spatial orbitals (n_qubits + 1 // 2).
 up_map – function mapping a spatial index to a spinorbital index. Default is the canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals
 down_map – function mapping spatial index to spinorbital index. Default is canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals.
Returns: operator (FermionOperator) – corresponding to the s+ operator over n_spatial_orbitals.
Warning
Default assumes a number occupation vector representation with even spinless fermions corresponding to spinup (alpha) and odd spinless fermions corresponding to spindown (beta).

openfermion.hamiltonians.
s_squared_operator
(n_spatial_orbitals)¶ Return the s^{2} operator.
\[\begin{align} S^{2} = S^{} S^{+} + S^{z}( S^{z} + 1) \end{align}\]Parameters: n_spatial_orbitals – number of spatial orbitals (n_qubits + 1 // 2). Returns: operator (FermionOperator) – corresponding to the s+ operator over n_spatial_orbitals. Warning
assumes a number occupation vector representation with even spinless fermions corresponding to spinup (alpha) and odd spinless fermions corresponding to spindown (beta).

openfermion.hamiltonians.
sz_operator
(n_spatial_orbitals, up_map=<function up_index>, down_map=<function down_index>)¶ Return the sz operator.
\[\begin{align} S^{z} = \frac{1}{2}\sum_{i = 1}^{n}(n_{i, \alpha}  n_{i, \beta}) \end{align}\]Parameters:  n_spatial_orbitals – number of spatial orbitals (n_qubits // 2).
 up_map – function mapping a spatial index to a spinorbital index. Default is the canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals
 down_map – function mapping spatial index to spinorbital index. Default is canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals.
Returns: operator (FermionOperator) – corresponding to the sz operator over n_spatial_orbitals.
Warning
Default assumes a number occupation vector representation with even spinless fermions corresponding to spinup (alpha) and odd spinless fermions corresponding to spindown (beta).

openfermion.hamiltonians.
up_index
(index)¶ Function to return uporbital index given a spatial orbital index.
Parameters: index (Int) – spatial orbital index

openfermion.hamiltonians.
wigner_seitz_length_scale
(wigner_seitz_radius, n_particles, dimension)¶ Function to give length_scale associated with WignerSeitz radius.
Parameters:  wigner_seitz_radius (float) – The radius per particle in atomic units.
 n_particles (int) – The number of particles in the simulation cell.
 dimension (int) – The dimension of the system.
Returns: length_scale (float) – The length scale for the simulation.
Raises: ValueError
– System dimension must be a positive integer.
openfermion.measurements¶

openfermion.measurements.
apply_constraints
(operator, n_fermions, use_scipy=True)¶ Function to use linear programming to apply constraints.
Parameters:  operator (FermionOperator) – FermionOperator with only 1 and 2body terms that we wish to vectorize.
 n_fermions (int) – The number of particles in the simulation.
 use_scipy (bool) – Whether to use scipy (True) or cvxopt (False).
Returns: modified_operator(FermionOperator) –
 The operator with reduced norm
that has been modified with equality constraints.

openfermion.measurements.
constraint_matrix
(n_orbitals, n_fermions)¶ Function to generate matrix of constraints.
Parameters:  n_orbitals (int) – The number of orbitals in the simulation.
 n_fermions (int) – The number of particles in the simulation.
Returns: constraint_matrix(scipy.sparse.coo_matrix) – The matrix of constraints.

openfermion.measurements.
linearize_term
(term, n_orbitals)¶ Function to return integer index of term indices.
Parameters:  term (tuple) – The term indices of a one or twobody FermionOperator.
 n_orbitals (int) – The number of orbitals in the simulation.
Returns: index(int) – The index of the term.

openfermion.measurements.
one_body_fermion_constraints
(n_orbitals, n_fermions)¶ Generates onebody positivity constraints on fermionic RDMs.
The specific constraints implemented are known positivity constraints on the onefermion reduced density matrices. Constraints are generated in the form of FermionOperators whose expectation value is known to be zero for any NRepresentable state. Generators are used for efficiency.Parameters:  n_orbitals (int) – number of spinorbitals on which operators act.
 n_fermions (int) – number of fermions in the system.
Yields: Constraint is a FermionOperator with zero expectation value.

openfermion.measurements.
two_body_fermion_constraints
(n_orbitals, n_fermions)¶ Generates twobody positivity constraints on fermionic RDMs.
The specific constraints implemented are known positivity constraints on the twofermion reduced density matrices. Constraints are generated in the form of FermionOperators whose expectation value is known to be zero for any NRepresentable state. Generators are used for efficiency.Parameters:  n_orbitals (int) – number of spinorbitals on which operators act.
 n_fermions (int) – number of fermions in the system.
Yields: Constraint is a FermionOperator with zero expectation value.

openfermion.measurements.
unlinearize_term
(index, n_orbitals)¶ Function to return integer index of term indices.
Parameters:  index (int) – The index of the term.
 n_orbitals (int) – The number of orbitals in the simulation.
Returns: term(tuple) – The term indices of a one or twobody FermionOperator.
openfermion.ops¶

class
openfermion.ops.
BinaryCode
(encoding, decoding)¶ Bases:
object
The BinaryCode class provides a representation of an encodingdecoding pair for binary vectors of different lengths, where the decoding is allowed to be nonlinear.
As the occupation number of fermionic mode is effectively binary, a lengthN vector (v) of binary number can be utilized to describe a configuration of a manybody fermionic state on N modes. An nqubit product state configuration w0> w1> w2> … wn1>, on the other hand is described by a lengthn binary vector w=(w0, w1, …, wn1). To map a subset of NOrbital Fermion states to nqubit states we define a binary code, which consists of a (here: linear) encoding (e) and a (nonlinear) decoding (d), such that for every v from that subset, w = e(v) is a lengthn binary vector with d(w) = v. This can be used to save qubits given a Hamiltonian that dictates such a subset, otherwise n=N.
Two binary codes (e,d) and (e’,d’) can construct a third code (e”,d”) by two possible operations:
Concatenation: (e”,d”) = (e,d) * (e’,d’) which means e”: v” > e’( e(v”) ) and d”: w” > d( d’(w”) ) where n” = n’ and N” = N, with n = N’ as necessary condition.
Appendage: (e”,d”) = (e,d) + (e’,d’) which means e”: (v + v’) > e(v) + e’(v’) and d”: (w + w’) > d(w) + d’( w’) where the addition is to be understood as appending two vectors together, so N” = N’ + N and n” = n + n’.
Appending codes is particularly useful when considering segment codes or segmented transforms.
A BinaryCodeinstance is initialized by BinaryCode(A,d), given the encoding (e) as n x N array or matrixlike nested lists A, such that e(v) = (A v) mod 2. The decoding d is an array or a list input of length N, which has entries either of type SymbolicBinary, or of valid type for an input of the SymbolicBinaryconstructor.
The signs + and *, += and *= are overloaded to implement concatenation and appendage on BinaryCodeobjects.
 NOTE: multiplication of a BinaryCode with an integer yields a
 multiple appending of the same code, the multiplication with another BinaryCode their concatenation.

decoder
¶ list – list of SymbolicBinary: Outputs the decoding functions as components.

encoder
¶ scipy.sparse.csc_matrix – Outputs A, the linear matrix that implements the encoding function.

n_modes
¶ int – Outputs the number of modes.

n_qubits
¶ int – Outputs the number of qubits.

__init__
(encoding, decoding)¶ Initialization of a binary code.
Parameters:  encoding (np.ndarray or list) – nested lists or binary 2Darray
 decoding (array or list) – list of SymbolicBinary(listlike or str)
Raises: TypeError
– nonlist, array like encoding or decoding, unsuitable SymbolicBinary generators,BinaryCodeError
– in case of decoder/encoder size mismatch or decoder size, qubits indexed mismatch

class
openfermion.ops.
FermionOperator
(term=None, coefficient=1.0)¶ Bases:
openfermion.ops._symbolic_operator.SymbolicOperator
FermionOperator stores a sum of products of fermionic ladder operators.
In OpenFermion, we describe fermionic ladder operators using the shorthand: ‘q^’ = a^dagger_q ‘q’ = a_q where {‘p^’, ‘q’} = delta_pq
One can multiply together these fermionic ladder operators to obtain a fermionic term. For instance, ‘2^ 1’ is a fermion term which creates at orbital 2 and destroys at orbital 1. The FermionOperator class also stores a coefficient for the term, e.g. ‘3.17 * 2^ 1’.
The FermionOperator class is designed (in general) to store sums of these terms. For instance, an instance of FermionOperator might represent 3.17 2^ 1  66.2 * 8^ 7 6^ 2 The Fermion Operator class overloads operations for manipulation of these objects by the user.
FermionOperator is a subclass of SymbolicOperator. Importantly, it has attributes set as follows:
actions = (1, 0) action_strings = ('^', '') action_before_index = False different_indices_commute = False
See the documentation of SymbolicOperator for more details.
Example
ham = (FermionOperator('0^ 3', .5) + .5 * FermionOperator('3^ 0')) # Equivalently ham2 = FermionOperator('0^ 3', 0.5) ham2 += FermionOperator('3^ 0', 0.5)
Note
Adding FermionOperators is faster using += (as this is done by inplace addition). Specifying the coefficient during initialization is faster than multiplying a FermionOperator with a scalar.

is_molecular_term
()¶ Query whether term has correct form to be from a molecular.
Require that term is particlenumber conserving (same number of raising and lowering operators). Require that term has 0, 2 or 4 ladder operators. Require that term conserves spin (parity of raising operators equals parity of lowering operators).

is_normal_ordered
()¶ Return whether or not term is in normal order.
In our convention, normal ordering implies terms are ordered from highest tensor factor (on left) to lowest (on right). Also, ladder operators come first.


class
openfermion.ops.
InteractionOperator
(constant, one_body_tensor, two_body_tensor)¶ Bases:
openfermion.ops._polynomial_tensor.PolynomialTensor
Class for storing ‘interaction operators’ which are defined to be fermionic operators consisting of onebody and twobody terms which conserve particle number and spin. The most common examples of data that will use this structure are molecular Hamiltonians. In principle, everything stored in this class could also be represented using the more general FermionOperator class. However, this class is able to exploit specific properties of how fermions interact to enable more numerically efficient manipulation of the data. Note that the operators stored in this class take the form: constant + sum_{p, q} h_[p, q] a^dagger_p a_q +
sum_{p, q, r, s} h_[p, q, r, s] a^dagger_p a^dagger_q a_r a_s.
one_body_tensor
¶ The coefficients of the onebody terms (h[p, q]). This is an n_qubits x n_qubits numpy array of floats.

two_body_tensor
¶ The coefficients of the twobody terms (h[p, q, r, s]). This is an n_qubits x n_qubits x n_qubits x n_qubits numpy array of floats.

__init__
(constant, one_body_tensor, two_body_tensor)¶ Initialize the InteractionOperator class.
Parameters:  constant – A constant term in the operator given as a float. For instance, the nuclear repulsion energy.
 one_body_tensor – The coefficients of the onebody terms (h[p,q]). This is an n_qubits x n_qubits numpy array of floats.
 two_body_tensor – The coefficients of the twobody terms (h[p, q, r, s]). This is an n_qubits x n_qubits x n_qubits x n_qubits numpy array of floats.

unique_iter
(complex_valued=False)¶ Iterate all terms that are not in the same symmetry group.
 Four point symmetry:
 pq = qp.
 pqrs = srqp = qpsr = rspq.
 Eight point symmetry:
 pq = qp.
 pqrs = rqps = psrq = srqp = qpsr = rspq = spqr = qrsp.
Parameters: complex_valued (bool) – Whether the operator has complex coefficients. Yields: tuple[int]


class
openfermion.ops.
InteractionRDM
(one_body_tensor, two_body_tensor)¶ Bases:
openfermion.ops._polynomial_tensor.PolynomialTensor
Class for storing 1 and 2body reduced density matrices.

one_body_tensor
¶ The expectation values <a^dagger_p a_q>.

two_body_tensor
¶ The expectation values <a^dagger_p a^dagger_q a_r a_s>.

__init__
(one_body_tensor, two_body_tensor)¶ Initialize the InteractionRDM class.
Parameters:  one_body_tensor – Expectation values <a^dagger_p a_q>.
 two_body_tensor – Expectation values <a^dagger_p a^dagger_q a_r a_s>.

expectation
(operator)¶ Return expectation value of an InteractionRDM with an operator.
Parameters: operator – A QubitOperator or InteractionOperator. Returns: float – Expectation value Raises: InteractionRDMError
– Invalid operator provided.

get_qubit_expectations
(qubit_operator)¶ Return expectations of QubitOperator in new QubitOperator.
Parameters: qubit_operator – QubitOperator instance to be evaluated on this InteractionRDM. Returns: QubitOperator – QubitOperator with coefficients corresponding to expectation values of those operators. Raises: InteractionRDMError
– Observable not contained in 1RDM or 2RDM.


class
openfermion.ops.
PolynomialTensor
(n_body_tensors)¶ Bases:
object
Class for storing tensor representations of operators that correspond with multilinear polynomials in the fermionic ladder operators. For instance, in a quadratic Hamiltonian (degree 2 polynomial) which conserves particle number, there are only terms of the form a^dagger_p a_q, and the coefficients can be stored in an n_qubits x n_qubits matrix. Higher order terms would be described with tensors of higher dimension. Note that each tensor must have an even number of dimensions, since parity is conserved. Much of the functionality of this class is redudant with FermionOperator but enables much more efficient numerical computations in many cases, such as basis rotations.

n_qubits
¶ int – The number of sites on which the tensor acts.

n_body_tensors
¶ dict – A dictionary storing the tensors describing nbody interactions. The keys are tuples that indicate the type of tensor. For instance, n_body_tensors[(1, 0)] would be an (n_qubits x n_qubits x n_qubits x n_qubits) numpy array, and it could represent the coefficients of terms of the form a^dagger_i a_j, whereas n_body_tensors[(0, 1)] would be an array of the same shape, but instead representing terms of the form a_i a^dagger_j.

__init__
(n_body_tensors)¶ Initialize the PolynomialTensor class.
Parameters: n_body_tensors (dict) – A dictionary storing the tensors describing nbody interactions.

constant
¶ Get the value of the constant term.

rotate_basis
(rotation_matrix)¶ Rotate the orbital basis of the PolynomialTensor.
Parameters: rotation_matrix – A square numpy array or matrix having dimensions of n_qubits by n_qubits. Assumed to be real and invertible.


class
openfermion.ops.
QuadraticHamiltonian
(constant, hermitian_part, antisymmetric_part=None, chemical_potential=0.0)¶ Bases:
openfermion.ops._polynomial_tensor.PolynomialTensor
Class for storing Hamiltonians that are quadratic in the fermionic ladder operators. The operators stored in this class take the form
\[\sum_{p, q} (M_{pq}  \mu \delta_{pq}) a^\dagger_p a_q + \frac12 \sum_{p, q} (\Delta_{pq} a^\dagger_p a^\dagger_q + \text{h.c.}) + \text{constant}\]where
 \(M\) is a Hermitian n_qubits x n_qubits matrix.
 \(\Delta\) is an antisymmetric n_qubits x n_qubits matrix.
 \(\mu\) is a real number representing the chemical potential.
 \(\delta_{pq}\) is the Kronecker delta symbol.
We separate the chemical potential \(\mu\) from \(M\) so that we can use it to adjust the expectation value of the total number of particles.

chemical_potential
¶ float – The chemical potential \(\mu\).

__init__
(constant, hermitian_part, antisymmetric_part=None, chemical_potential=0.0)¶ Initialize the QuadraticHamiltonian class.
Parameters:  constant (float) – A constant term in the operator.
 hermitian_part (ndarray) – The matrix \(M\), which represents the coefficients of the particlenumberconserving terms. This is an n_qubits x n_qubits numpy array of complex numbers.
 antisymmetric_part (ndarray) – The matrix \(\Delta\), which represents the coefficients of the nonparticlenumberconserving terms. This is an n_qubits x n_qubits numpy array of complex numbers.
 chemical_potential (float) – The chemical potential \(\mu\).

add_chemical_potential
(chemical_potential)¶ Increase (or decrease) the chemical potential by some value.

antisymmetric_part
¶ The antisymmetric part.

combined_hermitian_part
¶ The Hermitian part including the chemical potential.

conserves_particle_number
¶ Whether this Hamiltonian conserves particle number.

diagonalizing_bogoliubov_transform
()¶ Compute the unitary that diagonalizes a quadratic Hamiltonian.
Any quadratic Hamiltonian can be rewritten in the form
\[\sum_{j} \varepsilon_j b^\dagger_j b_j + \text{constant},\]where the \(b_j\) are a new set fermionic operators that satisfy the canonical anticommutation relations. The new fermionic operators are linear combinations of the original ones:
\[\begin{split}\begin{pmatrix} b^\dagger_1 \\ \vdots \\ b^\dagger_N \\ b_1 \\ \vdots \\ b_N \end{pmatrix} = W \begin{pmatrix} a^\dagger_1 \\ \vdots \\ a^\dagger_N \\ a_1 \\ \vdots \\ a_N \end{pmatrix},\end{split}\]where \(W\) is a \(2N \times 2N\) unitary matrix. This method returns the matrix \(W\).
Returns: diagonalizing_unitary (ndarray) – A (2 * n_qubits) x (2 * n_qubits) matrix representing the transformation \(W\) of the fermionic ladder operators.

ground_energy
()¶ Return the ground energy.

hermitian_part
¶ The Hermitian part not including the chemical potential.

majorana_form
()¶ Return the Majorana represention of the Hamiltonian.
Any quadratic Hamiltonian can be written in the form
\[\frac{i}{2} \sum_{j, k} A_{jk} f_j f_k + \text{constant}\]where the \(f_i\) are normalized Majorana fermion operators:
\[ \begin{align}\begin{aligned}f_j = \frac{1}{\sqrt{2}} (a^\dagger_j + a_j)\\f_{j + N} = \frac{i}{\sqrt{2}} (a^\dagger_j  a_j)\end{aligned}\end{align} \]and \(A\) is a (2 * n_qubits) x (2 * n_qubits) real antisymmetric matrix. This function returns the matrix \(A\) and the constant.

orbital_energies
(non_negative=False)¶ Return the orbital energies.
Any quadratic Hamiltonian is unitarily equivalent to a Hamiltonian of the form
\[\sum_{j} \varepsilon_j b^\dagger_j b_j + \text{constant}.\]We call the \(\varepsilon_j\) the orbital energies. The eigenvalues of the Hamiltonian are sums of subsets of the orbital energies (up to the additive constant).
Parameters: non_negative (bool) – If True, always return a list of orbital energies that are nonnegative. This option is ignored if the Hamiltonian does not conserve particle number, in which case the returned orbital energies are always nonnegative. Returns:  orbital_energies(ndarray) – A onedimensional array containing the \(\varepsilon_j\)
 constant(float) – The constant

class
openfermion.ops.
QubitOperator
(term=None, coefficient=1.0)¶ Bases:
openfermion.ops._symbolic_operator.SymbolicOperator
A sum of terms acting on qubits, e.g., 0.5 * ‘X0 X5’ + 0.3 * ‘Z1 Z2’.
A term is an operator acting on n qubits and can be represented as:
coefficient * local_operator[0] x … x local_operator[n1]
where x is the tensor product. A local operator is a Pauli operator (‘I’, ‘X’, ‘Y’, or ‘Z’) which acts on one qubit. In math notation a term is, for example, 0.5 * ‘X0 X5’, which means that a Pauli X operator acts on qubit 0 and 5, while the identity operator acts on all other qubits.
A QubitOperator represents a sum of terms acting on qubits and overloads operations for easy manipulation of these objects by the user.
Note for a QubitOperator to be a Hamiltonian which is a hermitian operator, the coefficients of all terms must be real.
hamiltonian = 0.5 * QubitOperator('X0 X5') + 0.3 * QubitOperator('Z0')
QubitOperator is a subclass of SymbolicOperator. Importantly, it has attributes set as follows:
actions = ('X', 'Y', 'Z') action_strings = ('X', 'Y', 'Z') action_before_index = True different_indices_commute = True
See the documentation of SymbolicOperator for more details.
Example
ham = ((QubitOperator('X0 Y3', 0.5) + 0.6 * QubitOperator('X0 Y3'))) # Equivalently ham2 = QubitOperator('X0 Y3', 0.5) ham2 += 0.6 * QubitOperator('X0 Y3')
Note
Adding QubitOperators is faster using += (as this is done by inplace addition). Specifying the coefficient during initialization is faster than multiplying a QubitOperator with a scalar.

renormalize
()¶ Fix the trace norm of an operator to 1


class
openfermion.ops.
SymbolicBinary
(term=None)¶ Bases:
object
The SymbolicBinary class provides an analytic representation of nonlinear binary functions. An instance of this class describes a term of binary variables (variables of the values {0,1}, indexed by integers like w0, w1, w2 and so on) that is considered to be evaluated modulo 2. This implies the following set of rules:
the binary addition w1 + w1 = 0, binary multiplication w2 * w2 = w2 and power rule w3 ^ 0 = 1, where raising to every other integer power than zero reproduces w3.
Of course, we can also add a nontrivial constant, which is 1. Due to these binary rules, every function available will be a multinomial like e.g.
1 + w1 w2 + w0 w1 .
These binary functions are used for nonlinear binary codes in order to decompress qubit bases back into fermion bases. In that instance, one SymbolicBinary object characterizes the occupation of single orbital given a multiqubit state in configuration w0> w1> w2> … .
For initialization, the preferred data types is either a string of the multinomial, where each variable and constant is to be well separated by a whitespace, or in its native form of tuples, 1 + w1 w2 + w0 w1 is represented as [(_SYMBOLIC_ONE,),(1,2),(0,1)]
 After initialization,SymbolicBinary terms can be manipulated with the
 overloaded signs +, * and ^, according to the binary rules mentioned.
Example
bin_fun = SymbolicBinary('1 + w1 w2 + w0 w1') # Equivalently bin_fun = SymbolicBinary(1) + SymbolicBinary([(1,2),(0,1)]) # Equivalently bin_fun = SymbolicBinary([(_SYMBOLIC_ONE,),(1,2),(0,1)])

terms
¶ list – a list of tuples. Each tuple represents a summand of the SymbolicBinary term and each summand can contain multiple tuples representing the factors.

__init__
(term=None)¶ Initialize the SymbolicBinary based on term
Parameters: term (str, list, tuple) – used for initializing a SymbolicBinary Raises: ValueError
– when term is not a string,list or tuple

enumerate_qubits
()¶ Enumerates all qubits indexed in a given SymbolicBinary.
Returns (list): a list of qubits

evaluate
(binary_list)¶ Evaluates a SymbolicBinary
Parameters: binary_list (list, array, str) – a list of binary values corresponding each binary variable (in order of their indices) in the expression Returns (int, 0 or 1): result of the evaluation
Raises: SymbolicBinaryError
– Length of list provided must match the number of qubits indexed in SymbolicBinary

classmethod
identity
()¶ Returns: multiplicative_identity (SymbolicBinary) – A symbolic operator u with the property that u*x = x*u = x for all operators x of the same class.

shift
(const)¶ Shift all qubit indices by a given constant.
Parameters: const (int) – the constant to shift the indices by Raises: TypeError
– const must be integer

classmethod
zero
()¶ Returns: additive_identity (SymbolicBinary) – A symbolic operator o with the property that o+x = x+o = x for all operators x of the same class.

class
openfermion.ops.
SymbolicOperator
(term=None, coefficient=1.0)¶ Bases:
object
Base class for FermionOperator and QubitOperator.
A SymbolicOperator stores an object which represents a weighted sum of terms; each term is a product of individual factors of the form (index, action), where index is a nonnegative integer and the possible values for action are determined by the subclass. For instance, for the subclass FermionOperator, action can be 1 or 0, indicating raising or lowering, and for QubitOperator, action is from the set {‘X’, ‘Y’, ‘Z’}. The coefficients of the terms are stored in a dictionary whose keys are the terms. SymbolicOperators of the same type can be added or multiplied together.
Note
Adding SymbolicOperators is faster using += (as this is done by inplace addition). Specifying the coefficient during initialization is faster than multiplying a SymbolicOperator with a scalar.

actions
¶ tuple – A tuple of objects representing the possible actions. This should be defined in the subclass. e.g. for FermionOperator, this is (1, 0).

action_strings
¶ tuple – A tuple of string representations of actions. These should be in onetoone correspondence with actions and listed in the same order. e.g. for FermionOperator, this is (‘^’, ‘’).

action_before_index
¶ bool – A boolean indicating whether in string representations, the action should come before the index.

different_indices_commute
¶ bool – A boolean indicating whether factors acting on different indices commute.

terms
¶ dict – key (tuple of tuples): A dictionary storing the coefficients of the terms in the operator. The keys are the terms. A term is a product of individual factors; each factor is represented by a tuple of the form (index, action), and these tuples are collected into a larger tuple which represents the term as the product of its factors.

compress
(abs_tol=1e12)¶ Eliminates all terms with coefficients close to zero and removes small imaginary and real parts.
Parameters: abs_tol (float) – Absolute tolerance, must be at least 0.0

classmethod
identity
()¶ Returns: multiplicative_identity (SymbolicOperator) – A symbolic operator u with the property that u*x = x*u = x for all operators x of the same class.

induced_norm
(order=1)¶ Compute the induced pnorm of the operator.
If we represent an operator as :math: sum_{j} w_j H_j where :math: w_j are scalar coefficients then this norm is :math: left(sum_{j}  w_j ^p right)^{frac{1}{p}} where :math: `p is the order of the induced norm
Parameters: order (int) – the order of the induced norm.

isclose
(other, rel_tol=1e12, abs_tol=1e12)¶ Returns True if other (SymbolicOperator) is close to self.
Comparison is done for each term individually. Return True if the difference between each term in self and other is less than the relative tolerance w.r.t. either other or self (symmetric test) or if the difference is less than the absolute tolerance.
Parameters:  other (SymbolicOperator) – SymbolicOperator to compare against.
 rel_tol (float) – Relative tolerance, must be greater than 0.0
 abs_tol (float) – Absolute tolerance, must be at least 0.0

classmethod
zero
()¶ Returns: additive_identity (SymbolicOperator) – A symbolic operator o with the property that o+x = x+o = x for all operators x of the same class.


openfermion.ops.
general_basis_change
(general_tensor, rotation_matrix, key)¶ Change the basis of an general interaction tensor.
 M’^{p_1p_2…p_n} = R^{p_1}_{a_1} R^{p_2}_{a_2} …
 R^{p_n}_{a_n} M^{a_1a_2…a_n} R^{p_n}_{a_n}^T … R^{p_2}_{a_2}^T R_{p_1}_{a_1}^T
where R is the rotation matrix, M is the general tensor, M’ is the transformed general tensor, and a_k and p_k are indices. The formula uses the Einstein notation (implicit sum over repeated indices).
In case R is complex, the kth R in the above formula need to be conjugated if key has a 1 in the kth place (meaning that the corresponding operator is a creation operator).
Parameters:  general_tensor – A square numpy array or matrix containing information about a general interaction tensor.
 rotation_matrix – A square numpy array or matrix having dimensions of n_qubits by n_qubits. Assumed to be unitary.
 key – A tuple indicating the type of general_tensor. Assumed to be nonempty. For example, a tensor storing coefficients of \(a^\dagger_p a_q\) would have a key of (1, 0) whereas a tensor storing coefficients of \(a^\dagger_p a_q a_r a^\dagger_s\) would have a key of (1, 0, 0, 1).
Returns: transformed_general_tensor – general_tensor in the rotated basis.

openfermion.ops.
hermitian_conjugated
(fermion_operator)¶ Return Hermitian conjugate of fermionic operator.

openfermion.ops.
linearize_decoder
(matrix)¶ Outputs linear decoding function from input matrix
Parameters: matrix (np.ndarray or list) – list of lists or 2D numpy array to derive the decoding function from Returns (list): list of SymbolicBinary

openfermion.ops.
normal_ordered
(fermion_operator)¶ Compute and return the normal ordered form of a FermionOperator.
In our convention, normal ordering implies terms are ordered from highest tensor factor (on left) to lowest (on right). Also, ladder operators come first.
Warning
Even assuming that each creation or annihilation operator appears at most a constant number of times in the original term, the runtime of this method is exponential in the number of qubits.
openfermion.transforms¶

openfermion.transforms.
binary_code_transform
(hamiltonian, code)¶ Transforms a Hamiltonian written in fermionic basis into a Hamiltonian written in qubit basis, via a binary code.
The role of the binary code is to relate the occupation vectors (v0 v1 v2 … vN1) that span the fermionic basis, to the qubit basis, spanned by binary vectors (w0, w1, w2, …, wn1).
The binary code has to provide an analytic relation between the binary vectors (v0, v1, …, vN1) and (w0, w1, …, wn1), and possibly has the property N>n, when the Fermion basis is smaller than the fermionic Fock space. The binary_code_transform function can transform Fermion operators to qubit operators for custom and qubitsaving mappings.
Note
Logic multiqubit operators are decomposed into Paulistrings (e.g. CPhase(1,2) = 0.5 * (1 + Z1 + Z2  Z1 Z2 ) ), which might increase the number of Hamiltonian terms drastically.
Parameters:  hamiltonian (FermionOperator) – the fermionic Hamiltonian
 code (BinaryCode) – the binary code to transform the Hamiltonian
Returns (QubitOperator): the transformed Hamiltonian
Raises: TypeError
– if the hamiltonian is not a FermionOperator or code is not a BinaryCode

openfermion.transforms.
bravyi_kitaev
(operator, n_qubits=None)¶ Apply the BravyiKitaev transform and return qubit operator.
Parameters:  operator (openfermion.ops.FermionOperator) – A FermionOperator to transform.
 n_qubits (intNone) – Can force the number of qubits in the resulting operator above the number that appear in the input operator.
Returns: transformed_operator – An instance of the QubitOperator class.
Raises: ValueError
– Invalid number of qubits specified.

openfermion.transforms.
bravyi_kitaev_fast
(operator)¶ Find the Paulirepresentation of InteractionOperator for BravyiKitaev Super fast (BKSF) algorithm. Paulirepresentation of general FermionOperator is not possible in BKSF. Also, the InteractionOperator given as input must be Hermitian. In future we might provide a transformation for a restricted set of fermion operator.
Parameters: operator – Interaction Operator. Returns: transformed_operator – An instance of the QubitOperator class. Raises: TypeError
– If operator is not an InteractionOperator

openfermion.transforms.
dissolve
(term)¶ Decomposition helper. Takes a product of binary variables and outputs the Paulistring sum that corresponds to the decomposed multiqubit operator.
Parameters: term (tuple) – product of binary variables, i.e.: ‘w0 w2 w3’ Returns (QubitOperator): superposition of Paulistrings
Raises: ValueError
– if the variable in term is not integer

openfermion.transforms.
get_fermion_operator
(polynomial_tensor)¶ Output PolynomialTensor as instance of FermionOperator class.
Returns: fermion_operator – An instance of the FermionOperator class.

openfermion.transforms.
get_interaction_operator
(fermion_operator, n_qubits=None)¶ Convert a 2body fermionic operator to InteractionOperator.
This function should only be called on fermionic operators which consist of only a_p^dagger a_q and a_p^dagger a_q^dagger a_r a_s terms. The onebody terms are stored in a matrix, one_body[p, q], and the twobody terms are stored in a tensor, two_body[p, q, r, s].
Returns: interaction_operator – An instance of the InteractionOperator class.
Raises: TypeError
– Input must be a FermionOperator.TypeError
– FermionOperator does not map to InteractionOperator.
Warning
Even assuming that each creation or annihilation operator appears at most a constant number of times in the original operator, the runtime of this method is exponential in the number of qubits.

openfermion.transforms.
get_interaction_rdm
(qubit_operator, n_qubits=None)¶ Build an InteractionRDM from measured qubit operators.
Returns: An InteractionRDM object.

openfermion.transforms.
get_molecular_data
(interaction_operator, geometry=None, basis=None, multiplicity=None, n_electrons=None, reduce_spin=True, data_directory=None)¶ Output a MolecularData object generated from an InteractionOperator
Parameters:  interaction_operator (InteractionOperator) – twobody interaction operator defining the “molecular interaction” to be simulated.
 geometry (string or list of atoms) –
 basis (string) – String denoting the basis set used to discretize the system.
 multiplicity (int) – Spin multiplicity desired in the system.
 n_electrons (int) – Number of electrons in the system
 reduce_spin (bool) – True if one wishes to perform spin reduction on integrals that are given in interaction operator. Assumes spatial (x) spin structure generically.
Returns: molecule(MolecularData) – Instance that captures the interaction_operator converted into the format that would come from an electronic structure package adorned with some metadata that may be useful.

openfermion.transforms.
get_quadratic_hamiltonian
(fermion_operator, chemical_potential=0.0, n_qubits=None)¶ Convert a quadratic fermionic operator to QuadraticHamiltonian.
This function should only be called on fermionic operators which consist of only a_p^dagger a_q, a_p^dagger a_q^dagger, and a_p a_q terms.
Returns: quadratic_hamiltonian – An instance of the QuadraticHamiltonian class.
Raises: TypeError
– Input must be a FermionOperator.TypeError
– FermionOperator does not map to QuadraticHamiltonian.
Warning
Even assuming that each creation or annihilation operator appears at most a constant number of times in the original operator, the runtime of this method is exponential in the number of qubits.

openfermion.transforms.
get_sparse_operator
(operator, n_qubits=None)¶ Map a FermionOperator, QubitOperator, or PolyomialTensor to a sparse matrix.

openfermion.transforms.
jordan_wigner
(operator)¶ Apply the JordanWigner transform to a FermionOperator or InteractionOperator to convert to a QubitOperator.
Operators are mapped as follows: a_j^dagger > Z_0 .. Z_{j1} (X_j  iY_j) / 2 a_j > Z_0 .. Z_{j1} (X_j + iY_j) / 2
Returns: transformed_operator – An instance of the QubitOperator class. Warning
The runtime of this method is exponential in the maximum locality of the original FermionOperator.

openfermion.transforms.
reverse_jordan_wigner
(qubit_operator, n_qubits=None)¶ Transforms a QubitOperator into a FermionOperator using the JordanWigner transform.
Operators are mapped as follows: Z_j > I  2 a^dagger_j a_j X_j > (a^dagger_j + a_j) Z_{j1} Z_{j2} .. Z_0 Y_j > i (a^dagger_j  a_j) Z_{j1} Z_{j2} .. Z_0
Parameters:  qubit_operator – the QubitOperator to be transformed.
 n_qubits – the number of qubits term acts on. If not set, defaults to the maximum qubit number acted on by term.
Returns: transformed_term – An instance of the FermionOperator class.
Raises: TypeError
– Input must be a QubitOperator.TypeError
– Invalid number of qubits specified.TypeError
– Pauli operators must be X, Y or Z.

openfermion.transforms.
verstraete_cirac_2d_square
(operator, x_dimension, y_dimension, add_auxiliary_hamiltonian=True, snake=False)¶ Apply the VerstraeteCirac transform on a 2d square lattice.
Note that this transformation adds one auxiliary fermionic mode for each mode already present, and hence it doubles the number of qubits needed to represent the system.
Currently only supports even values of x_dimension and only works for spinless models.
Parameters:  operator (FermionOperator) – The operator to transform.
 x_dimension (int) – The number of columns of the grid.
 y_dimension (int) – The number of rows of the grid.
 snake (bool, optional) – Indicates whether the fermions are already ordered according to the 2d “snake” ordering. If False, we assume they are in “lexicographic” order by row and column index. Default is False.
Returns: transformed_operator – A QubitOperator.
openfermion.utils¶

class
openfermion.utils.
Grid
(dimensions, length, scale)¶ A multidimensional grid of points.

__init__
(dimensions, length, scale)¶ Parameters:  dimensions (int) – The number of dimensions the grid lives in.
 length (int) – The number of points along each grid axis.
 scale (float) – The total length of each grid dimension.

all_points_indices
()¶ Returns: iterable[tuple[int]] – The indexcoordinate tuple of each point in the grid.

num_points
()¶ Returns: int – The number of points in the grid.

volume_scale
()¶ Returns: float – The volume of a lengthscale hypercube within the grid.


openfermion.utils.
amplitude_damping_channel
(density_matrix, probability, target_qubit, transpose=False)¶ Apply an amplitude damping channel
Applies an amplitude damping channel with a given probability to the target qubit in the density_matrix.
Parameters:  density_matrix (numpy.ndarray) – Density matrix of the system
 probability (float) – Probability error is applied p in [0, 1]
 target_qubit (int) – target for the channel error.
 transpose (bool) – Conjugate transpose channel operators, useful for acting on Hamiltonians in variational channel state models
Returns: new_density_matrix(numpy.ndarray) –
 Density matrix with the channel
applied.

openfermion.utils.
anticommutator
(operator_a, operator_b)¶ Compute the anticommutator of two operators.
Parameters: operator_b (operator_a,) – Operators in anticommutator. Any operators are accepted so long as implicit addition and multiplication are supported; e.g. QubitOperators, FermionOperators or Scipy sparse matrices. 2D Numpy arrays are also supported. Raises: TypeError
– operator_a and operator_b are not of the same type.

openfermion.utils.
bch_expand
(x, y, order=6)¶ Compute log[e^x e^y] using the BakerCampbellHausdorff formula.
This implementation is explained in arXiv:1712.01348.
Parameters:  x – An operator for which multiplication and addition are supported. For instance, a QubitOperator, FermionOperator or scipy sparse matrix.
 y – The same type as x.
 order (int) – The max degree of monomial with respect to X and Y to truncate the BCH expansions.
Returns: z – The truncated BCH operator.
Raises: ValueError
– operator x is not same type as operator y.ValueError
– invalid order parameter.ValueError
– order exceeds maximum order supported.

openfermion.utils.
commutator
(operator_a, operator_b)¶ Compute the commutator of two operators.
Parameters: operator_b (operator_a,) – Operators in commutator. Any operators are accepted so long as implicit subtraction and multiplication are supported; e.g. QubitOperators, FermionOperators or Scipy sparse matrices. 2D Numpy arrays are also supported. Raises: TypeError
– operator_a and operator_b are not of the same type.

openfermion.utils.
count_qubits
(operator)¶ Compute the minimum number of qubits on which operator acts.
Parameters: operator – FermionOperator, QubitOperator, or PolynomialTensor. Returns: num_qubits (int) – The minimum number of qubits on which operator acts. Raises: TypeError
– Operator of invalid type.

openfermion.utils.
dephasing_channel
(density_matrix, probability, target_qubit, transpose=False)¶ Apply a dephasing channel
Applies an amplitude damping channel with a given probability to the target qubit in the density_matrix.
Parameters:  density_matrix (numpy.ndarray) – Density matrix of the system
 probability (float) – Probability error is applied p in [0, 1]
 target_qubit (int) – target for the channel error.
 transpose (bool) – Conjugate transpose channel operators, useful for acting on Hamiltonians in variational channel state models
Returns: new_density_matrix (numpy.ndarray) –
 Density matrix with the channel
applied.

openfermion.utils.
depolarizing_channel
(density_matrix, probability, target_qubit, transpose=False)¶ Apply a depolarizing channel
Applies an amplitude damping channel with a given probability to the target qubit in the density_matrix.
Parameters:  density_matrix (numpy.ndarray) – Density matrix of the system
 probability (float) – Probability error is applied p in [0, 1]
 target_qubit (int/str) – target for the channel error, if given special value “all”, then a total depolarizing channel is applied.
 transpose (bool) – Dummy parameter to match signature of other channels but depolarizing channel is symmetric under conjugate transpose.
Returns: new_density_matrix (numpy.ndarray) –
 Density matrix with the channel
applied.

openfermion.utils.
double_commutator
(op1, op2, op3, indices2=None, indices3=None, is_hopping_operator2=None, is_hopping_operator3=None)¶ Return the double commutator [op1, [op2, op3]].
Parameters:  op2, op3 (op1,) – operators for the commutator.
 indices3 (indices2,) – The indices op2 and op3 act on.
 is_hopping_operator2 (bool) – Whether op2 is a hopping operator.
 is_hopping_operator3 (bool) – Whether op3 is a hopping operator.
Returns: The double commutator of the given operators.

openfermion.utils.
eigenspectrum
(operator, n_qubits=None)¶ Compute the eigenspectrum of an operator.
 WARNING: This function has cubic runtime in dimension of
 Hilbert space operator, which might be exponential.
Parameters: operator – QubitOperator, InteractionOperator, FermionOperator, PolynomialTensor, or InteractionRDM. Returns: eigenspectrum – dense numpy array of floats giving eigenspectrum.

openfermion.utils.
error_bound
(terms, tight=False)¶ Numerically upper bound the error in the ground state energy for the second order TrotterSuzuki expansion.
Parameters:  terms – a list of singleterm QubitOperators in the Hamiltonian to be simulated.
 tight – whether to use the triangle inequality to give a loose upper bound on the error (default) or to calculate the norm of the error operator.
Returns: A float upper bound on norm of error in the ground state energy.
 Notes: follows Poulin et al.’s work in “The Trotter Step Size
Required for Accurate Quantum Simulation of Quantum Chemistry”. In particular, Equation 16 is used for a loose upper bound, and the norm of Equation 9 is calculated for a tighter bound using the error operator from error_operator.
Possible extensions of this function would be to get the expectation value of the error operator with the HartreeFock state or CISD state, which can scalably bound the error in the ground state but much more accurately than the triangle inequality.

openfermion.utils.
error_operator
(terms, series_order=2)¶ Determine the difference between the exact generator of unitary evolution and the approximate generator given by TrotterSuzuki to the given order.
Parameters:  terms – a list of QubitTerms in the Hamiltonian to be simulated.
 series_order – the order at which to compute the BCH expansion. Only the second order formula is currently implemented (corresponding to Equation 9 of the paper).
Returns:  The difference between the true and effective generators of time
evolution for a single Trotter step.
 Notes: follows Equation 9 of Poulin et al.’s work in “The Trotter Step
 Size Required for Accurate Quantum Simulation of Quantum Chemistry”.

openfermion.utils.
expectation
(sparse_operator, state)¶ Compute expectation value of operator with a state.
Parameters: state – scipy.sparse.csc vector representing a pure state, or, a scipy.sparse.csc matrix representing a density matrix. Returns: A real float giving expectation value. Raises: ValueError
– Input state has invalid format.

openfermion.utils.
expectation_computational_basis_state
(operator, computational_basis_state)¶ Compute expectation value of operator with a state.
Parameters:  operator – Qubit or FermionOperator to evaluate expectation value of. If operator is a FermionOperator, it must be normalordered.
 computational_basis_state (scipy.sparse vector / list) – normalized computational basis state (if scipy.sparse vector), or list of occupied orbitals.
Returns: A real float giving expectation value.
Raises: TypeError
– Incorrect operator or state type.

openfermion.utils.
fourier_transform
(hamiltonian, grid, spinless)¶ Apply Fourier transform to change hamiltonian in plane wave basis.
\[c^\dagger_v = \sqrt{1/N} \sum_m {a^\dagger_m \exp(i k_v r_m)} c_v = \sqrt{1/N} \sum_m {a_m \exp(i k_v r_m)}\]Parameters:  hamiltonian (FermionOperator) – The hamiltonian in plane wave basis.
 grid (Grid) – The discretization to use.
 spinless (bool) – Whether to use the spinless model or not.
Returns: FermionOperator – The fouriertransformed hamiltonian.

openfermion.utils.
gaussian_state_preparation_circuit
(quadratic_hamiltonian, occupied_orbitals=None)¶ Obtain the description of a circuit which prepares a fermionic Gaussian state.
Fermionic Gaussian states can be regarded as eigenstates of quadratic Hamiltonians. If the Hamiltonian conserves particle number, then these are just Slater determinants. See arXiv:1711.05395 for a detailed description of how this procedure works.
The circuit description is returned as a sequence of elementary operations; operations that can be performed in parallel are grouped together. Each elementary operation is either
the string ‘pht’, indicating the particlehole transformation on the last fermionic mode, which is the operator \(\mathcal{B}\) such that
\[\begin{split}\begin{align} \mathcal{B} a_N \mathcal{B}^\dagger &= a_N^\dagger,\\ \mathcal{B} a_j \mathcal{B}^\dagger &= a_j, \quad j = 1, \ldots, N1, \end{align}\end{split}\]or
a tuple \((i, j, \theta, \varphi)\), indicating the operation
\[\exp[i \varphi a_j^\dagger a_j] \exp[\theta (a_i^\dagger a_j  a_j^\dagger a_i)],\]a Givens rotation of modes \(i\) and \(j\) by angles \(\theta\) and \(\varphi\).
Parameters:  quadratic_hamiltonian (QuadraticHamiltonian) – The Hamiltonian whose eigenstate is desired.
 occupied_orbitals (list) – A list of integers representing the indices of the occupied orbitals in the desired Gaussian state. If this is None (the default), then it is assumed that the ground state is desired, i.e., the orbitals with negative energies are filled.
Returns:  circuit_description (list[tuple]) – A list of operations describing the circuit. Each operation is a tuple of objects describing elementary operations that can be performed in parallel. Each elementary operation is either the string ‘pht’, indicating a particlehole transformation on the last fermionic mode, or a tuple of the form \((i, j, \theta, \varphi)\), indicating a Givens rotation of modes \(i\) and \(j\) by angles \(\theta\) and \(\varphi\).
 start_orbitals (list) – The occupied orbitals to start with. This describes the initial state that the circuit should be applied to: it should be a Slater determinant (in the computational basis) with these orbitals filled.

openfermion.utils.
get_file_path
(file_name, data_directory)¶ Compute file_path for the file that stores operator.
Parameters:  file_name – The name of the saved file.
 data_directory – Optional data directory to change from default data directory specified in config file.
Returns: file_path (string) – File path.
Raises: OperatorUtilsError
– File name is not provided.

openfermion.utils.
get_gap
(sparse_operator)¶ Compute gap between lowest eigenvalue and first excited state.
Returns: A real float giving eigenvalue gap.

openfermion.utils.
get_ground_state
(sparse_operator)¶ Compute lowest eigenvalue and eigenstate.
Returns:  eigenvalue – The lowest eigenvalue, a float.
 eigenstate – The lowest eigenstate in scipy.sparse csc format.

openfermion.utils.
hartree_fock_state_jellium
(grid, n_electrons, spinless=True, plane_wave=False)¶ Give the HartreeFock state of jellium.
Parameters:  grid (Grid) – The discretization to use.
 n_electrons (int) – Number of electrons in the system.
 spinless (bool) – Whether to use the spinless model or not.
 plane_wave (bool) – Whether to return the HartreeFock state in the plane wave (True) or dual basis (False).
Notes
The jellium model is built up by filling the lowestenergy singleparticle states in the planewave Hamiltonian until n_electrons states are filled.

openfermion.utils.
inner_product
(state_1, state_2)¶ Compute inner product of two states.

openfermion.utils.
inverse_fourier_transform
(hamiltonian, grid, spinless)¶ Apply inverse Fourier transform to change hamiltonian in plane wave dual basis.
\[a^\dagger_v = \sqrt{1/N} \sum_m {c^\dagger_m \exp(i k_v r_m)} a_v = \sqrt{1/N} \sum_m {c_m \exp(i k_v r_m)}\]Parameters:  hamiltonian (FermionOperator) – The hamiltonian in plane wave dual basis.
 grid (Grid) – The discretization to use.
 spinless (bool) – Whether to use the spinless model or not.
Returns: FermionOperator – The inversefouriertransformed hamiltonian.

openfermion.utils.
is_hermitian
(sparse_operator)¶ Test if matrix is Hermitian.

openfermion.utils.
is_identity
(operator)¶ Check whether QubitOperator of FermionOperator is identity.
Parameters: operator – QubitOperator or FermionOperator. Raises: TypeError
– Operator of invalid type.

openfermion.utils.
jordan_wigner_sparse
(fermion_operator, n_qubits=None)¶ Initialize a Scipy sparse matrix from a FermionOperator.
Operators are mapped as follows: a_j^dagger > Z_0 .. Z_{j1} (X_j  iY_j) / 2 a_j > Z_0 .. Z_{j1} (X_j + iY_j) / 2
Parameters:  fermion_operator (FermionOperator) – instance of the FermionOperator class.
 n_qubits (int) – Number of qubits.
Returns: The corresponding Scipy sparse matrix.

openfermion.utils.
jw_configuration_state
(occupied_orbitals, n_qubits)¶ Function to produce a basis state in the occupation number basis.
Parameters:  occupied_orbitals (list) – A list of integers representing the indices of the occupied orbitals in the desired basis state
 n_qubits (int) – The total number of qubits
Returns: basis_vector(sparse) – The basis state as a sparse matrix

openfermion.utils.
jw_get_gaussian_state
(quadratic_hamiltonian, occupied_orbitals=None)¶ Compute an eigenvalue and eigenstate of a quadratic Hamiltonian.
Eigenstates of a quadratic Hamiltonian are also known as fermionic Gaussian states.
Parameters:  quadratic_hamiltonian (QuadraticHamiltonian) – The Hamiltonian whose eigenstate is desired.
 occupied_orbitals (list) – A list of integers representing the indices of the occupied orbitals in the desired Gaussian state. If this is None (the default), then it is assumed that the ground state is desired, i.e., the orbitals with negative energies are filled.
Returns:  energy (float) – The eigenvalue.
 state (sparse) – The eigenstate in scipy.sparse csc format.

openfermion.utils.
jw_get_ground_states_by_particle_number
(sparse_operator, particle_number, sparse=True, num_eigs=3)¶ For a JordanWigner encoded Hermitian operator, compute the lowest eigenvalue and eigenstates at a particular particle number. The operator must conserve particle number.
Parameters:  sparse_operator (sparse) – A JordanWigner encoded sparse operator.
 particle_number (int) – The particle number at which to compute ground states.
 sparse (boolean, optional) – Whether to use sparse eigensolver. Default is True.
 num_eigs (int, optional) – The number of eigenvalues to request from the sparse eigensolver. Needs to be at least as large as the degeneracy of the ground energy in order to obtain all ground states. Only used if sparse=True. Default is 3.
Returns: ground_energy(float) –
 The lowest eigenvalue of sparse_operator within
the eigenspace of the number operator corresponding to particle_number.
ground_states(list[ndarray]): A list of the corresponding eigenstates.
Warning
The running time of this method is exponential in the number of qubits.

openfermion.utils.
jw_hartree_fock_state
(n_electrons, n_orbitals)¶ Function to produce HartreeFock state in JW representation.

openfermion.utils.
jw_number_restrict_operator
(operator, n_electrons, n_qubits=None)¶ Restrict a JordanWigner encoded operator to a given particle number
Parameters:  sparse_operator (ndarray or sparse) – Numpy operator acting on the space of n_qubits.
 n_electrons (int) – Number of particles to restrict the operator to
 n_qubits (int) – Number of qubits defining the total state
Returns: new_operator(ndarray or sparse) –
 Numpy operator restricted to
acting on states with the same particle number.

openfermion.utils.
jw_number_restrict_state
(state, n_electrons, n_qubits=None)¶ Restrict a JordanWigner encoded state to a given particle number
Parameters:  state (ndarray or sparse) – Numpy vector in the space of n_qubits.
 n_electrons (int) – Number of particles to restrict the state to
 n_qubits (int) – Number of qubits defining the total state
Returns: new_operator(ndarray or sparse) –
 Numpy vector restricted to
states with the same particle number. May not be normalized.

openfermion.utils.
jw_slater_determinant
(slater_determinant_matrix)¶ Obtain a Slater determinant.
The input is an \(N_f \times N\) matrix \(Q\) with orthonormal rows. Such a matrix describes the Slater determinant
\[b^\dagger_1 \cdots b^\dagger_{N_f} \lvert \text{vac} \rangle,\]where
\[b^\dagger_j = \sum_{k = 1}^N Q_{jk} a^\dagger_k.\]Parameters: slater_determinant_matrix – The matrix \(Q\) which describes the Slater determinant to be prepared. Returns: The Slater determinant as a sparse matrix.

openfermion.utils.
jw_sz_restrict_operator
(operator, sz_value, n_electrons=None, n_qubits=None, up_map=<function up_index>, down_map=<function down_index>)¶ Restrict a JordanWigner encoded operator to a given Sz value
Parameters:  operator (ndarray or sparse) – Numpy operator acting on the space of n_qubits.
 sz_value (float) – Desired Sz value. Should be an integer or halfinteger.
 n_electrons (int, optional) – Number of particles to restrict the operator to, if such a restriction is desired.
 n_qubits (int, optional) – Number of qubits defining the total state
 up_map (function, optional) – function mapping a spatial index to a spinorbital index. Default is the canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals
 down_map (function, optional) – function mapping spatial index to a spinorbital index. Default is the canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals.
Returns: new_operator(ndarray or sparse) –
 Numpy operator restricted to
acting on states with the desired Sz value.

openfermion.utils.
jw_sz_restrict_state
(state, sz_value, n_electrons=None, n_qubits=None, up_map=<function up_index>, down_map=<function down_index>)¶ Restrict a JordanWigner encoded state to a given Sz value
Parameters:  state (ndarray or sparse) – Numpy vector in the space of n_qubits.
 sz_value (float) – Desired Sz value. Should be an integer or halfinteger.
 n_electrons (int, optional) – Number of particles to restrict the operator to, if such a restriction is desired.
 n_qubits (int, optional) – Number of qubits defining the total state
 up_map (function, optional) – function mapping a spatial index to a spinorbital index. Default is the canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals
 down_map (function, optional) – function mapping spatial index to a spinorbital index. Default is the canonical spinup corresponds to even spinorbitals and spindown corresponds to odd spinorbitals.
Returns: new_operator(ndarray or sparse) –
 Numpy vector restricted to
states with the desired Sz value. May not be normalized.

openfermion.utils.
load_operator
(file_name=None, data_directory=None)¶ Load FermionOperator or QubitOperator from file.
Parameters:  file_name – The name of the saved file.
 data_directory – Optional data directory to change from default data directory specified in config file.
Returns: operator – The stored FermionOperator or QubitOperator
Raises: TypeError
– Operator of invalid type.

openfermion.utils.
low_depth_second_order_trotter_error_bound
(terms, indices=None, is_hopping_operator=None, jellium_only=False, verbose=False)¶ Numerically upper bound the error in the ground state energy for the secondorder TrotterSuzuki expansion.
Parameters:  terms – a list of singleterm FermionOperators in the Hamiltonian to be simulated.
 indices – a set of indices the terms act on in the same order as terms.
 is_hopping_operator – a list of whether each term is a hopping operator.
 jellium_only – Whether the terms are from the jellium Hamiltonian only, rather than the full dual basis Hamiltonian (i.e. whether c_i = c for all number operators i^ i, or whether they depend on i as is possible in the general case).
 verbose – Whether to print percentage progress.
Returns: A float upper bound on norm of error in the ground state energy.
Notes
Follows Equation 9 of Poulin et al.’s work in “The Trotter Step Size Required for Accurate Quantum Simulation of Quantum Chemistry” to calculate the error operator, for the “stagger”based Trotter step for detailed in Kivlichan et al., “Quantum Simulation of Electronic Structure with Linear Depth and Connectivity”, arxiv:1711.04789.

openfermion.utils.
low_depth_second_order_trotter_error_operator
(terms, indices=None, is_hopping_operator=None, jellium_only=False, verbose=False)¶ Determine the difference between the exact generator of unitary evolution and the approximate generator given by the secondorder TrotterSuzuki expansion.
Parameters:  terms – a list of FermionOperators in the Hamiltonian in the order in which they will be simulated.
 indices – a set of indices the terms act on in the same order as terms.
 is_hopping_operator – a list of whether each term is a hopping operator.
 jellium_only – Whether the terms are from the jellium Hamiltonian only, rather than the full dual basis Hamiltonian (i.e. whether c_i = c for all number operators i^ i, or whether they depend on i as is possible in the general case).
 verbose – Whether to print percentage progress.
Returns:  The difference between the true and effective generators of time
evolution for a single Trotter step.
 Notes: follows Equation 9 of Poulin et al.’s work in “The Trotter Step
 Size Required for Accurate Quantum Simulation of Quantum Chemistry”, applied to the “stagger”based Trotter step for detailed in Kivlichan et al., “Quantum Simulation of Electronic Structure with Linear Depth and Connectivity”, arxiv:1711.04789.

openfermion.utils.
pauli_exp_to_qasm
(qubit_operator_list, evolution_time=1.0, qubit_list=None, ancilla=None)¶ Exponentiate a list of QubitOperators to a QASM string generator.
 Exponentiates a list of QubitOperators, and yields string generators in
 QASM format using the formula: exp(1.0j * evolution_time * op).
Parameters:  qubit_operator_list (list of QubitOperators) – list of single Pauliterm QubitOperators to be exponentiated
 evolution_time (float) – evolution time of the operators in the list
 qubit_list – (list/tuple or None)Specifies the labels for the qubits to be output in qasm. If a list/tuple, must have length greater than or equal to the number of qubits in the QubitOperator. Entries in the list must be castable to string. If None, qubits are labeled by index (i.e. an integer).
 ancilla (string or None) – if any, an ancilla qubit to perform the rotation conditional on (for quantum phase estimation)
Yields: string

openfermion.utils.
qubit_operator_sparse
(qubit_operator, n_qubits=None)¶ Initialize a Scipy sparse matrix from a QubitOperator.
Parameters:  qubit_operator (QubitOperator) – instance of the QubitOperator class.
 n_qubits (int) – Number of qubits.
Returns: The corresponding Scipy sparse matrix.

openfermion.utils.
save_operator
(operator, file_name=None, data_directory=None, allow_overwrite=False)¶ Save FermionOperator or QubitOperator to file.
Parameters:  operator – An instance of FermionOperator or QubitOperator.
 file_name – The name of the saved file.
 data_directory – Optional data directory to change from default data directory specified in config file.
 allow_overwrite – Whether to allow files to be overwritten.
Raises: OperatorUtilsError
– Not saved, file already exists.TypeError
– Operator of invalid type.

openfermion.utils.
slater_determinant_preparation_circuit
(slater_determinant_matrix)¶ Obtain the description of a circuit which prepares a Slater determinant.
The input is an \(N_f \times N\) matrix \(Q\) with orthonormal rows. Such a matrix describes the Slater determinant
\[b^\dagger_1 \cdots b^\dagger_{N_f} \lvert \text{vac} \rangle,\]where
\[b^\dagger_j = \sum_{k = 1}^N Q_{jk} a^\dagger_k.\]The output is the description of a circuit which prepares this Slater determinant, up to a global phase. The starting state which the circuit should be applied to is a Slater determinant (in the computational basis) with the first \(N_f\) orbitals filled.
Parameters: slater_determinant_matrix – The matrix \(Q\) which describes the Slater determinant to be prepared. Returns: circuit_description – A list of operations describing the circuit. Each operation is a tuple of elementary operations that can be performed in parallel. Each elementary operation is a tuple of the form \((i, j, \theta, \varphi)\), indicating a Givens rotation of modes \(i\) and \(j\) by angles \(\theta\) and \(\varphi\).

openfermion.utils.
sparse_eigenspectrum
(sparse_operator)¶ Perform a dense diagonalization.
Returns: eigenspectrum – The lowest eigenvalues in a numpy array.

openfermion.utils.
trotter_operator_grouping
(hamiltonian, trotter_number=1, trotter_order=1, term_ordering=None, k_exp=1.0)¶ Trotterdecomposes operators into groups without exponentiating.
 Operators are still Hermitian at the end of this method but have been
 multiplied by k_exp.
Note
The default term_ordering is simply the ordered keys of the QubitOperators.terms dict.
Parameters:  hamiltonian (QubitOperator) – full hamiltonian
 trotter_number (int) – optional number of trotter steps  default is 1
 trotter_order (int) – optional order of trotterization as an integer from 13  default is 1
 term_ordering (list of (tuples of tuples)) – optional list of QubitOperator terms dictionary keys that specifies order of terms when trotterizing
 k_exp (float) – optional exponential factor to all terms when trotterizing
Yields: QubitOperator generator
Raises:  ValueError if order > 3 or order <= 0,
 TypeError for incorrect types

openfermion.utils.
trotterize_exp_qubop_to_qasm
(hamiltonian, trotter_number=1, trotter_order=1, term_ordering=None, k_exp=1.0, qubit_list=None, ancilla=None)¶ Trotterize a Qubit hamiltonian and write it to QASM format.
Assumes input hamiltonian is still hermitian and 1.0j has not yet been applied. Therefore, signs of coefficients should reflect this. Returns a generator which generates a QASM file.
Parameters:  hamiltonian (QubitOperator) – hamiltonian
 trotter_number (int) – optional number of trotter steps (slices) for trotterization as an integer  default = 1
 trotter_order – optional order of trotterization as an integer  default = 1
 term_ordering (list of (tuples of tuples)) – list of tuples (QubitOperator terms dictionary keys) that specifies order of terms when trotterizing
 qubit_list – (list/tuple or None)Specifies the labels for the qubits to be output in qasm. If a list/tuple, must have length greater than or equal to the number of qubits in the QubitOperator. Entries in the list must be castable to string. If None, qubits are labeled by index (i.e. an integer).
 k_exp (float) – optional exponential factor to all terms when trotterizing
 Yields – string generator

openfermion.utils.
uccsd_convert_amplitude_format
(single_amplitudes, double_amplitudes)¶ Reformat single_amplitudes and double_amplitudes from ndarrays to lists.
Parameters:  single_amplitudes (ndarray) – [NxN] array storing single excitation amplitudes corresponding to t[i,j] * (a_i^dagger a_j  H.C.)
 double_amplitudes (ndarray) – [NxNxNxN] array storing double excitation amplitudes corresponding to t[i,j,k,l] * (a_i^dagger a_j a_k^dagger a_l  H.C.)
Returns: single_amplitudes_list(list) –
 list of lists with each sublist storing
a list of indices followed by single excitation amplitudes i.e. [[[i,j],t_ij], …]
 double_amplitudes_list(list): list of lists with each sublist storing
a list of indices followed by double excitation amplitudes i.e. [[[i,j,k,l],t_ijkl], …]

openfermion.utils.
uccsd_operator
(single_amplitudes, double_amplitudes, anti_hermitian=True)¶ Create a fermionic operator that is the generator of uccsd.
This a the most straightforward method to generate UCCSD operators, however it is slightly inefficient. In particular, it parameterizes all possible excitations, so it represents a generalized unitary coupled cluster ansatz, but also does not explicitly enforce the uniqueness in parametrization, so it is redundant. For example there will be a linear dependency in the ansatz of single_amplitudes[i,j] and single_amplitudes[j,i].
Parameters:  single_amplitudes (list or ndarray) – list of lists with each sublist storing a list of indices followed by single excitation amplitudes i.e. [[[i,j],t_ij], …] OR [NxN] array storing single excitation amplitudes corresponding to t[i,j] * (a_i^dagger a_j  H.C.)
 double_amplitudes (list or ndarray) – list of lists with each sublist storing a list of indices followed by double excitation amplitudes i.e. [[[i,j,k,l],t_ijkl], …] OR [NxNxNxN] array storing double excitation amplitudes corresponding to t[i,j,k,l] * (a_i^dagger a_j a_k^dagger a_l  H.C.)
 anti_hermitian (Bool) – Flag to generate only normal CCSD operator rather than unitary variant, primarily for testing
Returns: uccsd_generator(FermionOperator) – Antihermitian fermion operator that is the generator for the uccsd wavefunction.

openfermion.utils.
uccsd_singlet_operator
(packed_amplitudes, n_qubits, n_electrons)¶ Create a singlet UCCSD generator for a system with n_electrons
 This function generates a FermionOperator for a UCCSD generator designed
 to act on a single reference state consisting of n_qubits spin orbitals and n_electrons electrons, that is a spin singlet operator, meaning it conserves spin.
Parameters:  packed_amplitudes (ndarray) – Compact array storing the unique single and double excitation amplitudes for a singlet UCCSD operator. The ordering lists unique single excitations before double excitations.
 n_qubits (int) – Number of spinorbitals used to represent the system, which also corresponds to number of qubits in a noncompact map.
 n_electrons (int) – Number of electrons in the physical system.
Returns: uccsd_generator(FermionOperator) –
 Generator of the UCCSD operator that
builds the UCCSD wavefunction.

openfermion.utils.
uccsd_singlet_paramsize
(n_qubits, n_electrons)¶ Determine number of independent amplitudes for singlet UCCSD
Parameters:  n_qubits (int) – Number of qubits/spinorbitals in the system
 n_electrons (int) – Number of electrons in the reference state
Returns: Number of independent parameters for singlet UCCSD with a single reference.

openfermion.utils.
variance
(sparse_operator, state)¶ Compute variance of operator with a state.
Parameters: state – scipy.sparse.csc vector representing a pure state, or, a scipy.sparse.csc matrix representing a density matrix. Returns: A real float giving the variance. Raises: ValueError
– Input state has invalid format.