from proveit.expression import Literal, Operation, STRING, LATEX pkg = __package__ class InverseFourierTransform(Operation): ''' Represents the quantum circuit for the quantum fourier transform algorithm. ''' def __init__(self, n): ''' QFT circuit for n qubits. ''' Operation.__init__(self, INV_FT, n) self.nqubits = n def formatted(self, formatType, fence=False): formattedOperator = self.operator.formatted(formatType, fence=False) formatedNqubits = self.nqubits.formatted(formatType, fence=False) return formattedOperator + '_{' + formatedNqubits + '}' INV_FT = Literal( pkg, 'INV_FT', { STRING: 'FT^{dag}', LATEX: r'{\rm FT}^{\dag}' }, operationMaker=lambda operands: InverseFourierTransform(*operands))
from proveit.expression import Literal, Operation, LATEX pkg = __package__ class AngDiff(Operation): def __init__(self, angle1, angle2): Operation.__init__(self, ANGULAR_DIFFERENCE, (angle1, angle2)) self.angle1 = angle1 self.angle2 = angle2 ANGULAR_DIFFERENCE = Literal( pkg, 'AngDiff', {LATEX: r'{\rm AngDiff}'}, operationMaker=lambda operands: AngDiff(*operands))
from proveit.expression import Operation, Literal pkg = __package__ class Domain(Operation): def __init__(self, mapExpr): Operation.__init__(self, DOMAIN, [mapExpr]) DOMAIN = Literal(pkg, 'DOMAIN', lambda operand : Domain(operand)) class CoDomain(Operation): def __init__(self, mapExpr): Operation.__init__(self, CODOMAIN, [mapExpr]) CODOMAIN = Literal(pkg, 'CODOMAIN', lambda operand : CoDomain(operand))
def __init__(self, expr_tensor): Operation.__init__(self, MATRIX, expr_tensor) self.tensor = self.operands if not isinstance(self.tensor, ExpressionTensor): raise ImproperMatrix( 'Matrix must be given an ExpressionTensor for its operands') if len(self.tensor.shape) != 2: raise ImproperMatrix( 'Matrix must be given a 2-dimensional ExpressionTensor') self.nrows = self.tensor.shape[0] self.ncolumns = self.tensor.shape[1] def formatted(self, format_type, fence=True): if format_type == STRING: return Operation.formatted(format_type, fence=False) elif format_type == LATEX: return r'\left[' + self.operands.formatted(format_type) + '\right]' MATRIX = Literal(pkg, 'MATRIX', operation_maker=lambda operands: Matrix(operands)) class ImproperMatrix: def __init__(self, msg): self.msg = msg def str(self): return self.msg
from proveit.expression import Literal, STRING, LATEX from proveit.number import Exp, Abs, Add, Sub, Neg, Mult, frac, Interval from proveit.number.common import one, two from proveit.common import k, l, eps from proveit.physics.quantum.QPE.phaseEstOps import SubIndexed pkg = __package__ # U: Unitary operator to apply quantum phase estimation. U_ = Literal(pkg, 'U') # n: Number of qubits which U acts on. n_ = Literal(pkg, 'n') # u: Eigenvector of U to apply the quantum phase estimation. u_ = Literal(pkg, 'u') # phase: Eigenvalue phase of u w.r.t. U. U u = e^{i \varphi} u. # This \varphi is the phase that is the objective of phase estimation. phase_ = Literal(pkg, 'phase', {LATEX: r'\varphi'}) # t: Number of qubit registers for the quantum phase estimation. # We prove that this is the bits of precision of phase estimation. t_ = Literal(pkg, 't') # Psi: Outcome of register qubits following the quantum phase estimation circuit. Psi_ = Literal(pkg, 'PSI', {STRING: 'Psi', LATEX: r'\Psi'}) # psi: indexed intermediate output registers inside the quantum phase estimation circuit. psi_ = Literal(pkg, 'psi', {STRING: 'psi', LATEX: r'\psi'}) psi_k = SubIndexed(psi_, k) psi_t = SubIndexed(psi_, t_)
from proveit.expression import Operation, Literal pkg = __package__ # Special Unitary group class SU(Operation): def __init__(self, n): ''' Create some SU(n), the special unitary of degree n. ''' Operation.__init__(self, SPECIAL_UNITARY, n) self.operand = n SPECIAL_UNITARY = Literal(pkg, 'SU', operationMaker=lambda operands: SU(*operands))
) return tensorProdEquivByElimination.specialize({ aEtc: tensorEquality.lhs.factors[:k], x: factor1, y: factor2, zEtc: tensorEquality.lhs.factors[k + 1:] }) TENSOR_PROD = Literal(pkg, 'TENSOR_PROD', { STRING: r'otimes', LATEX: r'\otimes' }, operationMaker=lambda operands: TensorProd(*operands)) class TensorExp(Operation): def __init__(self, base, exponent): r''' Tensor exponentiation to any natural number exponent. ''' Operation.__init__(self, TENSOR_EXP, (base, exponent)) self.base = self.operands[0] self.exponent = self.operands[1] def formatted(self, formatType, fence=True): formattedBase = self.base.formatted(formatType, fence=True)
pkg = __package__ class QPE(Operation): ''' Represents the quantum circuit for the quantum phase estimation algorithm. ''' def __init__(self, U, t): ''' Phase estimator circuit for Unitary U and t register qubits. ''' Operation.__init__(self, QUANTUM_PHASE_ESTIMATION, (U, t)) QUANTUM_PHASE_ESTIMATION = Literal( pkg, 'QPE', {LATEX: r'{\rm QPE}'}, operationMaker=lambda operands: QPE(*operands)) class PhaseEst(Operation): ''' Represents the quantum circuit for estimating the phase. The quantum phase estimation algorithm consists of a PHASE_ESTIMATOR followed by quantum fourier transform. ''' def __init__(self, U, t): ''' Phase estimator circuit for Unitary U and t register qubits. ''' Operation.__init__(self, PHASE_ESTIMATION, (U, t))
def __init__(self, state): ''' Create a INPUT operation with the given input state. ''' Operation.__init__(self, INPUT, state) self.state = state def formatted(self, formatType, fence=False): formattedState = self.state.formatted(formatType, fence=False) if formatType == LATEX: return r'\lstick{' + formattedState + r'}' else: return Operation.formatted(self, formatType, fence) INPUT = Literal(pkg, 'INPUT', operationMaker=lambda operands: Input(*operands) ) # An input state (entering the left of the circuit) class Output(Operation): ''' Represents an input state entering from the left of the circuit ''' def __init__(self, state): ''' Create a INPUT operation with the given input state. ''' Operation.__init__(self, OUTPUT, state) self.state = state def formatted(self, formatType, fence=False): formattedState = self.state.formatted(formatType, fence=False)
from proveit.expression import Operation, Literal from proveit.common import x, X pkg = __package__ class Prob(Operation): def __init__(self, event, random_variable): Operation.__init__(self, PROB, [event, random_variable]) self.event = event self.random_variable = random_variable def formatted(self, formatType, fence=False): formattedEvent = self.event.formatted(formatType, fence=False) formattedVar = self.random_variable.formatted(formatType, fence=False) return 'Pr_{' + formattedVar + '}[' + formattedEvent + ']' def deduceInInterval(self): from axioms import probBetweenZeroAndOne return probBetweenZeroAndOne.specialize({ x: self.random_variable, X: self.event }) def deduceInReals(self): from theorems import probInReals return probInReals.specialize({x: self.random_variable, X: self.event}) PROB = Literal(pkg, 'PROB', operationMaker=lambda operands: Prob(*operands))
class Bra(Operation): def __init__(self, label): Operation.__init__(self, BRA, label) self.label = label def formatted(self, formatType, fence=False): if formatType == LATEX: return r'\langle ' + self.label.formatted(formatType, fence=False) + r' \rvert' else: return '<' + self.label.formatted(formatType, fence=False) + '|' BRA = Literal(pkg, 'BRA', operationMaker=lambda operands: Bra(*operands)) class Ket(Operation): def __init__(self, label): Operation.__init__(self, KET, label) self.label = label def formatted(self, formatType, fence=False, no_lvert=False): leftStr = r'\lvert ' if formatType == LATEX else '|' if no_lvert: leftStr = '' if formatType == LATEX: return leftStr + self.label.formatted(formatType, fence=False) + r' \rangle' else: return leftStr + self.label.formatted(formatType,
def __init__(self, *operands): r''' Matrix dot product of any number of operands. ''' AssociativeOperation.__init__(self, MATRIX_PROD, *operands) def formatted(self, formatType, fence=False, subFence=True): # Temporary hack to get quantum bra and ket products to display properly. # This should eventually be done differently because we shouldn't need to # know anything about the quantum application here. from proveit.physics.quantum import Bra, Ket, RegisterBra, RegisterKet if len(self.operands) == 2 and (isinstance(self.operands[0], Bra) or isinstance(self.operands[0], RegisterBra)) and (isinstance(self.operands[1], Ket) or isinstance(self.operands[1], RegisterKet)): return self.operands[0].formatted(formatType) + self.operands[1].formatted(formatType, no_lvert=True) return AssociativeOperation.formatted(self, formatType, fence, subFence) MATRIX_PROD = Literal(pkg, 'MATRIX_PROD', {STRING: r'.', LATEX: r' '}, operationMaker = lambda operands : MatrixProd(*operands)) class ScalarProd(BinaryOperation): def __init__(self, *operands): r''' Product between a scalar and a matrix. ''' BinaryOperation.__init__(self, SCALAR_PROD, *operands) self.scalar = operands[0] self.scaled = operands[1] def simplification(self): ''' For the trivial case a nested scalar product, derive and return this scalar product expression equated with a simplified form. '''
from proveit.common import A, B, C, D from proveit.expression import Variable, Literal, LATEX, STRING from proveit.multiExpression import Block from proveit.number import Exp, frac, sqrt from proveit.number.common import zero, one, two from proveit.number.numberSets import Complexes from proveit.linalg import TensorExp, SU from proveit.physics.quantum.circuit import Gate from proveit.physics.quantum.quantumOps import Ket pkg = __package__ I = Literal(pkg, 'I') # Single qubit identity X = Literal(pkg, 'X') # Pauli-X Y = Literal(pkg, 'Y') # Pauli-Y Z = Literal(pkg, 'Z') # Pauli-Z H = Literal(pkg, 'H') # Hadamard # PASS: either a blank spot or continuation of a wire in a quantum circuit. # Can be used when initializing the circuit with a list of lists -- these PASS elements # are subsequently removed and turned into empty spots of the quantum circuit tensor. PASS = Literal(pkg, 'PASS') PLUS = Literal(pkg, 'PLUS', {LATEX:'+', STRING:'+'}) # For positive X eigenstate MINUS = Literal(pkg, 'MINUS', {LATEX:'-', STRING:'-'}) # For negative X eigenstate ket0 = Ket(zero) ket1 = Ket(one) ketPlus = Ket(PLUS) ketMinus = Ket(MINUS)
from proveit.common import A, B, C, D from proveit.expression import Variable, Literal, LATEX, STRING from proveit.multi_expression import Block from proveit.numbers import Exp, frac, sqrt from proveit.numbers.common import zero, one, two from proveit.numbers.number_sets import Complex from proveit.linalg import TensorExp, SU from proveit.physics.quantum.circuit import Gate from proveit.physics.quantum.quantum_ops import Ket pkg = __package__ I = Literal(pkg, 'I') # Single qubit identity X = Literal(pkg, 'X') # Pauli-X Y = Literal(pkg, 'Y') # Pauli-Y Z = Literal(pkg, 'Z') # Pauli-Z H = Literal(pkg, 'H') # Hadamard # PASS: either a blank spot or continuation of a wire in a quantum circuit. # Can be used when initializing the circuit with a list of lists -- these PASS elements # are subsequently removed and turned into empty spots of the quantum # circuit tensor. PASS = Literal(pkg, 'PASS') # For positive X eigenstate PLUS = Literal(pkg, 'PLUS', {LATEX: '+', STRING: '+'}) # For negative X eigenstate MINUS = Literal(pkg, 'MINUS', {LATEX: '-', STRING: '-'}) ket0 = Ket(zero) ket1 = Ket(one)