Skip to content
This repository has been archived by the owner on Jun 12, 2023. It is now read-only.

Commit

Permalink
Optional resets and delays in RepetitionCode (#599)
Browse files Browse the repository at this point in the history
Add the ability to run repetition codes without resets and with delays.

* add delays and option to remove reset

* add test for resets

* linting

* change qasm sim to aer

* change default value of resets

* test addition of delays

* add reno

* Update releasenotes/notes/optional-resets-and-delays-2cd301f1257b3962.yaml

Co-authored-by: Matthew Treinish <[email protected]>

* Update releasenotes/notes/optional-resets-and-delays-2cd301f1257b3962.yaml

Co-authored-by: Matthew Treinish <[email protected]>

* add notes on syndrome_measurement

* Update qiskit/ignis/verification/topological_codes/fitters.py

Co-authored-by: Matthew Treinish <[email protected]>

* Update releasenotes/notes/optional-resets-and-delays-2cd301f1257b3962.yaml

Co-authored-by: Matthew Treinish <[email protected]>

* Update releasenotes/notes/optional-resets-and-delays-2cd301f1257b3962.yaml

Co-authored-by: Matthew Treinish <[email protected]>

* Update releasenotes/notes/optional-resets-and-delays-2cd301f1257b3962.yaml

Co-authored-by: Matthew Treinish <[email protected]>

* edit line breaks

Co-authored-by: Matthew Treinish <[email protected]>
  • Loading branch information
quantumjim and mtreinish authored Oct 18, 2021
1 parent f0728b6 commit 0eb9dcc
Show file tree
Hide file tree
Showing 4 changed files with 70 additions and 15 deletions.
44 changes: 34 additions & 10 deletions qiskit/ignis/verification/topological_codes/circuits.py
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ class RepetitionCode:
T syndrome measurement rounds.
"""

def __init__(self, d, T=0, xbasis=False):
def __init__(self, d, T=0, xbasis=False, resets=False, delay=0):
"""
Creates the circuits corresponding to a logical 0 and 1 encoded
using a repetition code.
Expand All @@ -35,6 +35,8 @@ def __init__(self, d, T=0, xbasis=False):
d (int): Number of code qubits (and hence repetitions) used.
T (int): Number of rounds of ancilla-assisted syndrome measurement.
xbasis (bool): Whether to use the X basis to use for encoding (Z basis used by default).
resets (bool): Whether to include a reset gate after mid-circuit measurements.
delay (float): Time (in dt) to delay after mid-circuit measurements (and delay).
Additional information:
Expand All @@ -61,14 +63,15 @@ def __init__(self, d, T=0, xbasis=False):
)

self._xbasis = xbasis
self._resets = resets

self._preparation()

for _ in range(T - 1):
self.syndrome_measurement()
self.syndrome_measurement(delay=delay)

if T != 0:
self.syndrome_measurement(reset=False)
self.syndrome_measurement(final=True)
self.readout()

def get_circuit_list(self):
Expand Down Expand Up @@ -113,13 +116,14 @@ def _preparation(self, barrier=False):

self.x(["1"])

def syndrome_measurement(self, reset=True, barrier=False):
def syndrome_measurement(self, final=False, barrier=False, delay=0):
"""
Application of a syndrome measurement round.
Args:
reset (bool): If set to true add a boolean at the end of each round
final (bool): Whether this is the final syndrome measurement round.
barrier (bool): Boolean denoting whether to include a barrier at the end.
delay (float): Time (in dt) to delay after mid-circuit measurements (and delay).
"""
self.link_bits.append(
ClassicalRegister((self.d - 1), "round_" + str(self.T) + "_link_bit")
Expand Down Expand Up @@ -148,9 +152,12 @@ def syndrome_measurement(self, reset=True, barrier=False):
self.circuit[log].h(self.link_qubit)

for j in range(self.d - 1):
self.circuit[log].measure(self.link_qubit[j], self.link_bits[self.T][j])
if reset:
self.circuit[log].measure(
self.link_qubit[j], self.link_bits[self.T][j])
if self._resets and not final:
self.circuit[log].reset(self.link_qubit[j])
if delay > 0 and not final:
self.circuit[log].delay(delay, self.link_qubit[j])

if barrier:
self.circuit[log].barrier()
Expand Down Expand Up @@ -210,10 +217,27 @@ def process_results(self, raw_results):
syndrome_changes = ""
for t in range(self.T + 1):
for j in range(self.d - 1):
if t == 0:
change = syndrome_list[-1][j] != "0"
if self._resets:
if t == 0:
change = (syndrome_list[-1][j] != "0")
else:
change = (syndrome_list[-t - 1][j]
!= syndrome_list[-t][j])
else:
change = syndrome_list[-t][j] != syndrome_list[-t - 1][j]
if t <= 1:
if t != self.T:
change = (syndrome_list[-t - 1][j] != "0")
else:
change = (syndrome_list[-t - 1][j]
!= syndrome_list[-t][j])
elif t == self.T:
last3 = ""
for dt in range(3):
last3 += syndrome_list[-t - 1 + dt][j]
change = last3.count("1") % 2 == 1
else:
change = (syndrome_list[-t - 1][j]
!= syndrome_list[-t + 1][j])
syndrome_changes += "0" * (not change) + "1" * change
syndrome_changes += " "

Expand Down
2 changes: 1 addition & 1 deletion qiskit/ignis/verification/topological_codes/fitters.py
Original file line number Diff line number Diff line change
Expand Up @@ -132,7 +132,7 @@ def _make_syndrome_graph(self, results=None):
error_circuit[temp_qc.name] = temp_qc

if HAS_AER:
simulator = Aer.get_backend("qasm_simulator")
simulator = Aer.get_backend("aer_simulator")
else:
simulator = BasicAer.get_backend("qasm_simulator")

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@

features:
- |
The :class:`~qiskit.ignis.verification.RepetitionCode` now has keyword arguments ``resets`` and ``delay``.
The former determines whether reset gates are inserted after measurement.
The latter allows a time (in dt) to be specificed for a delay after each
measurement (and reset, if applicable).
The :meth:`~qiskit.ignis.verification.RepitionCode.syndrome_measurement` method of
:class:`~qiskit.ignis.verification.RepetitionCode` now has keyword
arguments ``final`` and ``delay``. The former determines whether to add reset gates according
to the global ``resets``, or to overwrite it with appropriate behavior for the
final round of syndrome measurements. The latter allows a time (in dt) to be specificed
for a delay after each measurement (and reset, if applicable).
upgrade:
- |
The keyword argument `reset` has been removed for
the :meth:`~qiskit.ignis.verification.RepitionCode.syndrome_measurement` method of
:class:`~qiskit.ignis.verification.RepetitionCode`. This is replaced by the global
``resets` keyword argument for the class as well as the keyword argument ``final``
for ``syndrome_measurement``. In cases where one would previously add the final
measurement round using ``reset=False`` to avoid the final reset gates, one
should now use ``final=True``.
16 changes: 12 additions & 4 deletions test/topological_codes/test_codes.py
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ def get_syndrome(code, noise_model, shots=1014):

job = execute(
circuits,
Aer.get_backend("qasm_simulator"),
Aer.get_backend("aer_simulator"),
noise_model=noise_model,
shots=shots,
)
Expand Down Expand Up @@ -92,7 +92,7 @@ def single_error_test(self, code):
circuit_name[(j, qubit, error)] = temp_qc.name
error_circuit[temp_qc.name] = temp_qc

simulator = Aer.get_backend("qasm_simulator")
simulator = Aer.get_backend("aer_simulator")
job = execute(list(error_circuit.values()), simulator)

for j in range(depth):
Expand Down Expand Up @@ -136,8 +136,16 @@ def test_graph_construction(self):
for d in [2, 3]:
for T in [1, 2]:
for xbasis in [False, True]:
code = RepetitionCode(d, T, xbasis=xbasis)
self.single_error_test(code)
for resets in [False, True]:
for delay in [0, 16]:
code = RepetitionCode(d, T, xbasis=xbasis, resets=resets, delay=delay)
self.single_error_test(code)
if delay > 0 and T > 1:
num_delays = code.circuit['0'].count_ops()['delay']
self.assertTrue(
num_delays == (d-1)*(T-1),
"Error: wrong number of delay gates."
)

def test_weight(self):
"""Error weighting code test."""
Expand Down

0 comments on commit 0eb9dcc

Please sign in to comment.