From ca25c42311fb319215c001986ff5213eaa5fc409 Mon Sep 17 00:00:00 2001 From: Evan Peters Date: Sun, 24 Oct 2021 21:41:23 -0400 Subject: [PATCH] Qcircuit exponent (#4593) Currently the `cirq.contrib.circuit_to_latex_using_qcircuit` utility doesn't handle exponents for multiqubit gates properly. For example, converting `cirq.ISWAP(q0, q1) ** 0.5` outputs the qcircuit source ``` \Qcircuit @R=1em @C=0.75em { \\ &\lstick{\text{0}}& \qw&\multigate{1}{\text{ISWAP}^{0.5}}^0.5 \qw&\qw\\ &\lstick{\text{1}}& \qw&\ghost{\text{ISWAP}^{0.5}}^0.5 \qw&\qw\\ \\ } ``` which produces the diagram ![before](https://user-images.githubusercontent.com/14928221/138499001-8fe6c0d3-f20a-43e3-be87-88e7650d93b2.png) The `0.5` exponent is getting duplicated and put in the wrong place. This PR resolves this issue by bypassing any additional processing by `Circuit.to_text_diagram_drawer` by just hardcoding `exponent=1` into `CircuitDiagramInfo`. This results in the correct output, ``` \Qcircuit @R=1em @C=0.75em { \\ &\lstick{\text{0}}& \qw&\multigate{1}{\text{ISWAP}^{0.5}} \qw&\qw\\ &\lstick{\text{1}}& \qw&\ghost{\text{ISWAP}^{0.5}} \qw&\qw\\ \\ } ``` and the diagram ![after](https://user-images.githubusercontent.com/14928221/138499507-d86a781d-5013-4871-b9e5-46f364f032c0.png) --- .../cirq/contrib/qcircuit/qcircuit_diagram_info.py | 5 ++--- .../contrib/qcircuit/qcircuit_diagram_info_test.py | 2 +- cirq-core/cirq/contrib/qcircuit/qcircuit_test.py | 14 ++++++++++++++ 3 files changed, 17 insertions(+), 4 deletions(-) diff --git a/cirq-core/cirq/contrib/qcircuit/qcircuit_diagram_info.py b/cirq-core/cirq/contrib/qcircuit/qcircuit_diagram_info.py index d9e75d00aa1..719d3fc1a3f 100644 --- a/cirq-core/cirq/contrib/qcircuit/qcircuit_diagram_info.py +++ b/cirq-core/cirq/contrib/qcircuit/qcircuit_diagram_info.py @@ -98,9 +98,8 @@ def multigate_qcircuit_diagram_info( assert args.qubit_map is not None assert args.known_qubits is not None symbols = tuple(box if (args.qubit_map[q] == min_index) else ghost for q in args.known_qubits) - return protocols.CircuitDiagramInfo( - symbols, exponent=1 if info is None else info.exponent, connected=False - ) + # Force exponent=1 to defer to exponent formatting given above. + return protocols.CircuitDiagramInfo(symbols, connected=False) def fallback_qcircuit_diagram_info( diff --git a/cirq-core/cirq/contrib/qcircuit/qcircuit_diagram_info_test.py b/cirq-core/cirq/contrib/qcircuit/qcircuit_diagram_info_test.py index e3e4e414d0c..f63fc9bff64 100644 --- a/cirq-core/cirq/contrib/qcircuit/qcircuit_diagram_info_test.py +++ b/cirq-core/cirq/contrib/qcircuit/qcircuit_diagram_info_test.py @@ -32,7 +32,7 @@ def test_get_qcircuit_diagram_info(): actual_info = ccq.get_qcircuit_diagram_info(op, args) name = r'{\text{SWAP}^{0.5}}' expected_info = cirq.CircuitDiagramInfo( - (r'\multigate{1}' + name, r'\ghost' + name), exponent=0.5, connected=False + (r'\multigate{1}' + name, r'\ghost' + name), exponent=1, connected=False ) assert actual_info == expected_info diff --git a/cirq-core/cirq/contrib/qcircuit/qcircuit_test.py b/cirq-core/cirq/contrib/qcircuit/qcircuit_test.py index 91a357c1553..9721280d5dd 100644 --- a/cirq-core/cirq/contrib/qcircuit/qcircuit_test.py +++ b/cirq-core/cirq/contrib/qcircuit/qcircuit_test.py @@ -155,3 +155,17 @@ def test_two_cx_diagram(): \\ }""".strip() assert_has_qcircuit_diagram(circuit, expected_diagram) + + +def test_sqrt_iswap_diagram(): + # test for proper rendering of ISWAP^{0.5} + q0, q1 = cirq.LineQubit.range(2) + circuit = cirq.Circuit(cirq.ISWAP(q0, q1) ** 0.5) + expected_diagram = r""" +\Qcircuit @R=1em @C=0.75em { + \\ + &\lstick{\text{0}}& \qw&\multigate{1}{\text{ISWAP}^{0.5}} \qw&\qw\\ + &\lstick{\text{1}}& \qw&\ghost{\text{ISWAP}^{0.5}} \qw&\qw\\ + \\ +}""".strip() + assert_has_qcircuit_diagram(circuit, expected_diagram)