qml.pauli¶
Overview¶
This module defines functions and classes for generating and manipulating
elements of the Pauli group. It also contains a subpackage pauli/grouping
for Pauli-word partitioning functionality used in measurement optimization.
Functions¶
|
Performs a check if two Pauli words have the same |
|
Given a list of observables assumed to be valid Pauli observables, determine if they are pairwise qubit-wise commuting. |
|
Converts a binary vector of even dimension to an Observable instance. |
|
Computes the partition indices of a list of observables using a specified grouping type and graph colouring method. |
|
Transforms the Pauli word to diagonal form in the computational basis. |
|
Diagonalizes a list of qubit-wise commutative groupings of Pauli strings. |
|
Diagonalizes a list of mutually qubit-wise commutative Pauli words. |
|
Partitions a list of observables (Pauli operations and tensor products thereof) into groupings according to a binary relation (qubit-wise commuting, fully-commuting, or anticommuting). |
|
Checks if an observable instance consists only of Pauli and Identity Operators. |
|
Checks if two Pauli words in the binary vector representation are qubit-wise commutative. |
|
Converts a list of Pauli words into a matrix where each row is the binary vector (symplectic) representation of the |
|
Partitions then diagonalizes a list of Pauli words, facilitating simultaneous measurement of all observables within a partition. |
|
Partitions the \(n\)-qubit Pauli group into qubit-wise commuting terms. |
|
Decomposes a Hermitian matrix into a linear combination of Pauli operators. |
|
Generate the \(n\)-qubit Pauli group. |
|
Return the PauliSentence representation of an arithmetic operator or Hamiltonian. |
|
Converts a Pauli word to the binary vector (symplectic) representation. |
|
If the operator provided is a valid Pauli word (i.e a single term which may be a tensor product of pauli operators), then this function extracts the prefactor. |
|
Convert a Pauli word from a tensor to its matrix representation. |
|
Convert a Pauli word to a string. |
|
Obtains the adjacency matrix for the complementary graph of the qubit-wise commutativity graph for a given set of observables in the binary representation. |
|
Performs circuit implementation of diagonalizing unitary for a Pauli word. |
|
Add together identical terms in the Hamiltonian. |
|
Convert a string in terms of |
Classes¶
|
Class for partitioning a list of Pauli words according to some binary symmetric relation. |
Dictionary representing a linear combination of Pauli words, with the keys as |
|
|
Class representing the linearly independent basis of a vector space. |
|
Immutable dictionary used to represent a Pauli Word, associating wires with their respective operators. |
PauliWord and PauliSentence¶
The single-qubit Pauli group consists of the four single-qubit Pauli operations
Identity
, PauliX
,
PauliY
, and PauliZ
. The \(n\)-qubit
Pauli group is constructed by taking all possible \(N\)-fold tensor products
of these elements. Elements of the \(n\)-qubit Pauli group are known as
Pauli words, and have the form \(P_J = \otimes_{i=1}^{n}\sigma_i^{(J)}\),
where \(\sigma_i^{(J)}\) is one of the Pauli operators
(PauliX
, PauliY
,
PauliZ
) or identity (Identity
) acting on
the \(i^{th}\) qubit. The full \(n\)-qubit Pauli group has size
\(4^n\) (neglecting the four possible global phases that may arise from
multiplication of its elements).
PauliWord
is a lightweight class which uses a dictionary
approach to represent Pauli words. A PauliWord
can be
instantiated by passing a dictionary of wires and their associated Pauli operators.
>>> from pennylane.pauli import PauliWord
>>> pw1 = PauliWord({0:"X", 1:"Z"}) # X@Z
>>> pw2 = PauliWord({0:"Y", 1:"Z"}) # Y@Z
>>> pw1, pw2
(X(0) @ Z(1), Y(0) @ Z(1))
The purpose of this class is to efficiently compute products of Pauli words and obtain the matrix representation.
>>> pw1 @ pw2
1j * Z(0)
>>> pw1.to_mat(wire_order=[0, 1])
array([[ 0, 0, 1, 0],
[ 0, 0, 0, -1],
[ 1, 0, 0, 0],
[ 0, -1, 0, 0]])
The PauliSentence
class represents linear combinations of
Pauli words. Using a similar dictionary based approach we can efficiently add, multiply
and extract the matrix of operators in this representation.
>>> ps1 = PauliSentence({pw1: 1.2, pw2: 0.5j})
>>> ps2 = PauliSentence({pw1: -1.2})
>>> ps1
1.2 * X(0) @ Z(1)
+ 0.5j * Y(0) @ Z(1)
>>> ps1 + ps2
0.0 * X(0) @ Z(1)
+ 0.5j * Y(0) @ Z(1)
>>> ps1 @ ps2
-1.44 * I
+ (-0.6+0j) * Z(0)
>>> (ps1 + ps2).to_mat(wire_order=[0, 1])
array([[ 0. +0.j, 0. +0.j, 0.5+0.j, 0. +0.j],
[ 0. +0.j, 0. +0.j, 0. +0.j, -0.5+0.j],
[-0.5+0.j, 0. +0.j, 0. +0.j, 0. +0.j],
[ 0. +0.j, 0.5+0.j, 0. +0.j, 0. +0.j]])
We can intuitively use Pauli arithmetic to construct Hamiltonians consisting of PauliWord
and PauliSentence
objects like the spin-1/2 XXZ model Hamiltonian,
Here we look at the simple topology of a one-dimensional chain with periodic boundary conditions
(i.e. qubit number \(n \equiv 0\) for pythonic numbering of wires, e.g. [0, 1, 2, 3]
for n=4
).
In code we can do this via the following example with 4 qubits.
n = 4
J_orthogonal = 1.5
ops = [
J_orthogonal * (PauliWord({i:"X", (i+1)%n:"X"}) + PauliWord({i:"Y", (i+1)%n:"Y"}))
for i in range(n)
]
J_zz = 0.5
ops += [J_zz * PauliWord({i:"Z", (i+1)%n:"Z"}) for i in range(n)]
h = 2.
ops += [h * PauliWord({i:"Z"}) for i in range(n)]
H = sum(ops)
We can also displace the Hamiltonian by an arbitrary amount. Here, for example, such that the ground state energy is 0.
>>> H = H - np.min(np.linalg.eigvalsh(H.to_mat()))
Graph colouring¶
A module for heuristic algorithms for colouring Pauli graphs.
A Pauli graph is a graph where vertices represent Pauli words and edges denote if a specified symmetric binary relation (e.g., commutation) is satisfied for the corresponding Pauli words. The graph-colouring problem is to assign a colour to each vertex such that no vertices of the same colour are connected, using the fewest number of colours (lowest “chromatic number”) as possible.
Functions¶
|
Performs graph-colouring using the Largest Degree First heuristic. |
|
Performs graph-colouring using the Recursive Largest Degree First heuristic. |
Grouping observables¶
Pauli words can be used for expressing a qubit Hamiltonian
.
A qubit Hamiltonian has the form \(H_{q} = \sum_{J} C_J P_J\) where
\(C_{J}\) are numerical coefficients, and \(P_J\) are Pauli words.
A list of Pauli words can be partitioned according to certain grouping
strategies. As an example, the group_observables()
function partitions
a list of observables (Pauli operations and tensor products thereof) into
groupings according to a binary relation (e.g., qubit-wise commuting):
>>> observables = [qml.PauliY(0), qml.PauliX(0) @ qml.PauliX(1), qml.PauliZ(1)]
>>> obs_groupings = group_observables(observables)
>>> obs_groupings
[[PauliX(wires=[0]) @ PauliX(wires=[1])],
[PauliY(wires=[0]), PauliZ(wires=[1])]]
The \(C_{J}\) coefficients for each \(P_J\) Pauli word making up a Hamiltonian can also be specified along with further options, such as the Pauli-word grouping method (e.g., qubit-wise commuting) and the underlying graph-colouring algorithm (e.g., recursive largest first) used for creating the groups of observables:
>>> obs = [qml.PauliY(0), qml.PauliX(0) @ qml.PauliX(1), qml.PauliZ(1)]
>>> coeffs = [1.43, 4.21, 0.97]
>>> obs_groupings, coeffs_groupings = group_observables(obs, coeffs, 'qwc', 'rlf')
>>> obs_groupings
[[PauliX(wires=[0]) @ PauliX(wires=[1])],
[PauliY(wires=[0]), PauliZ(wires=[1])]]
>>> coeffs_groupings
[[4.21], [1.43, 0.97]]
For a larger example of how grouping can be used with PennyLane, check out the Measurement Optimization demo.
Dynamical Lie Algebras¶
PennyLane provides support for working with dynamical Lie algebras (DLA) of Pauli operators. See our introduction to Dynamical Lie Algebras for quantum practitioners.
|
Compute the dynamical Lie algebra from a set of generators. |
|
Compute the structure constants that make up the adjoint representation of a Lie algebra. |
|
A function to compute the center of a Lie algebra. |