Quick Start

TenCirChem contains two primary modules: the static module and the dynamic module, responsible for molecular static and dynamic properties respectively. In the static module, the UCC classes is for noiseless UCC circuit simulation and the HEA class is for noisy simulation or arbitrary circuits.

Installation

TenCirChem can be installed via pip

pip install tencirchem

This will install a minimal version of TenCirChem with NumPy backend. For GPU support and some of the advanced features, install JAX and CuPy for respective backends.

TenCirChem relies heavily on PySCF, which for the moment does not support Windows platform. Windows users are recommended to install TenCirChem in the WSL environment.

UCC Calculation

For static molecular properties using UCC ansatze, TenCirChem has implemented UCCSD (Peruzzo2014), kUpCCGSD (Lee2019), and pUCCD (Elfving2021), based on the UCC base class.

 1from tencirchem import UCCSD, KUPCCGSD, PUCCD, M
 2
 3# distance unit is angstrom
 4d = 0.8
 5# M is borrowed from PySCF. In other words, `from tencirchem import M`
 6# is equivalent to `from pyscf import M`
 7m = M(atom=[["H", 0, 0, d * i] for i in range(2)])
 8
 9# setup
10uccsd = UCCSD(m)
11# calculate and returns energy
12uccsd.kernel()
13# analyze result
14uccsd.print_summary(include_circuit=True)
15
16# other classes share the same interface
17print(KUPCCGSD(m).kernel())
18print(PUCCD(m).kernel())

Apart from the high-level interface inherited from PySCF, TenCirChem offers a rich set of useful intermediate interfaces for access and modification, to facilitate the development and validation of novel algorithms. Functions of the UCC classes include

  • outputting the Hamiltonian as integrals or OpenFermion objects,

  • outputting the circuit as TensorCircuit object,

  • active space approximation,

  • calculating one and two body reduced density matrices,

  • interfacing with PySCF for CASSCF calculation and nuclear gradients,

and much more. Please refer to the UCC Functions tutorial for detailed guide and the Examples directory for working examples.

UCC Speed

The UCC class exploits particle number conservation and UCC factor expansion for extremely efficient simulation. Here we show the tested UCCSD wall time of TenCirChem over hydrogen chain system, along with corresponding error compared to FCI. The bond length is 0.8 Å and the basis set is STO-3G. We do not include the wall time of other packages, but the tremendous speed up is quite visible.

Molecule

Qubits

Circuit Depth

Parameters

Wall time (s)

Error (mH)

\(\rm{H}_4\)

8

78

11

0.05

0.01

\(\rm{H}_6\)

12

462

39

0.4

0.27

\(\rm{H}_8\)

16

1,834

108

1.9

0.72

\(\rm{H}_{10}\)

20

5,586

246

14

1.37

\(\rm{H}_{12}\)

24

13,917

495

51

2.13

\(\rm{H}_{14}\)

28

30,428

899

2093

2.92

\(\rm{H}_{16}\)

32

59,634

1,520

50909

3.72

For the first three row the engine is "civector" with NumPy backend, and the rest is with "civector-large" engine and CuPy backend on V100 GPU. For more details please refer to Why is TenCirChem so fast?.

Noisy Circuit Simulation

TenCirChem supports noisy circuit simulation through the HEA class. HEA.ry accepts integrals and setups the class with \(R_y\) ansatz. The engine argument controls how the energy is evaluated. "tensornetwork" is for noiseless simulation, "tensornetwork-noise" includes gate noise, "tensornetwork-shot" includes measurement uncertainty, and "tensornetwork-noise&shot" includes both.

 1from tencirchem import UCCSD, HEA
 2from tencirchem.molecule import h2
 3
 4# use the `UCCSD` class to access the integrals
 5uccsd = UCCSD(h2)
 6
 7# use the `HEA` class for noisy circuits. A 1-layer Ry ansatz is used
 8hea = HEA.ry(uccsd.int1e, uccsd.int2e, uccsd.n_elec, uccsd.e_core, n_layers=1, engine="tensornetwork-noise")
 9hea.kernel()
10hea.print_summary()
11
12# noiseless energy
13print(hea.energy(engine="tensornetwork"))
14# the energy with gate noise and measurement noise
15print(hea.energy(engine="tensornetwork-noise&shot"))

The HEA class supports arbitrary circuit and Hamiltonian. The cutomization guide is included in the Noisy Circuit Simulation tutorial.

Dynamics Calculation

In the following we show how to perform quantum dynamics simulation using a 1-mode spin-boson model as an example.

\[\hat H = \epsilon \hat \sigma_z + \Delta \hat \sigma_x + \omega \hat b^\dagger \hat b + g \sigma_z (\hat b^\dagger + \hat b)\]

For simplicity in the following we assume \(\epsilon=\Delta=\omega=g=1\).

TenCirChem uses the Op and BasisSet classes in Renormalizer to define the Hamiltonian and the basis sets.

# equivalent to `from renormalizer import ...`
from tencirchem import Op, BasisHalfSpin, BasisSHO

ham_terms = [
    Op("sigma_z", "spin"),
    Op("sigma_x", "spin"),
    Op(r"b^\dagger b", "boson"),
    Op("sigma_z", "spin") * Op(r"b^\dagger+b", "boson")
]
basis = [BasisHalfSpin("spin"), BasisSHO("boson", omega=1, nbas=4)]

For more about these classes please refer to the Renormalizer document.

Next, run the time evolution

from tencirchem import TimeEvolution, set_backend

# the dynamics module only supports JAX backend
set_backend("jax")

# property_op_dict determines the physical observables that is calculated during time evolution
te = TimeEvolution(ham_terms, basis, property_op_dict={"Z": Op("sigma_z", spin)})
# one step of time evolution and time step is 0.1
te.kernel(0.1)
# print physical observable
print(te.properties["Z"])

See the Dynamics of the Spin-Boson Model for what’s happening under the hood and how to customize the TimeEvolution class.

Further Readings

That’s all for the basics of TenCirChem! If you wish to learn more, you may visit