Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add CZSWAP gate and optimize stim.PauliString.{after,before} #685

Merged
merged 9 commits into from
Jan 24, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
47 changes: 47 additions & 0 deletions doc/gates.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
- [CXSWAP](#CXSWAP)
- [CY](#CY)
- [CZ](#CZ)
- [CZSWAP](#CZSWAP)
- [ISWAP](#ISWAP)
- [ISWAP_DAG](#ISWAP_DAG)
- [SQRT_XX](#SQRT_XX)
Expand All @@ -36,6 +37,7 @@
- [SQRT_ZZ_DAG](#SQRT_ZZ_DAG)
- [SWAP](#SWAP)
- [SWAPCX](#SWAPCX)
- [SWAPCZ](#SWAPCZ)
- [XCX](#XCX)
- [XCY](#XCY)
- [XCZ](#XCZ)
Expand Down Expand Up @@ -1103,6 +1105,51 @@ Decomposition (into H, S, CX, M, R):
H 1


<a name="CZSWAP"></a>
### The 'CZSWAP' Gate

Alternate name: <a name="SWAPCZ"></a>`SWAPCZ`

A combination CZ-and-SWAP gate.
This gate is kak-equivalent to the iswap gate.

Parens Arguments:

This instruction takes no parens arguments.

Targets:

Qubit pairs to operate on.

Example:

CZSWAP 5 6
CZSWAP 42 43
CZSWAP 5 6 42 43

Stabilizer Generators:

X_ -> ZX
Z_ -> _Z
_X -> XZ
_Z -> Z_

Unitary Matrix (little endian):

[+1 , , , ]
[ , , +1 , ]
[ , +1 , , ]
[ , , , -1 ]

Decomposition (into H, S, CX, M, R):

# The following circuit is equivalent (up to global phase) to `CZSWAP 0 1`
H 0
CX 0 1
CX 1 0
H 1


<a name="ISWAP"></a>
### The 'ISWAP' Gate

Expand Down
2 changes: 1 addition & 1 deletion file_lists/benchmark_files
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
src/stim/benchmark_main.perf.cc
src/stim/benchmark_util.perf.cc
src/stim/circuit/circuit.perf.cc
src/stim/circuit/gate_data.perf.cc
src/stim/gates/gates.perf.cc
src/stim/io/measure_record_reader.perf.cc
src/stim/main_namespaced.perf.cc
src/stim/mem/simd_bit_table.perf.cc
Expand Down
2 changes: 1 addition & 1 deletion file_lists/python_api_files
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
src/stim/circuit/circuit.pybind.cc
src/stim/circuit/circuit_instruction.pybind.cc
src/stim/circuit/circuit_repeat_block.pybind.cc
src/stim/circuit/gate_data.pybind.cc
src/stim/circuit/gate_target.pybind.cc
src/stim/cmd/command_diagram.pybind.cc
src/stim/dem/detector_error_model.pybind.cc
src/stim/dem/detector_error_model_instruction.pybind.cc
src/stim/dem/detector_error_model_repeat_block.pybind.cc
src/stim/dem/detector_error_model_target.pybind.cc
src/stim/gates/gates.pybind.cc
src/stim/io/read_write.pybind.cc
src/stim/py/base.pybind.cc
src/stim/py/compiled_detector_sampler.pybind.cc
Expand Down
28 changes: 14 additions & 14 deletions file_lists/source_files_no_main
Original file line number Diff line number Diff line change
Expand Up @@ -3,20 +3,6 @@ src/stim/arg_parse.cc
src/stim/circuit/circuit.cc
src/stim/circuit/circuit_instruction.cc
src/stim/circuit/export_qasm.cc
src/stim/circuit/gate_data.cc
src/stim/circuit/gate_data_annotations.cc
src/stim/circuit/gate_data_blocks.cc
src/stim/circuit/gate_data_collapsing.cc
src/stim/circuit/gate_data_controlled.cc
src/stim/circuit/gate_data_hada.cc
src/stim/circuit/gate_data_heralded.cc
src/stim/circuit/gate_data_noisy.cc
src/stim/circuit/gate_data_pair_measure.cc
src/stim/circuit/gate_data_pauli.cc
src/stim/circuit/gate_data_period_3.cc
src/stim/circuit/gate_data_period_4.cc
src/stim/circuit/gate_data_pp.cc
src/stim/circuit/gate_data_swaps.cc
src/stim/circuit/gate_decomposition.cc
src/stim/circuit/gate_target.cc
src/stim/cmd/command_analyze_errors.cc
Expand Down Expand Up @@ -51,6 +37,20 @@ src/stim/diagram/lattice_map.cc
src/stim/diagram/timeline/timeline_3d_drawer.cc
src/stim/diagram/timeline/timeline_ascii_drawer.cc
src/stim/diagram/timeline/timeline_svg_drawer.cc
src/stim/gates/gate_data_annotations.cc
src/stim/gates/gate_data_blocks.cc
src/stim/gates/gate_data_collapsing.cc
src/stim/gates/gate_data_controlled.cc
src/stim/gates/gate_data_hada.cc
src/stim/gates/gate_data_heralded.cc
src/stim/gates/gate_data_noisy.cc
src/stim/gates/gate_data_pair_measure.cc
src/stim/gates/gate_data_pauli.cc
src/stim/gates/gate_data_period_3.cc
src/stim/gates/gate_data_period_4.cc
src/stim/gates/gate_data_pp.cc
src/stim/gates/gate_data_swaps.cc
src/stim/gates/gates.cc
src/stim/gen/circuit_gen_params.cc
src/stim/gen/gen_color_code.cc
src/stim/gen/gen_rep_code.cc
Expand Down
3 changes: 2 additions & 1 deletion file_lists/test_files
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@ src/stim.test.cc
src/stim/arg_parse.test.cc
src/stim/circuit/circuit.test.cc
src/stim/circuit/export_qasm.test.cc
src/stim/circuit/gate_data.test.cc
src/stim/circuit/gate_decomposition.test.cc
src/stim/circuit/gate_target.test.cc
src/stim/circuit/stabilizer_flow.test.cc
Expand All @@ -26,6 +25,7 @@ src/stim/diagram/json_obj.test.cc
src/stim/diagram/timeline/timeline_3d_drawer.test.cc
src/stim/diagram/timeline/timeline_ascii_drawer.test.cc
src/stim/diagram/timeline/timeline_svg_drawer.test.cc
src/stim/gates/gates.test.cc
src/stim/gen/circuit_gen_params.test.cc
src/stim/gen/gen_color_code.test.cc
src/stim/gen/gen_rep_code.test.cc
Expand Down Expand Up @@ -74,6 +74,7 @@ src/stim/stabilizers/conversions.test.cc
src/stim/stabilizers/flex_pauli_string.test.cc
src/stim/stabilizers/pauli_string.test.cc
src/stim/stabilizers/pauli_string_iter.test.cc
src/stim/stabilizers/pauli_string_ref.test.cc
src/stim/stabilizers/tableau.test.cc
src/stim/stabilizers/tableau_iter.test.cc
src/stim/str_util.test.cc
Expand Down
2 changes: 2 additions & 0 deletions glue/cirq/stimcirq/__init__.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
__version__ = '1.13.dev0'
from ._cirq_to_stim import cirq_circuit_to_stim_circuit
from ._cx_swap_gate import CXSwapGate
from ._cz_swap_gate import CZSwapGate
from ._det_annotation import DetAnnotation
from ._obs_annotation import CumulativeObservableAnnotation
from ._shift_coords_annotation import ShiftCoordsAnnotation
Expand All @@ -20,5 +21,6 @@
"SweepPauli": SweepPauli,
"TwoQubitAsymmetricDepolarizingChannel": TwoQubitAsymmetricDepolarizingChannel,
"CXSwapGate": CXSwapGate,
"CZSwapGate": CZSwapGate,
}
JSON_RESOLVER = JSON_RESOLVERS_DICT.get
46 changes: 46 additions & 0 deletions glue/cirq/stimcirq/_cz_swap_gate.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
from typing import Any, Dict, List

import cirq
import stim


@cirq.value_equality
class CZSwapGate(cirq.Gate):
"""Handles explaining stim's CZSWAP gates to cirq."""

def _num_qubits_(self) -> int:
return 2

def _circuit_diagram_info_(self, args: cirq.CircuitDiagramInfoArgs) -> List[str]:
return ['ZSWAP', 'ZSWAP']

def _value_equality_values_(self):
return ()

def _decompose_(self, qubits):
a, b = qubits
yield cirq.SWAP(a, b)
yield cirq.CZ(a, b)

def _stim_conversion_(self, edit_circuit: stim.Circuit, targets: List[int], **kwargs):
edit_circuit.append_operation('CZSWAP', targets)

def __pow__(self, power: int) -> 'CZSwapGate':
if power == +1:
return self
if power == -1:
return self
return NotImplemented

def __str__(self) -> str:
return 'CZSWAP'

def __repr__(self):
return f'stimcirq.CZSwapGate()'

@staticmethod
def _json_namespace_() -> str:
return ''

def _json_dict_(self) -> Dict[str, Any]:
return {}
72 changes: 72 additions & 0 deletions glue/cirq/stimcirq/_cz_swap_test.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
import cirq
import stim
import stimcirq


def test_stim_conversion():
a, b, c = cirq.LineQubit.range(3)

cirq_circuit = cirq.Circuit(
stimcirq.CZSwapGate().on(a, b),
stimcirq.CZSwapGate().on(b, c),
)
stim_circuit = stim.Circuit(
"""
CZSWAP 0 1
TICK
CZSWAP 1 2
TICK
"""
)
assert stimcirq.cirq_circuit_to_stim_circuit(cirq_circuit) == stim_circuit
assert stimcirq.stim_circuit_to_cirq_circuit(stim_circuit) == cirq_circuit


def test_diagram():
a, b = cirq.LineQubit.range(2)
cirq.testing.assert_has_diagram(
cirq.Circuit(
stimcirq.CZSwapGate()(a, b),
stimcirq.CZSwapGate()(a, b),
),
"""
0: ---ZSWAP---ZSWAP---
| |
1: ---ZSWAP---ZSWAP---
""",
use_unicode_characters=False,
)


def test_inverse():
a = stimcirq.CZSwapGate()
assert a**+1 == a
assert a**-1 == a


def test_repr():
val = stimcirq.CZSwapGate()
assert eval(repr(val), {"stimcirq": stimcirq}) == val


def test_equality():
eq = cirq.testing.EqualsTester()
eq.add_equality_group(stimcirq.CZSwapGate(), stimcirq.CZSwapGate())


def test_json_serialization():
a, b, d = cirq.LineQubit.range(3)
c = cirq.Circuit(
stimcirq.CZSwapGate()(a, b),
stimcirq.CZSwapGate()(b, d),
)
json = cirq.to_json(c)
c2 = cirq.read_json(json_text=json, resolvers=[*cirq.DEFAULT_RESOLVERS, stimcirq.JSON_RESOLVER])
assert c == c2


def test_json_backwards_compat_exact():
raw = stimcirq.CZSwapGate()
packed = '{\n "cirq_type": "CZSwapGate"\n}'
assert cirq.to_json(raw) == packed
assert cirq.read_json(json_text=packed, resolvers=[*cirq.DEFAULT_RESOLVERS, stimcirq.JSON_RESOLVER]) == raw
2 changes: 2 additions & 0 deletions glue/cirq/stimcirq/_stim_to_cirq.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
import stim

from ._cx_swap_gate import CXSwapGate
from ._cz_swap_gate import CZSwapGate
from ._det_annotation import DetAnnotation
from ._measure_and_or_reset_gate import MeasureAndOrResetGate
from ._obs_annotation import CumulativeObservableAnnotation
Expand Down Expand Up @@ -424,6 +425,7 @@ def handler(
measure=False, reset=True, basis='X', invert_measure=False, key=''
)
),
"CZSWAP": gate(CZSwapGate()),
"CXSWAP": gate(CXSwapGate(inverted=False)),
"SWAPCX": gate(CXSwapGate(inverted=True)),
"RY": gate(
Expand Down
2 changes: 1 addition & 1 deletion glue/javascript/tableau.js.cc
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
#include <emscripten/bind.h>

#include "common.js.h"
#include "stim/circuit/gate_data.h"
#include "stim/gates/gates.h"

using namespace stim;

Expand Down
3 changes: 1 addition & 2 deletions src/stim.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,6 @@
#include "stim/circuit/circuit.h"
#include "stim/circuit/circuit_instruction.h"
#include "stim/circuit/export_qasm.h"
#include "stim/circuit/gate_data.h"
#include "stim/circuit/gate_data_table.h"
#include "stim/circuit/gate_decomposition.h"
#include "stim/circuit/gate_target.h"
#include "stim/circuit/stabilizer_flow.h"
Expand Down Expand Up @@ -45,6 +43,7 @@
#include "stim/diagram/timeline/timeline_3d_drawer.h"
#include "stim/diagram/timeline/timeline_ascii_drawer.h"
#include "stim/diagram/timeline/timeline_svg_drawer.h"
#include "stim/gates/gates.h"
#include "stim/gen/circuit_gen_params.h"
#include "stim/gen/gen_color_code.h"
#include "stim/gen/gen_rep_code.h"
Expand Down
3 changes: 2 additions & 1 deletion src/stim/circuit/circuit.cc
Original file line number Diff line number Diff line change
Expand Up @@ -14,11 +14,12 @@

#include "stim/circuit/circuit.h"

#include <algorithm>
#include <string>
#include <utility>

#include "stim/circuit/gate_data.h"
#include "stim/circuit/gate_target.h"
#include "stim/gates/gates.h"
#include "stim/str_util.h"

using namespace stim;
Expand Down
2 changes: 1 addition & 1 deletion src/stim/circuit/circuit.h
Original file line number Diff line number Diff line change
Expand Up @@ -28,8 +28,8 @@
#include <vector>

#include "stim/circuit/circuit_instruction.h"
#include "stim/circuit/gate_data.h"
#include "stim/circuit/gate_target.h"
#include "stim/gates/gates.h"
#include "stim/mem/monotonic_buffer.h"
#include "stim/mem/span_ref.h"

Expand Down
1 change: 1 addition & 0 deletions src/stim/circuit/circuit.test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -1619,6 +1619,7 @@ Circuit stim::generate_test_circuit_with_all_operations() {
ISWAP_DAG 4 5
SWAP 6 7
SWAPCX 8 9
CZSWAP 10 11
SQRT_XX 0 1
SQRT_XX_DAG 2 3
SQRT_YY 4 5
Expand Down
2 changes: 1 addition & 1 deletion src/stim/circuit/circuit_instruction.cc
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@
#include <utility>

#include "stim/circuit/circuit.h"
#include "stim/circuit/gate_data.h"
#include "stim/circuit/gate_target.h"
#include "stim/gates/gates.h"

using namespace stim;

Expand Down
2 changes: 1 addition & 1 deletion src/stim/circuit/circuit_instruction.pybind.cc
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,8 @@

#include "stim/circuit/circuit_instruction.pybind.h"

#include "stim/circuit/gate_data.h"
#include "stim/circuit/gate_target.pybind.h"
#include "stim/gates/gates.h"
#include "stim/py/base.pybind.h"
#include "stim/str_util.h"

Expand Down
2 changes: 1 addition & 1 deletion src/stim/circuit/circuit_instruction.pybind.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,8 @@
#include <pybind11/pybind11.h>

#include "stim/circuit/circuit_instruction.h"
#include "stim/circuit/gate_data.h"
#include "stim/circuit/gate_target.h"
#include "stim/gates/gates.h"

namespace stim_pybind {

Expand Down
Loading
Loading