Coverage for qml_essentials / states.py: 97%
29 statements
« prev ^ index » next coverage.py v7.13.4, created at 2026-09-03 21:15 +0000
« prev ^ index » next coverage.py v7.13.4, created at 2026-09-03 21:15 +0000
1r"""State-preparation utilities.
3Constructors for input statevectors used in trainability and barren-plateau
4analysis. All functions return a dense statevector of shape :math:`(2^n,)`
5with qubit 0 leftmost (most significant), consistent with
6:mod:`qml_essentials.algebra` and ``g_purity_from_basis``. The arrays are plain
7numpy and auto-convert to the jnp ``initial_state`` accepted by
8:meth:`jaqsi.script.Script.execute`.
10- :func:`dicke_state` builds the permutation-symmetric Dicke state
11 :math:`|D_{n,k}\rangle`.
12- :func:`haar_state` builds a Haar-random pure state.
13- :func:`graph_state_vector` builds the graph state :math:`\prod_{(i,j)} CZ_{ij}
14 H^{\otimes n}|0\rangle` for a given edge set, with :func:`matching_edges`,
15 :func:`path_edges`, and :func:`complete_edges` as standard edge-set
16 constructors.
17"""
19from typing import Iterable, List, Tuple, Union
21import numpy as np
24def dicke_state(n: int, k: int) -> np.ndarray:
25 r"""Return the Dicke state :math:`|D_{n,k}\rangle`.
27 The permutation-symmetric equal superposition of all computational basis
28 states of Hamming weight :math:`k`.
30 Args:
31 n: Number of qubits.
32 k: Hamming weight, with :math:`0 \leq k \leq n`.
34 Returns:
35 The normalised statevector of shape :math:`(2^n,)` (qubit 0 leftmost).
37 Raises:
38 ValueError: If ``n < 1`` or ``k`` is outside ``[0, n]``.
39 """
40 if n < 1:
41 raise ValueError(f"n must be at least 1, got {n}")
42 if not 0 <= k <= n:
43 raise ValueError(f"k must satisfy 0 <= k <= n, got k={k} for n={n}")
44 psi = np.zeros(2**n, dtype=complex)
45 idx = [x for x in range(2**n) if bin(x).count("1") == k]
46 psi[idx] = 1.0
47 return psi / np.linalg.norm(psi)
50def haar_state(
51 n: int, seed: Union[int, np.random.Generator, None] = None
52) -> np.ndarray:
53 r"""Return a Haar-random pure state.
55 Drawn as a normalised complex Gaussian vector, which is uniform with respect
56 to the Haar measure on pure states.
58 Args:
59 n: Number of qubits.
60 seed: Source of randomness. An ``int`` seed, a
61 :class:`numpy.random.Generator`, or ``None`` for fresh entropy.
63 Returns:
64 The normalised statevector of shape :math:`(2^n,)`.
65 """
66 rng = seed if isinstance(seed, np.random.Generator) else np.random.default_rng(seed)
67 v = rng.normal(size=2**n) + 1j * rng.normal(size=2**n)
68 return v / np.linalg.norm(v)
71def graph_state_vector(n: int, edges: Iterable[Tuple[int, int]]) -> np.ndarray:
72 r"""Return the explicit graph-state statevector for the given edges.
74 The graph state is :math:`\prod_{(i,j) \in E} CZ_{ij} H^{\otimes n}|0\rangle`.
75 Each :math:`CZ` flips the sign of the amplitudes whose two qubits are both
76 one.
78 Args:
79 n: Number of qubits.
80 edges: Iterable of qubit-index pairs :math:`(i, j)`.
82 Returns:
83 The statevector of shape :math:`(2^n,)` (qubit 0 leftmost).
84 """
85 psi = np.ones(2**n, dtype=complex) / np.sqrt(2**n) # H^n|0>
86 idx = np.arange(2**n)
87 for i, j in edges:
88 bi = (idx >> (n - 1 - i)) & 1 # qubit 0 is most significant
89 bj = (idx >> (n - 1 - j)) & 1
90 psi = psi * np.where(bi & bj, -1.0, 1.0)
91 return psi
94def matching_edges(n: int) -> List[Tuple[int, int]]:
95 r"""Return the perfect-matching edges :math:`(0,1),(2,3),\dots`.
97 Yields a disconnected graph state (a product of two-qubit graph states) with
98 low entanglement.
100 Args:
101 n: Number of qubits.
103 Returns:
104 The list of edge pairs.
105 """
106 return [(i, i + 1) for i in range(0, n - 1, 2)]
109def path_edges(n: int) -> List[Tuple[int, int]]:
110 r"""Return the path edges :math:`0\text{-}1\text{-}\dots\text{-}(n-1)`.
112 Yields a connected one-dimensional cluster state.
114 Args:
115 n: Number of qubits.
117 Returns:
118 The list of edge pairs.
119 """
120 return [(i, i + 1) for i in range(n - 1)]
123def complete_edges(n: int) -> List[Tuple[int, int]]:
124 r"""Return the complete-graph edges of :math:`K_n`.
126 Yields a connected, permutation-symmetric graph state.
128 Args:
129 n: Number of qubits.
131 Returns:
132 The list of edge pairs :math:`(i, j)` with :math:`i < j`.
133 """
134 return [(i, j) for i in range(n) for j in range(i + 1, n)]