def _(xx: XX, parameters): phi = parameters[0] return gates.XX(-phi) if xx.inverse else gates.XX(phi)
def _translate_two_qubit_cirq_operation_to_braket_instruction( op: "cirq.Operation", ) -> List[Instruction]: """Translates a two-qubit Cirq operation to a (sequence of) Braket instruction(s) according to the following rules: 1. Attempts to find a "standard translation" from Cirq to Braket. - e.g., checks if `op` is a CNOT and, if so, returns the Braket CNOT. 2. If (1) is not successful, performs a KAK decomposition of the unitary of `op` to obtain a circuit ──A1──X^0.5───@───X^a───X──────────────────@───B1─── │ │ │ ──A2──────────X───Y^b───@───X^-0.5───Z^c───X───B2──── where A1, A2, B1, and B2 are arbitrary single-qubit unitaries and a, b, c are floats. Args: op: Two-qubit Cirq operation to translate. """ # Translate qubit indices. q1, q2 = [qubit.x for qubit in op.qubits] # Check common two-qubit gates. if isinstance(op.gate, cirq_ops.CNotPowGate) and np.isclose( abs(op.gate.exponent), 1.0): return [Instruction(braket_gates.CNot(), [q1, q2])] elif isinstance(op.gate, cirq_ops.CZPowGate) and np.isclose( abs(op.gate.exponent), 1.0): return [Instruction(braket_gates.CZ(), [q1, q2])] elif isinstance(op.gate, cirq_ops.ISwapPowGate) and np.isclose( op.gate.exponent, 1.0): return [Instruction(braket_gates.ISwap(), [q1, q2])] elif isinstance(op.gate, cirq_ops.XXPowGate): return [ Instruction(braket_gates.XX(op.gate.exponent * np.pi), [q1, q2]) ] elif isinstance(op.gate, cirq_ops.YYPowGate): return [ Instruction(braket_gates.YY(op.gate.exponent * np.pi), [q1, q2]) ] elif isinstance(op.gate, cirq_ops.ZZPowGate): return [ Instruction(braket_gates.ZZ(op.gate.exponent * np.pi), [q1, q2]) ] # Arbitrary two-qubit unitary decomposition. kak = kak_decomposition(protocols.unitary(op)) A1, A2 = kak.single_qubit_operations_before x, y, z = kak.interaction_coefficients a = x * -2 / np.pi + 0.5 b = y * -2 / np.pi + 0.5 c = z * -2 / np.pi + 0.5 B1, B2 = kak.single_qubit_operations_after return [ *_translate_one_qubit_cirq_operation_to_braket_instruction(A1, q1), *_translate_one_qubit_cirq_operation_to_braket_instruction(A2, q2), Instruction(braket_gates.Rx(0.5 * np.pi), q1), Instruction(braket_gates.CNot(), [q1, q2]), Instruction(braket_gates.Rx(a * np.pi), q1), Instruction(braket_gates.Ry(b * np.pi), q2), Instruction(braket_gates.CNot(), [q2, q1]), Instruction(braket_gates.Rx(-0.5 * np.pi), q2), Instruction(braket_gates.Rz(c * np.pi), q2), Instruction(braket_gates.CNot(), [q1, q2]), *_translate_one_qubit_cirq_operation_to_braket_instruction(B1, q1), *_translate_one_qubit_cirq_operation_to_braket_instruction(B2, q2), ]
(Circuit().iswap(0, 1), gates.ISwap().to_matrix()), (Circuit().pswap(1, 0, 0.15), gates.PSwap(0.15).to_matrix()), (Circuit().pswap(0, 1, 0.15), gates.PSwap(0.15).to_matrix()), (Circuit().xy(1, 0, 0.15), gates.XY(0.15).to_matrix()), (Circuit().xy(0, 1, 0.15), gates.XY(0.15).to_matrix()), (Circuit().cphaseshift(1, 0, 0.15), gates.CPhaseShift(0.15).to_matrix()), (Circuit().cphaseshift00(1, 0, 0.15), gates.CPhaseShift00(0.15).to_matrix()), (Circuit().cphaseshift01(1, 0, 0.15), gates.CPhaseShift01(0.15).to_matrix()), (Circuit().cphaseshift10(1, 0, 0.15), gates.CPhaseShift10(0.15).to_matrix()), (Circuit().cy(1, 0), gates.CY().to_matrix()), (Circuit().cz(1, 0), gates.CZ().to_matrix()), (Circuit().xx(1, 0, 0.15), gates.XX(0.15).to_matrix()), (Circuit().yy(1, 0, 0.15), gates.YY(0.15).to_matrix()), (Circuit().zz(1, 0, 0.15), gates.ZZ(0.15).to_matrix()), (Circuit().ccnot(2, 1, 0), gates.CCNot().to_matrix()), ( Circuit().ccnot(2, 1, 0).add_result_type( ResultType.Expectation(observable=Observable.Y(), target=[1])), gates.CCNot().to_matrix(), ), (Circuit().ccnot(1, 2, 0), gates.CCNot().to_matrix()), (Circuit().cswap(2, 1, 0), gates.CSwap().to_matrix()), (Circuit().cswap(2, 0, 1), gates.CSwap().to_matrix()), (Circuit().h(1), np.kron(gates.H().to_matrix(), np.eye(2))), (Circuit().x(1).i(2), np.kron(np.eye(2), np.kron(gates.X().to_matrix(), np.eye(2)))), (