LogicalQ.Logical ================ .. py:module:: LogicalQ.Logical Classes ------- .. autoapisummary:: LogicalQ.Logical.LogicalCircuit LogicalQ.Logical.LogicalQubit LogicalQ.Logical.LogicalRegister LogicalQ.Logical.LogicalStatevector LogicalQ.Logical.LogicalDensityMatrix Functions --------- .. autoapisummary:: LogicalQ.Logical.logical_state_fidelity Module Contents --------------- .. py:class:: LogicalCircuit(n_logical_qubits, label, stabilizer_tableau, name = None) Bases: :py:obj:`qiskit.QuantumCircuit` Core LogicalQ representation of a logical quantum circuit. .. py:attribute:: n_logical_qubits .. py:attribute:: stabilizer_tableau .. py:attribute:: n_stabilizers .. py:attribute:: label .. py:attribute:: n_physical_qubits .. py:attribute:: n_ancilla_qubits .. py:attribute:: n_measure_qubits .. py:attribute:: flagged_stabilizers_1 :value: [] .. py:attribute:: flagged_stabilizers_2 :value: [] .. py:attribute:: x_stabilizers :value: [] .. py:attribute:: z_stabilizers :value: [] .. py:attribute:: qed_cycle_indices_initial .. py:attribute:: qed_cycle_indices_final .. py:attribute:: qec_cycle_indices_initial .. py:attribute:: qec_cycle_indices_final .. py:attribute:: logical_qregs :value: [] .. py:attribute:: ancilla_qregs :value: [] .. py:attribute:: logical_op_qregs :value: [] .. py:attribute:: enc_verif_cregs :value: [] .. py:attribute:: curr_syndrome_cregs :value: [] .. py:attribute:: prev_syndrome_cregs :value: [] .. py:attribute:: flagged_syndrome_diff_cregs :value: [] .. py:attribute:: unflagged_syndrome_diff_cregs :value: [] .. py:attribute:: pauli_frame_cregs :value: [] .. py:attribute:: logical_op_meas_cregs :value: [] .. py:attribute:: final_measurement_cregs :value: [] .. py:attribute:: qreg_lists .. py:attribute:: creg_lists .. py:attribute:: output_creg .. py:attribute:: cbit_setter_qreg .. py:attribute:: data_without_qec .. py:attribute:: data_without_qed .. py:method:: from_physical_circuit(physical_circuit, label, stabilizer_tableau, name = None, max_iterations = 1) :classmethod: Construct a LogicalCircuit from a physical qiskit circuit. :param physical_circuit: The QuantumCircuit to construct from. :param label: The QECC label. :param stabilizer_tableau: The set of stabilizers for the QECC. :param name: An optional name for the circuit. :param max_iterations: Number of times, to attempt to encod qubits. :returns: The LogicalCircuit constructed from the physical. .. py:method:: add_logical_qubits(logical_qubit_count) Add logical qubit(s) to the LogicalCircuit. :param logical_qubit_count: The number of logical qubits to add. .. py:method:: group_stabilizers() Generate the stabilizers for the code. .. py:method:: generate_code() Generate the encoding circuit and logical operators for the selected tableau. .. py:method:: encode(*qubits, max_iterations = 1, initial_states = None) Prepare logical qubit(s) in the specified initial state. :param qubits: Qubits to encode. :param max_iterations: Maximum number of times, to try to encode data. :param initial_states: Initial states to encode in each qubit. :returns: True, always :rtype: :py:type:`bool` .. py:method:: reset_ancillas(logical_qubit_indices = None) Reset all ancillas associated with specified logical qubits. :param logical_qubit_indices: Indices of logical qubits to reset. If None, then reset all. .. py:method:: steane_flagged_circuit1(logical_qubit_indices) Measure first set of flagged syndromes for the Steane code. .. py:method:: steane_flagged_circuit2(logical_qubit_indices) Measure second set of flagged syndromes for the Steane code. .. py:method:: measure_stabilizers(logical_qubit_indices = None, stabilizer_indices = None) Measure specified stabilizers to the circuit as controlled Pauli operators. :param logical_qubit_indices: Indices of logical qubits for which to measure stabilizers. :param stabilizer_indices: Indices of stabilizers to measure. .. py:method:: measure_syndrome_diff(logical_qubit_indices = None, stabilizer_indices = None, flagged = False, steane_flag_1 = False, steane_flag_2 = False) Measure flagged or unflagged syndrome differences for specified logical qubits and stabilizers. :param logical_qubit_indices: Logical qubits for which to measure indices. :param stabilizer_indices: Stabilizers for which to measure indices. :param flagged: Whether to measure flagged or unflagged differences. :param steane_flag_1: Whether to measure the first Steane code syndrome. Takes priority over `steane_flag_2`. :param steane_flag_2: Whether to measure the second Steane code syndrome. Ignored if `steane_flag_1` is True. .. py:method:: optimize_qec_cycle_indices(logical_qubit_indices = None, constraint_model = None, ignore_existing_qec = False, clear_existing_qec = False) Compute optimal QEC cycle indices. :param logical_qubit_indices: Logical qubits for which to compute optimal QEC cycle indices. :param constraint_model: Constraint model, i.e., dictionary of gadget costs for the circuit. :param ignore_existing_qec: Whether to ignore QEC-related parameters in the constraint model. :param clear_existing_qec: Whether to remove existing QEC cycles. :returns: Dictionary with optimal QEC cycle indices for each requested qubit. .. py:method:: insert_qec_cycles(logical_qubit_indices = None, qec_cycle_indices = None, clear_existing_qec = False) Insert QEC cycles at specified indices in the circuit data. :param logical_qubit_indices: Logical qubits for which to insert QEC cycles. :param qec_cycle_indices: Indices at which to insert QEC cycles for each logical qubit. :param clear_existing_qec: Whether to clear the existing QEC cycles. :returns: Original circuit data and data after appending QEC cycles. .. py:method:: append_qed_cycle(logical_qubit_indices = None, perform_flagged_syndrome_measurements = True) Append a QED cycle to the end of the circuit. :param logical_qubit_indices: Logical qubits for which to add QED cycles. :returns: Qubits and indices with QED cycles, before and after appending. .. py:method:: append_qec_cycle(logical_qubit_indices = None, perform_flagged_syndrome_measurements = True) Append a QEC cycle to the end of the circuit. :param logical_qubit_indices: Logical qubits for which to add QEC cycles. :returns: Qubits and indices with QEC cycles, before and after appending. .. py:method:: clear_qec_cycles(logical_qubit_indices = None, qec_cycle_indices = None) Clear QEC cycles (either specified or all) on specified logical qubits. :param logical_qubit_indices: Logical qubits from which to clear QEC cycles. Clears all if :py:type:`None`. :param qec_cycle_indices: QEC cycles to clear. Clears all if :py:type:`None` :returns: This method is not yet implemented. .. py:method:: apply_decoding(logical_qubit_indices, stabilizer_indices, with_flagged) Decode the syndrome measurements to determine the correction to apply. :param logical_qubit_indices: Logical qubits to apply decoding to. :param stabilizer_indices: Stabilizers for which to decode syndromes. :param with_flagged: Whether to decode with flagged or unflagged syndrome differences. .. py:method:: measure(logical_qubit_indices, cbit_indices, with_error_correction = True) Measure specified qubits (in the Z basis) into classical bits. :param logical_qubit_indices: Logical qubits to measure. :param cbit_indices: Classical bits in which to record measurements. :param with_error_correction: Whether to apply QEC. :raises ValueError: if `logical_qubit_indices` or `cbit_indices` is not an iterable or if number of qubits and cbits does not match. .. py:method:: measure_all(inplace = True, with_error_correction = True) Add measurements to all qubits. :param inplace: Whether to perform measurements on this circuit or a copy. If `False`, a new circuit is returned. :param with_error_correction: Whether to perform measurements with QEC. :returns: Circuit with measurements, if `inplace = False`. .. py:method:: remove_final_measurements(inplace = False) Remove final measurements from circuit. :param inplace: Whether to remove measurements in place, i.e., for this circuit (not supported). :raises NotImplementedError: if in-place measurement is attempted. :returns: The circuit without measurements. .. py:method:: get_logical_counts(physical_counts, logical_qubit_indices = None) Get logical counts from physical counts. :param physical_counts: Physical counts to convert to logical counts. :param logical_qubit_indices: Logical qubits to get counts for. If `None`, then get counts for all. :returns: Logical qubit counts. .. py:method:: h(*targets, method='Coherent_Feedback') Logical Hadamard gate .. py:method:: x(*targets) Logical PauliX gate .. py:method:: y(*targets) Logical PauliY gate .. py:method:: z(*targets) Logical PauliZ gate .. py:method:: s(*targets, method='Coherent_Feedback') Logical S gate Definition: [1 0] [0 i] .. py:method:: sdg(*targets, method='Coherent_Feedback') Logical S^dagger gate Definition: [1 0] [0 -i] .. py:method:: t(*targets, method='Coherent_Feedback') Logical T gate Definition: [1 0 ] [0 e^(ipi/4)] .. py:method:: tdg(*targets, method='Coherent_Feedback') Logical T^dagger gate Definition: [1 0 ] [0 e^(-ipi/4)] .. py:method:: cx(control, *_targets, method='Ancilla_Assisted') Logical Controlled-PauliX gate .. py:method:: cz(control, *_targets, method='Ancilla_Assisted') Logical Controlled-PauliZ gate .. py:method:: cy(control, *_targets, method='Ancilla_Assisted') Logical Controlled-PauliY gate .. py:method:: mcmt(gate, controls, targets) Logical Multi-Control Multi-Target gate .. py:method:: rx(theta, targets, method='S-K', depth=10, recursion_degree=1, box=True) Logical Single-Target Rotation Gate method = "LCU" -> linear combination of unitaries or "S-K" -> solovay-kitaev algorithm or "OAA" -> oblivious amplitude amplification theta in radians .. py:method:: ry(theta, targets, method='S-K', depth=10, recursion_degree=1, box=True) Logical Single-Target Rotation Gate method = "LCU" or "S-K" theta in radians .. py:method:: rz(theta, targets, method='S-K', depth=10, recursion_degree=1, box=True) Logical Single-Target Rotation Gate method = "LCU" or "S-K" theta in radians .. py:method:: rxx(theta, targets, method='S-K', depth=10, recursion_degree=1, box=True) Apply :class:`~qiskit.circuit.library.RXXGate`. For the full matrix form of this gate, see the underlying gate documentation. :param theta: The angle of the rotation. :param qubit1: The qubit(s) to apply the gate to. :param qubit2: The qubit(s) to apply the gate to. :returns: A handle to the instructions created. .. py:method:: ryy(theta, targets, method='S-K', depth=10, recursion_degree=1, box=True) Apply :class:`~qiskit.circuit.library.RYYGate`. For the full matrix form of this gate, see the underlying gate documentation. :param theta: The rotation angle of the gate. :param qubit1: The qubit(s) to apply the gate to. :param qubit2: The qubit(s) to apply the gate to. :returns: A handle to the instructions created. .. py:method:: rzz(theta, targets, method='S-K', depth=10, recursion_degree=1, box=True) Apply :class:`~qiskit.circuit.library.RZZGate`. For the full matrix form of this gate, see the underlying gate documentation. :param theta: The rotation angle of the gate. :param qubit1: The qubit(s) to apply the gate to. :param qubit2: The qubit(s) to apply the gate to. :returns: A handle to the instructions created. .. py:method:: append_sk_decomposition(circuit, targets, label='U', depth=10, recursion_degree=1, box=False, return_subcircuit=False) .. py:method:: r(axis, targets, theta=0, label='R', depth=10, recursion_degree=1, box=True, method='S-K') Apply :class:`~qiskit.circuit.library.RGate`. For the full matrix form of this gate, see the underlying gate documentation. :param theta: The angle of the rotation. :param phi: The angle of the axis of rotation in the x-y plane. :param qubit: The qubit(s) to apply the gate to. :returns: A handle to the instructions created. .. py:method:: append(instruction, qargs=None, cargs=None, copy=True) Append one or more instructions to the end of the circuit, modifying the circuit in place. The ``qargs`` and ``cargs`` will be expanded and broadcast according to the rules of the given :class:`~.circuit.Instruction`, and any non-:class:`.Bit` specifiers (such as integer indices) will be resolved into the relevant instances. If a :class:`.CircuitInstruction` is given, it will be unwrapped, verified in the context of this circuit, and a new object will be appended to the circuit. In this case, you may not pass ``qargs`` or ``cargs`` separately. :param instruction: :class:`~.circuit.Instruction` instance to append, or a :class:`.CircuitInstruction` with all its context. :param qargs: specifiers of the :class:`~.circuit.Qubit`\ s to attach instruction to. :param cargs: specifiers of the :class:`.Clbit`\ s to attach instruction to. :param copy: if ``True`` (the default), then the incoming ``instruction`` is copied before adding it to the circuit if it contains symbolic parameters, so it can be safely mutated without affecting other circuits the same instruction might be in. If you are sure this instruction will not be in other circuits, you can set this ``False`` for a small speedup. :returns: a handle to the :class:`.CircuitInstruction`\ s that were actually added to the circuit. :rtype: qiskit.circuit.InstructionSet :raises CircuitError: if the operation passed is not an instance of :class:`~.circuit.Instruction` . .. py:method:: add_error(l_ind, p_ind, error_type) .. py:method:: set_cbit(cbit, value) .. py:method:: cbit_not(cbit) .. py:method:: cbit_and(cbits, values) .. py:method:: cbit_xor(cbits) .. py:method:: draw(output=None, scale=None, filename=None, style=None, interactive=False, plot_barriers=True, reverse_bits=None, justify=None, vertical_compression='medium', idle_wires=None, with_layout=True, fold=None, ax=None, initial_state=False, cregbundle=None, wire_order=None, expr_len=30, fold_qec=True, fold_logicalop=True) LogicalCircuit drawer based on Qiskit circuit drawer .. py:class:: LogicalQubit(regs=None, qregs=None, cregs=None) Bases: :py:obj:`list` A single LogicalQubit .. py:attribute:: _data :value: [] .. py:attribute:: qregs :value: [] .. py:attribute:: cregs :value: [] .. py:class:: LogicalRegister(qregs=None, cregs=None) Bases: :py:obj:`list` A register containing LogicalQubits .. py:attribute:: qregs :value: None .. py:attribute:: cregs :value: None .. py:class:: LogicalStatevector(data, logical_circuit = None, n_logical_qubits = None, label = None, stabilizer_tableau = None, dims = None) Bases: :py:obj:`qiskit.quantum_info.Statevector` A LogicalStatevector .. py:attribute:: _logical_decomposition :value: None .. py:method:: from_counts(counts, n_logical_qubits, label, stabilizer_tableau, basis = 'physical') :classmethod: Construct a LogicalStatevector from measurement counts. :param counts: The set of counts measured from a circuit execution. :type counts: dict :param n_logical_qubits: The number of logical qubits. :type n_logical_qubits: int :param label: The quantum error correction code [[n,k,d]] (given as a tuple). :type label: tuple :param stabilizer_tableau: The set of stabilizers for the QECC. :type stabilizer_tableau: Iterable[str] :param basis: The basis in which each respective count's vector is given, physical or logical. :type basis: str :returns: The normalized LogicalStatevector constructed from the counts. :raises ValueError: if the counts format could not be parsed or if `basis` is invalid. .. py:method:: from_basis_str(basis_str, n_logical_qubits, label, stabilizer_tableau, basis='physical') :classmethod: Construct a LogicalStatevector, an element of the logical computational basis, from a basis string. :param basis_str: Either a binary bitstring or its hex equivalent to identify the basis. :type basis_str: str :param n_logical_qubits: Number of logical qubits. :type n_logical_qubits: int :param label: The label of the quantum error correction code [[n,k,d]] (as a tuple). :type label: tuple :param stabilizer_tableau: The set of stabilizers for the QECC. :type stabilizer_tableau: Iterable[str] :param basis: The basis in which each respective count's vector is given, physical or logical. :type basis: str :returns: The LogicalStatevector of the given basis state. :rtype: :py:class:`~LogicalQ.Logical.LogicalStatevector` :raises ValueError: if the `basis_str` could not be parsed due to improper format. .. py:property:: logical_decomposition Give a decomposition of a LogicalStatevector into the logical basis. :param atol: Tolerance within which to set probability amplitude to zero. :type atol: float :returns: The set of coefficients :math:`\alpha_i, \delta`, where :math:`|\psi\rangle = \sum_{x=0}^{2^n - 1}\alpha_x|x\rangle + \delta|\psi^\perp\rangle`, where :math:`|\psi^\perp\rangle` is the component of the state vector not in the codespace. Note that coefficients are returned in ascending order of value, e.g., 000, 001, 010, 011, 100, 101, etc. :rtype: :py:type:`np.ndarray` .. py:method:: __array__(basis='physical', dtype=None, copy=_numpy_compat.COPY_ONLY_IF_NEEDED) Return an array representation of the object. :param basis: The basis, physical or logical, in which to represent the vector. :type basis: str :param dtype: The desired data-type for the array. :type dtype: data-type :param copy: If `True`, then the array data is copied :type copy: bool :returns: The :py:meth:`~LogicalQ.Logical.LogicalStatevector.logical_decomposition` if basis is logical and the statevector data otherwise. :rtype: :py:type:`np.ndarray` :raises ValueError: if the basis is invalid. .. py:method:: __repr__(basis='logical') Return a string representation of the statevector. :param basis: The basis, logical or physical, in which to return the array. :type basis: str :returns: String representation of the statevector in the requested basis. :rtype: :py:type:`np.ndarray` :raises ValueError: if the basis is invalid. .. py:method:: draw(output=None) Return a visual representation of the statevector in the logical basis. :param output: The method in which to draw. Valid choices are `text`, `latex`, and `latex_source`. :type output: str :returns: String or LaTeX representation of the statevector. :rtype: :py:type:`str` or :py:class:`IPython.display.Latex` :raises ValueError: if the draw method is invalid. .. py:class:: LogicalDensityMatrix(data, n_logical_qubits=None, label=None, stabilizer_tableau=None, dims=None) Bases: :py:obj:`qiskit.quantum_info.DensityMatrix` A LogicalDensityMatrix .. py:attribute:: _logical_decomposition :value: None .. py:property:: logical_decomposition :abstractmethod: .. py:method:: __repr__(basis='logical') .. py:function:: logical_state_fidelity(state1, state2)