示例#1
0
def ms(rads: float) -> ops.XXPowGate:
    """The Mølmer–Sørensen gate, a native two-qubit operation in ion traps.

    A rotation around the XX axis in the two-qubit bloch sphere.

    The gate implements the following unitary:

        exp(-i t XX) = [ cos(t)   0        0       -isin(t)]
                       [ 0        cos(t)  -isin(t)  0      ]
                       [ 0       -isin(t)  cos(t)   0      ]
                       [-isin(t)  0        0        cos(t) ]

    Args:
        rads: The rotation angle in radians.

    Returns:
        Mølmer–Sørensen gate rotating by the desired amount.
    """
    return ops.XXPowGate(exponent=rads * 2 / np.pi, global_shift=-0.5)
示例#2
0
def _translate_two_qubit_braket_instruction_to_cirq_operation(
    instr: Instruction, ) -> List["cirq.Operation"]:
    """Converts the two-qubit braket instruction to Cirq.

    Args:
        instr: Two-qubit Braket instruction to convert.

    Raises:
        ValueError: If the instruction cannot be converted to Cirq.
    """
    qubits = [LineQubit(int(qubit)) for qubit in instr.target]
    gate = instr.operator

    # Two-qubit non-parameterized gates.
    if isinstance(gate, braket_gates.CNot):
        return [cirq_ops.CNOT.on(*qubits)]

    elif isinstance(gate, braket_gates.Swap):
        return [cirq_ops.SWAP.on(*qubits)]
    elif isinstance(gate, braket_gates.ISwap):
        return [cirq_ops.ISWAP.on(*qubits)]
    elif isinstance(gate, braket_gates.CZ):
        return [cirq_ops.CZ.on(*qubits)]
    elif isinstance(gate, braket_gates.CY):
        return [
            cirq_ops.S.on(qubits[1])**-1,
            cirq_ops.CNOT.on(*qubits),
            cirq_ops.S.on(qubits[1]),
        ]

    # Two-qubit parameterized gates.
    elif isinstance(gate, braket_gates.PSwap):
        raise ValueError  # TODO.
    elif isinstance(gate, braket_gates.CPhaseShift):
        return [cirq_ops.CZ.on(*qubits)**(gate.angle / np.pi)]
    elif isinstance(gate, braket_gates.CPhaseShift00):
        raise ValueError  # TODO.
    elif isinstance(gate, braket_gates.CPhaseShift01):
        raise ValueError  # TODO.
    elif isinstance(gate, braket_gates.CPhaseShift10):
        raise ValueError  # TODO.
    elif isinstance(gate, braket_gates.XX):
        return [
            cirq_ops.XXPowGate(exponent=gate.angle / np.pi,
                               global_shift=-0.5).on(*qubits)
        ]
    elif isinstance(gate, braket_gates.YY):
        return [
            cirq_ops.YYPowGate(exponent=gate.angle / np.pi,
                               global_shift=-0.5).on(*qubits)
        ]
    elif isinstance(gate, braket_gates.ZZ):
        return [
            cirq_ops.ZZPowGate(exponent=gate.angle / np.pi,
                               global_shift=-0.5).on(*qubits)
        ]
    elif isinstance(gate, braket_gates.XY):
        return [cirq_ops.ISwapPowGate(exponent=gate.angle / np.pi).on(*qubits)]

    else:
        raise ValueError(
            f"Unable to convert the instruction {instr} to Cirq. If you think "
            "this is a bug, you can open an issue on the Mitiq GitHub at "
            "https://github.com/unitaryfund/mitiq.")
示例#3
0
    cirq_circuit = Circuit(uncommon_gate.on(LineQubit(0)))
    test_circuit = from_braket(to_braket(cirq_circuit))
    testing.assert_allclose_up_to_global_phase(
        protocols.unitary(test_circuit),
        protocols.unitary(cirq_circuit),
        atol=1e-7,
    )


@pytest.mark.parametrize(
    "common_gate",
    [
        ops.CNOT,
        ops.CZ,
        ops.ISWAP,
        ops.XXPowGate(exponent=-0.2),
        ops.YYPowGate(exponent=0.3),
        ops.ZZPowGate(exponent=-0.1),
    ],
)
def test_to_from_braket_common_two_qubit_gates(common_gate):
    """These gates should stay the same (i.e., not get decomposed) when
    converting Cirq -> Braket -> Cirq.
    """
    cirq_circuit = Circuit(common_gate.on(*LineQubit.range(2)))
    test_circuit = from_braket(to_braket(cirq_circuit))
    testing.assert_allclose_up_to_global_phase(
        protocols.unitary(test_circuit),
        protocols.unitary(cirq_circuit),
        atol=1e-7,
    )
示例#4
0
def _translate_two_qubit_braket_instruction_to_cirq_operation(
    instr: Instruction,
) -> List["cirq.Operation"]:
    """Converts the two-qubit braket instruction to Cirq.

    Args:
        instr: Two-qubit Braket instruction to convert.

    Raises:
        ValueError: If the instruction cannot be converted to Cirq.
    """
    qubits = [LineQubit(int(qubit)) for qubit in instr.target]
    gate = instr.operator

    # Two-qubit non-parameterized gates.
    if isinstance(gate, braket_gates.CNot):
        return [cirq_ops.CNOT.on(*qubits)]

    elif isinstance(gate, braket_gates.Swap):
        return [cirq_ops.SWAP.on(*qubits)]
    elif isinstance(gate, braket_gates.ISwap):
        return [cirq_ops.ISWAP.on(*qubits)]
    elif isinstance(gate, braket_gates.CZ):
        return [cirq_ops.CZ.on(*qubits)]
    elif isinstance(gate, braket_gates.CY):
        return [
            cirq_ops.S.on(qubits[1]) ** -1,
            cirq_ops.CNOT.on(*qubits),
            cirq_ops.S.on(qubits[1]),
        ]

    # Two-qubit parameterized gates.
    elif isinstance(gate, braket_gates.CPhaseShift):
        return [cirq_ops.CZ.on(*qubits) ** (gate.angle / np.pi)]
    elif isinstance(gate, braket_gates.CPhaseShift00):
        return [
            cirq_ops.XX(*qubits),
            cirq_ops.CZ.on(*qubits) ** (gate.angle / np.pi),
            cirq_ops.XX(*qubits),
        ]
    elif isinstance(gate, braket_gates.CPhaseShift01):
        return [
            cirq_ops.X(qubits[0]),
            cirq_ops.CZ.on(*qubits) ** (gate.angle / np.pi),
            cirq_ops.X(qubits[0]),
        ]
    elif isinstance(gate, braket_gates.CPhaseShift10):
        return [
            cirq_ops.X(qubits[1]),
            cirq_ops.CZ.on(*qubits) ** (gate.angle / np.pi),
            cirq_ops.X(qubits[1]),
        ]
    elif isinstance(gate, braket_gates.PSwap):
        return [
            cirq_ops.SWAP.on(*qubits),
            cirq_ops.CNOT.on(*qubits),
            cirq_ops.Z.on(qubits[1]) ** (gate.angle / np.pi),
            cirq_ops.CNOT.on(*qubits),
        ]
    elif isinstance(gate, braket_gates.XX):
        return [
            cirq_ops.XXPowGate(
                exponent=gate.angle / np.pi, global_shift=-0.5
            ).on(*qubits)
        ]
    elif isinstance(gate, braket_gates.YY):
        return [
            cirq_ops.YYPowGate(
                exponent=gate.angle / np.pi, global_shift=-0.5
            ).on(*qubits)
        ]
    elif isinstance(gate, braket_gates.ZZ):
        return [
            cirq_ops.ZZPowGate(
                exponent=gate.angle / np.pi, global_shift=-0.5
            ).on(*qubits)
        ]
    elif isinstance(gate, braket_gates.XY):
        return [cirq_ops.ISwapPowGate(exponent=gate.angle / np.pi).on(*qubits)]

    else:
        _raise_braket_to_cirq_error(instr)