Source code for qsttoolkit.data.states

import numpy as np
import scipy.special
import random
from qutip import coherent, Qobj, fock, ket2dm
import warnings

from qsttoolkit.data.num_state_coeffs import states17, statesM, statesP, statesP2, statesM2
from qsttoolkit.utils import _range_error


##### State vectors #####

[docs] def cat_state(dim: int, alpha: float, N=None) -> Qobj: """ Generates a cat state (superposition of coherent states). Parameters ---- dim: int Hilbert space dimensionality. alpha: float Coherent state parameter. Returns ------- Qobj Cat state. """ if not dim: if N: dim = N warnings.warn("N is deprecated and will be removed in a future version. Please use dim instead.", DeprecationWarning, stacklevel=2) else: raise ValueError("dim must be specified.") if not isinstance(dim, int): raise TypeError("dim must be an integer") return (coherent(dim, alpha) + coherent(dim, -alpha)).unit()
[docs] def num_state(state: str, dim: int=None, state_index: int=None, N=None) -> Qobj: """ Generates a 'num state' (specific superposition of Fock states numerically optimized for quantum error correction). Parameters ---- state: str Type of num state to generate. Must be one of '17', 'M', 'P', 'P2', or 'M2'. dim: int Hilbert space dimensionality. If None, the dimension of the state vector will be used. state_index: int Index of the state to generate. If None, a random state will be generated. Returns ------- Qobj 'Num state'. """ if N: dim = N warnings.warn("N is deprecated and will be removed in a future version. Please use dim instead.", DeprecationWarning, stacklevel=2) if not isinstance(dim, int): raise TypeError("dim must be an integer.") if state == '17': coeffs = states17 elif state == 'M': coeffs = statesM elif state == 'P': coeffs = statesP elif state == 'P2': coeffs = statesP2 elif state == 'M2': coeffs = statesM2 else: raise ValueError("state must be one of '17', 'M', 'P', 'P2', or 'M2'") if state_index is not None: if state_index < 0: raise ValueError("state_index must be non-negative.") elif state_index >= len(coeffs): raise ValueError("state_index must be less than the number of states in the given type set.") else: state_index = random.randint(0, len(coeffs) - 1) vector = coeffs[state_index] if dim is not None: if dim < len(vector): raise ValueError("dim must be greater than or equal to the length of the state vector.") elif dim > len(vector): # Extend vector with zeros vector = np.append(vector, np.zeros((dim - len(vector), 1)), axis=0) return Qobj(vector).unit()
[docs] def binomial_state(dim: int, S: int, N: int, mu: int, Nc=None) -> Qobj: """ Generates a binomial superposition of Fock states. Parameters ---- dim: int Hilbert space dimensionality. S: int Coherent state parameter. N: int Number of excitations. mu: int Logical encoding parameter. Returns ------- Qobj Binomial state in the Nc-dimensional Hilbert space. """ if not dim: if Nc: dim = Nc warnings.warn("Nc is deprecated and will be removed in a future version. Please use dim instead.", DeprecationWarning, stacklevel=2) else: raise ValueError("dim must be specified.") if not isinstance(dim, int): raise TypeError("dim must be an integer.") if S < 1 or S > 10: raise ValueError("S must be between 1 and 10.") # if N < 2 or N > (dim // (S + 1))-1: Ignored for now, will be reintroduced in a future version # raise ValueError("N must be between 2 and dim/(S+1) - 1") return sum([(-1 ** (mu*m)) * np.sqrt(scipy.special.binom(N+1, m)) * fock(dim, (S+1)*m) for m in range(N+1)]).unit()
[docs] def gkp_state(dim: int, n1_range: list[int, int], n2_range: list[int, int], delta: float, mu: int, N=None) -> Qobj: """ Generates a Gottesman-Kitaev-Preskill (GKP) state. Parameters ---- dim: int Hilbert space dimensionality. n1_range: list Grid parameter 1. n2_range: int Grid parameter 2. delta: float Real normalisation parameter. mu: int Logical encoding parameter. Returns ------- Qobj GKP state. """ if not dim: if N: dim = N warnings.warn("N is deprecated and will be removed in a future version. Please use dim instead.", DeprecationWarning, stacklevel=2) else: raise ValueError("dim must be specified.") if not isinstance(dim, int): raise TypeError("dim must be an integer.") _range_error(n1_range, integers=True, positive=False) _range_error(n2_range, integers=True, positive=False) # if not isinstance(mu, int): raise TypeError("mu must be an integer.") Ignored for now, may be reintroduced in a future version grid = np.array([[n1, n2] for n1 in range(n1_range[0], n1_range[1]+1) for n2 in range(n2_range[0], n2_range[1]+1)]) alphas = np.array([np.sqrt(np.pi/2)*((2*n1 + mu) + 1j*n2) for n1, n2 in grid]) return sum([np.exp(-delta**2 * np.abs(alpha)**2) * np.exp(-1j * alpha.real * alpha.imag) * coherent(dim, alpha) for alpha in alphas]).unit()
##### Density matrices #####
[docs] def cat_dm(dim: int, alpha: float, N=None) -> Qobj: """ Generates a density matrix for a cat state (superposition of coherent states). Parameters ---- dim: int Hilbert space dimensionality. alpha: float Coherent state parameter. Returns ------- Qobj Density matrix for a cat state. """ if not dim: if N: dim = N warnings.warn("N is deprecated and will be removed in a future version. Please use dim instead.", DeprecationWarning, stacklevel=2) else: raise ValueError("dim must be specified.") return ket2dm(cat_state(dim, alpha))
[docs] def num_dm(state: str, dim=None, state_index=None, N=None) -> Qobj: """ Generates a density matrix for a 'num state' (specific superposition of Fock states numerically optimized for quantum error correction). Parameters ---- state: str Type of 'num state' to generate. Must be one of '17', 'M', 'P', 'P2', or 'M2'. dim: int Hilbert space dimensionality. If None, the dimension of the state vector will be used. state_index: int Index of the state to generate. If None, a random state will be generated. Returns ------- Qobj Density matrix for a 'num state'. """ if not dim: if N: dim = N warnings.warn("N is deprecated and will be removed in a future version. Please use dim instead.", DeprecationWarning, stacklevel=2) else: raise ValueError("dim must be specified.") return ket2dm(num_state(state, dim, state_index))
[docs] def binomial_dm(dim: int, S: int, N: int, mu: int, Nc=None) -> Qobj: """ Generates a density matrix for a binomial superposition of Fock states. Parameters ---- dim: int Hilbert space dimensionality. S: int Coherent state parameter. N: int Number of excitations. mu: int Logical encoding parameter. Returns ------- Qobj Density matrix for a binomial state in the Nc-dimensional Hilbert space. """ if not dim: if Nc: dim = Nc warnings.warn("Nc is deprecated and will be removed in a future version. Please use dim instead.", DeprecationWarning, stacklevel=2) else: raise ValueError("dim must be specified.") return ket2dm(binomial_state(dim, S, N, mu))
[docs] def gkp_dm(dim: int, n1_range: list[int, int], n2_range: list[int, int], delta: float, mu: int, N=None) -> Qobj: """ Generates a density matrix for a Gottesman-Kitaev-Preskill (GKP) state. Parameters ---- dim: int Hilbert space dimensionality. n1_range: list Grid parameter 1. n2_range: int Grid parameter 2. delta: float Real normalisation parameter. mu: int Logical encoding parameter. Returns ------- Qobj Density matrix for a GKP state. """ if not dim: if N: dim = N warnings.warn("N is deprecated and will be removed in a future version. Please use dim instead.", DeprecationWarning, stacklevel=2) else: raise ValueError("dim must be specified.") return ket2dm(gkp_state(dim, n1_range, n2_range, delta, mu))