diff --git a/docs/SteaneFTSP.md b/docs/SteaneFTSP.md new file mode 100644 index 000000000..f092b2285 --- /dev/null +++ b/docs/SteaneFTSP.md @@ -0,0 +1,207 @@ +--- +file_format: mystnb +kernelspec: + name: python3 +mystnb: + number_source_lines: true +--- + +```{code-cell} ipython3 +:tags: [remove-cell] +%config InlineBackend.figure_formats = ['svg'] +``` + +# Steane-type Fault-Tolerant State Preparation + +This module provides automated synthesis for **Steane-type Fault-Tolerant State Preparation (FTSP)** circuits. This approach is particularly well-suited for quantum computing architectures that support a high degree of gate-level parallelism, such as trapped-ion and neutral atom quantum computers. + +Unlike other methods that rely on measuring stabilizers directly on the data qubits (flag-based or standard syndrome extraction), Steane-type preparation works by initializing separate logical ancilla states and interacting them with the data state via transversal CNOT gates to detect errors. + +## The Challenge: Error Cancellation + +The core principle of Steane-type error detection is to copy errors from a data block to an ancilla block using transversal CNOTs and then measure the ancilla to detect the error. + +However, if we consider more than just one error to occur under circuit level noise models, so errors can also happen on the ancilla qubits, then this approach can lead to a critical issue: **Error Cancellation**. +For example, if the data state and the ancilla state are prepared using the _exact same_ circuit structure, they suffer from identical propagated errors at identical locations error locations. + +When two identical errors meet at a transversal CNOT gate, they can cancel each other out on the target (ancilla) while remaining on the control (data). For example, if an X-error occurs on the $i$-th qubit of both the data and ancilla, the transversal CNOT interaction may result in no detectable syndrome on the ancilla. Consequently, the error on the data block goes undetected, breaking fault tolerance. + +### Solution: Structurally Distinct Circuits + +To ensure fault tolerance, we must break this symmetry. We need to prepare logical states using circuits that are **logically equivalent** (they prepare the same quantum state) but **structurally distinct** regarding error propagation. +In other words, we want to synthesize circuits in which errors propagate differently, so that no matter where an error occurs, we still get a detectable syndrome on the ancilla. + +#### Example: The Steane Code ($d=3$) + +To see all of the above in action, let's consider the Steane code, which is a $[[7,1,3]]$ CSS code. +Since the code distance is $d=3$, it can correct up to $t=1$ error. Therefore, we only focus on single errors in the circuit and how they propagate. +We can find a state preparation circuit for the logical $|0\rangle_L$ state using the QECC synthesis tools. This will be our reference circuit, and we can analyze its fault set to understand how errors propagate through it. + +```{code-cell} ipython3 +from mqt.qecc import CSSCode + +steane_code = CSSCode.from_code_name("Steane") +print(steane_code.stabs_as_pauli_strings()) +``` + +```{code-cell} ipython3 +from mqt.qecc.circuit_synthesis.state_prep import heuristic_prep_circuit + +steane_circ = heuristic_prep_circuit(steane_code) +steane_circ.circ.draw('mpl') +``` + +Errors propagate this circuit in a specific way, which we can analyze by extracting the fault set. +The fault set lists propagated errors which are the result of a errors within the circuit. +For example, a single X-error on $q_1$ just before the last CNOT gate will propagate to a weight two error on qubits $q_1$ and $q_5$. +Looking at the fault set of the circuit above, we can see this error listed here. + +```{code-cell} ipython3 +steane_circ.compute_fault_sets() +steane_circ.x_fault_sets[0].faults +``` + +Note that the fault set is reduced and ignores stabilizer-equivalent errors. Meaning that the propagated error on $q_0$ and $q_4$ is not listed, since it is equivalent to the error on $q_1$ and $q_5$ up to multiplication by the first stabilizer generator $XXIIXXI$. + +The bottom line is that the fault set above characterizes the error propagation of the given circuit. So if we were to synthesize a second circuit for the same logical state, that has a different fault set, we can be sure that no errors $E$ of weight up to $\text{wt}(E)=1$ can cancel each other out. + +For this, QECC provides a function called `heuristic_reference_prep_circuit` which takes a reference circuit and its fault set as input and tries to find a new circuit that avoids the same faults. + +```{code-cell} ipython3 +from mqt.qecc.circuit_synthesis.state_prep import heuristic_reference_prep_circuit + +steane_circ_alt = heuristic_reference_prep_circuit(steane_code, ref_x_fs=steane_circ.x_fault_sets[0].faults) +steane_circ_alt.circ.draw('mpl') + +``` + +```{code-cell} ipython3 +steane_circ_alt.compute_fault_sets() +steane_circ_alt.x_fault_sets[0].faults +``` + +The two fault sets are distinct also under multiplication by stabilizers. One can verify this by multiplying each of the propagated errors with the $X$ stabilizer generators of the Steane Code and ensuring that errors are not equivalent. + +## The 4-Circuit Protocol (Distance $\ge 5$) + +For higher-distance codes ($d \geq 5$), simply avoiding identical errors is not enough. We must ensure that the verification process itself does not introduce high-weight errors that go undetected. + +This module implements a constant-overhead protocol that uses **four specific circuits** to guarantee strict fault tolerance. This protocol is general and works even for codes without symmetries, such as the $[[17,1,5]]$ color code. + +### The Protocol Structure + +The protocol requires synthesizing four unique circuits ($C_1, C_2, C_3, C_4$) that interact in a specific sequence: + +1. **$C_1$ (Data Candidate):** The initial state we wish to prepare. +2. **$C_2$ (X-Verifier):** An ancilla used to detect X-errors on $C_1$. + - _Constraint:_ Must have a distinct X-fault set from $C_1$. +3. **$C_3$ (Z-Verifier):** An ancilla used to detect Z-errors on $C_1$. + - _Constraint:_ Must have a distinct Z-fault set from _both_ $C_1$ and $C_2$ (since Z-errors can propagate backward from ancilla to data). +4. **$C_4$ (Verifier of the Verifier):** An ancilla used to detect X-errors on $C_3$. + - _Constraint:_ Ensures that the Z-verification step ($C_3$) did not introduce undetectable X-errors. It must be distinct from the relevant faults of the previous chains. + +### Utility: Automated 4-Circuit Synthesis Wrapper + +While you can call the synthesis API manually for each step, you can use the following custom helper function in your workflow to automatically generate the full suite of 4 mutually distinct circuits based on the protocol rules. + +However, note that for codes with higher distance, the search space for circuits grows significantly, and hence the synthesis process might get stuck sometimes. +Therefore, this utility function is not guaranteed to always find a solution and might be more of a starting point for your own custom synthesis workflow. + +```{code-cell} ipython3 +import numpy as np +from mqt.qecc.circuit_synthesis import heuristic_prep_circuit +from mqt.qecc.circuit_synthesis.synthesis_utils import check_mutually_disjointness_spcs, get_fs_based_on_d + +def synthesize_four_ft_circuits(c1_circuit): + """ + Synthesizes the four distinct state preparation circuits required + for Steane-type Fault-Tolerant State Preparation. + + Args: + c1_circuit: The reference state preparation circuit (C1). + + Returns: + List of 4 circuits [C1, C2, C3, C4] satisfying t-distinctness constraints. + """ + # --------------------------------------------------------- + # Step 1: Analyze Reference Circuit (C1) + # --------------------------------------------------------- + c1_x_faults, c1_z_faults = get_fs_based_on_d(c1_circuit) + + # --------------------------------------------------------- + # Step 2: Synthesize X-Verifier (C2) + # Constraint: X-faults must be distinct from C1. + # --------------------------------------------------------- + c2_circuit = heuristic_reference_prep_circuit(c1_circuit.code, ref_x_fs=c1_x_faults) + #BUG: Distance is not properly initialized + c2_circuit.code.distance = c1_circuit.code.distance + c2_x_faults, c2_z_faults = get_fs_based_on_d(c2_circuit) + + # --------------------------------------------------------- + # Step 3: Synthesize Z-Verifier (C3) + # Constraint: Z-faults must be distinct from BOTH C1 and C2. + # --------------------------------------------------------- + # Combine Z-faults from C1 and C2 to avoid them simultaneously + if c1_z_faults.size and c2_z_faults.size: + combined_z_faults = np.unique(np.vstack((c1_z_faults, c2_z_faults), dtype=np.int8), axis=0) + elif c1_z_faults.size: + combined_z_faults = c1_z_faults + elif c2_z_faults.size: + combined_z_faults = c2_z_faults + else: + # If no Z-faults exist that require distinctness, fallback to reusing circuits + return [c1_circuit, c2_circuit, c1_circuit, c2_circuit] + + c3_circuit = heuristic_reference_prep_circuit(c1_circuit.code, ref_z_fs=combined_z_faults, guide_by_x=False) + #BUG: Distance is not properly initialized + c3_circuit.code.distance = c1_circuit.code.distance + c3_x_faults, c3_z_faults = get_fs_based_on_d(c3_circuit) + + # --------------------------------------------------------- + # Step 4: Synthesize Final Verifier (C4) + # Constraint: X-faults distinct from C3, Z-faults distinct from C1 & C2. + # --------------------------------------------------------- + c4_circuit = heuristic_reference_prep_circuit( + c1_circuit.code, + ref_x_fs=c3_x_faults, + ref_z_fs=combined_z_faults, + guide_by_x=False + ) + + return [c1_circuit, c2_circuit, c3_circuit, c4_circuit] +``` + +### Automated Synthesis with the $[[17,1,5]]$ Color Code + +The $[[17,1,5]]$ color code is a perfect candidate for this approach because it lacks the symmetries required by older manual construction methods. The QECC toolkit uses a "Fault-Set Guided Synthesis" algorithm to find these circuits automatically by backtracking whenever a constraint is violated. + +```{code-cell} ipython3 +from mqt.qecc.codes import SquareOctagonColorCode + +soc = SquareOctagonColorCode(5) +c1 = heuristic_prep_circuit(soc) +#BUG: Distance is not properly initialized +c1.code.distance = soc.distance +c1.code.x_distance = soc.distance +c1.code.z_distance = soc.distance +c1c2c3c4 = synthesize_four_ft_circuits(c1) + +``` + +## Simulation and Verification + +Once the four circuits are generated, they form a complete fault-tolerant gadget. The expected behavior is that the logical error rate should scale with $O(p^{\lceil d/2 \rceil})$, and the circuit should satisfy strict fault tolerance (no error of weight $t \le (d-1)/2$ leads to a logical failure). + +```{code-cell} ipython3 +from mqt.qecc.circuit_synthesis.simulation import SteaneNDFTStatePrepSimulator +simulation = SteaneNDFTStatePrepSimulator( + circ1=c1c2c3c4[0].circ.to_qiskit_circuit(), + circ2=c1c2c3c4[1].circ.to_qiskit_circuit(), + circ3=c1c2c3c4[2].circ.to_qiskit_circuit(), + circ4=c1c2c3c4[3].circ.to_qiskit_circuit(), + code=soc +) +ps = [0.007,0.006,0.005, 0.004, 0.003, 0.002, 0.001] +# simulation.plot_state_prep(ps, min_errors=10, p_idle_factor=0.01) + +``` diff --git a/docs/index.md b/docs/index.md index 7dbe169bb..44de8aaa0 100644 --- a/docs/index.md +++ b/docs/index.md @@ -28,6 +28,7 @@ self installation LightsOutDecoder StatePrep +SteaneFTSP CatStates CodeSwitching Encoders diff --git a/scripts/ft_stateprep/canonical_steane/estimate_canonical.py b/scripts/ft_stateprep/canonical_steane/estimate_canonical.py new file mode 100644 index 000000000..6e8e6cd53 --- /dev/null +++ b/scripts/ft_stateprep/canonical_steane/estimate_canonical.py @@ -0,0 +1,82 @@ +# Copyright (c) 2023 - 2026 Chair for Design Automation, TUM +# All rights reserved. +# +# SPDX-License-Identifier: MIT +# +# Licensed under the MIT License + +"""Estimate logical error rate for CSS state preparation circuits for a given code and physical error rate.""" + +from __future__ import annotations + +import argparse + +from mqt.qecc import CSSCode +from mqt.qecc.circuit_synthesis import SteaneNDFTStatePrepSimulator, heuristic_prep_circuit +from mqt.qecc.circuit_synthesis.state_prep import canonical_steane_type_prep_circuits, random_steane_type_prep_circuits +from mqt.qecc.codes import HexagonalColorCode, SquareOctagonColorCode + +codes = {"golay": CSSCode.from_code_name("golay"), "hex": HexagonalColorCode(7), "sqoct": SquareOctagonColorCode(7)} + + +def main() -> None: + """Run the logical error rate estimation for a given code and physical error rate.""" + parser = argparse.ArgumentParser(description="Estimate logical error rate for CSS state preparation circuits") + parser.add_argument( + "code", + type=str, + help="Code for which to estimate logical error rate. Available codes: " + ", ".join(codes), + ) + parser.add_argument("-p", "--p_error", type=float, help="Physical error rate") + parser.add_argument("-n", "--n_errors", type=int, default=500, help="Number of errors to sample") + parser.add_argument( + "--perm", + type=str, + default="canonical", + help="Permutation for state preparation. Can be 'canonical' or 'random'", + ) + parser.add_argument( + "-e", "--error_type", type=str, default="X", help="Type of error to use for simulation. Can be 'X' or 'Z'." + ) + + args = parser.parse_args() + code_name = args.code + if code_name in codes: + code = codes[code_name] + else: + raise ValueError("Code " + code_name + " not available. Available codes: " + ", ".join(codes)) + + if args.perm == "canonical": + qc1, qc2, qc3, qc4 = canonical_steane_type_prep_circuits(code) + perm = "canonical" + elif args.perm == "random": + qc1, qc2, qc3, qc4, perm = random_steane_type_prep_circuits(code) + else: + raise ValueError("Permutation " + args.perm + " not available. Available permutations: 'canonical, random'") + + sim = SteaneNDFTStatePrepSimulator( + qc1, qc2, code, qc3, qc4, check_circuit=heuristic_prep_circuit(code, zero_state=False).circ + ) + sim.set_p(args.p_error, args.p_error * 0.01) + + if args.error_type == "X": + p_l, r_a, num_logical_errors, total_shots, p_l_error, r_a_error = sim.logical_error_rate( + min_errors=args.n_errors + ) + elif args.error_type == "Z": + p_l, r_a, num_logical_errors, total_shots, p_l_error, r_a_error = sim.secondary_logical_error_rate( + min_errors=args.n_errors + ) + else: + msg = "Error type should be either X or Z." + raise ValueError(msg) + + print( + ";".join([ + str(x) for x in [args.p_error, p_l, r_a, num_logical_errors, total_shots, p_l_error, r_a_error, perm] + ]) + ) + + +if __name__ == "__main__": + main() diff --git a/scripts/ft_stateprep/canonical_steane/run_parallel.sh b/scripts/ft_stateprep/canonical_steane/run_parallel.sh new file mode 100755 index 000000000..eb773d6a0 --- /dev/null +++ b/scripts/ft_stateprep/canonical_steane/run_parallel.sh @@ -0,0 +1,21 @@ +#!/bin/bash +# Copyright (c) 2023 - 2026 Chair for Design Automation, TUM +# All rights reserved. +# +# SPDX-License-Identifier: MIT +# +# Licensed under the MIT License + +declare -a p=("0.001" "0.0015" "0.002" "0.0025" "0.003" "0.0035" "0.004" "0.0045" "0.005" "0.0055" "0.006" "0.0065" "0.007" "0.0075" "0.008" "0.0085" "0.009" "0.0095" "0.01") + +echo "p;p_l;r_a;num_logical_errors;total_shots;p_l_error;r_a_error" > "$1.csv" + +run_and_write() { + local res=$(python estimate_canonical.py ${@:2:$#-2} "-p" "${@: -1}") + local line="${@: -1};${res}" + (flock -e 200 echo $line >> "$1.csv") 200>lock +} + +export -f run_and_write + +parallel --load 16 --link run_and_write $@ ::: ${p[@]} diff --git a/scripts/ft_stateprep/eval/estimate_logical_error_rate.py b/scripts/ft_stateprep/eval/estimate_logical_error_rate.py index 52cfc7bb7..b0e6e40e9 100644 --- a/scripts/ft_stateprep/eval/estimate_logical_error_rate.py +++ b/scripts/ft_stateprep/eval/estimate_logical_error_rate.py @@ -16,7 +16,7 @@ from mqt.qecc import CSSCode from mqt.qecc.circuit_synthesis import ( - NoisyNDFTStatePrepSimulator, + VerificationNDFTStatePrepSimulator, gate_optimal_prep_circuit, gate_optimal_verification_circuit, heuristic_prep_circuit, @@ -98,7 +98,7 @@ def main() -> None: # load circuit from file qc = QuantumCircuit.from_qasm_file(prefix / code_name / circ_file) - sim = NoisyNDFTStatePrepSimulator( + sim = VerificationNDFTStatePrepSimulator( qc, code=code, p=args.p_error, diff --git a/scripts/ft_stateprep/eval/run_d7.py b/scripts/ft_stateprep/eval/run_d7.py index 6958d80e5..1a9186300 100644 --- a/scripts/ft_stateprep/eval/run_d7.py +++ b/scripts/ft_stateprep/eval/run_d7.py @@ -16,7 +16,7 @@ from qiskit import QuantumCircuit from mqt.qecc.circuit_synthesis import ( - NoisyNDFTStatePrepSimulator, + VerificationNDFTStatePrepSimulator, ) from mqt.qecc.codes import SquareOctagonColorCode @@ -38,7 +38,9 @@ def main() -> None: lut_path = (Path(__file__) / "../luts/decoder_488_7.pickle").resolve() with lut_path.open("rb") as f: lut = pickle.load(f) # noqa: S301 - sim = NoisyNDFTStatePrepSimulator(qc, code, decoder=lut, p=args.p_error, p_idle=args.p_idle_factor * args.p_error) + sim = VerificationNDFTStatePrepSimulator( + qc, code, decoder=lut, p=args.p_error, p_idle=args.p_idle_factor * args.p_error + ) res = sim.logical_error_rate(min_errors=args.n_errors) print(",".join([str(x) for x in [args.p_error, *res]])) diff --git a/scripts/ft_stateprep/eval_circ_mod/check_matrix/eve_20_2_6.txt b/scripts/ft_stateprep/eval_circ_mod/check_matrix/eve_20_2_6.txt new file mode 100644 index 000000000..76db61039 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/check_matrix/eve_20_2_6.txt @@ -0,0 +1,18 @@ +XIIIIIIIIXIXXIXXXXII +IXIIIIIIIXIIXXIIXXXX +IIXIIIIIIIXXIXXIXXXI +IIIXIIIIIIXIXXXXIXIX +IIIIXIIIIXXIXIIIXXXX +IIIIIXIIIXIXIIXXXXIX +IIIIIIXIIIXXIXIXXXXI +IIIIIIIXIXIXIIIIIIXI +IIIIIIIIXIXIXXXXXIIX +ZIIIIIIIIZIZZIZZZZII +IZIIIIIIIZIIZZIIZZZZ +IIZIIIIIIIZZIZZIZZZI +IIIZIIIIIIZIZZZZIZIZ +IIIIZIIIIZZIZIIIZZZZ +IIIIIZIIIZIZIIZZZZIZ +IIIIIIZIIIZZIZIZZZZI +IIIIIIIZIZIZIIIIIIZI +IIIIIIIIZIZIZZZZZIIZ diff --git a/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_17_1_5.txt b/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_17_1_5.txt new file mode 100644 index 000000000..d9515d0bf --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_17_1_5.txt @@ -0,0 +1,16 @@ +ZZZZIIIIIIIIIIIII +IZIZIIZZIIIIIIIII +IIIIZIIIZIIIZZIII +IIIIZZIIZZIIIIIII +IIZZIZZIIZZIIIZZI +IIIIIIZZIIZZIIIII +IIIIIIIIZZIIIZZII +IIIIIIIIIIZZIIIZZ +XXXXIIIIIIIIIIIII +IXIXIIXXIIIIIIIII +IIIIXIIIXIIIXXIII +IIIIXXIIXXIIIIIII +IIXXIXXIIXXIIIXXI +IIIIIIXXIIXXIIIII +IIIIIIIIXXIIIXXII +IIIIIIIIIIXXIIIXX diff --git a/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_20_2_6.txt b/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_20_2_6.txt new file mode 100644 index 000000000..af215778f --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_20_2_6.txt @@ -0,0 +1,18 @@ +ZZZZIIIIIIIIIIIIIIII +IIIIZZZZIIIIIIIIIIII +IIIIIIIIZZZZIIIIIIII +IIIIIIIIIIIIZZZZIIII +IIIIIIIIIIIIIIIIZZZZ +ZIIZIIZZIIZZZIIZIIII +IIIIZIIZIIZZIIZZZIIZ +ZIIZIIIIZIIZIIZZIIZZ +IIZZZIIZIIIIZIIZIIZZ +XXXXIIIIIIIIIIIIIIII +IIIIXXXXIIIIIIIIIIII +IIIIIIIIXXXXIIIIIIII +IIIIIIIIIIIIXXXXIIII +IIIIIIIIIIIIIIIIXXXX +XIIXIIXXIIXXXIIXIIII +IIIIXIIXIIXXIIXXXIIX +XIIXIIIIXIIXIIXXIIXX +IIXXXIIXIIIIXIIXIIXX diff --git a/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_25_1_5.txt b/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_25_1_5.txt new file mode 100644 index 000000000..6e4bb34ff --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_25_1_5.txt @@ -0,0 +1,24 @@ +IIIIZIIIIZIIIIIIIIIIIIIII +IIIIIIIIIIIIIIZIIIIZIIIII +IIIIIIIIZZIIIZZIIIIIIIIII +IIIIIIIIIIIIIIIIIIZZIIIZZ +IIZZIIIZZIIIIIIIIIIIIIIII +IIIIIIIIIIIIZZIIIZZIIIIII +IIIIIIZZIIIZZIIIIIIIIIIII +IIIIIIIIIIIIIIIIZZIIIZZII +ZZIIIZZIIIIIIIIIIIIIIIIII +IIIIIIIIIIZZIIIZZIIIIIIII +IIIIIZIIIIZIIIIIIIIIIIIII +IIIIIIIIIIIIIIIZIIIIZIIII +XXIIIIIIIIIIIIIIIIIIIIIII +IIXXIIIIIIIIIIIIIIIIIIIII +IXXIIIXXIIIIIIIIIIIIIIIII +IIIXXIIIXXIIIIIIIIIIIIIII +IIIIIXXIIIXXIIIIIIIIIIIII +IIIIIIIXXIIIXXIIIIIIIIIII +IIIIIIIIIIIXXIIIXXIIIIIII +IIIIIIIIIIIIIXXIIIXXIIIII +IIIIIIIIIIIIIIIXXIIIXXIII +IIIIIIIIIIIIIIIIIXXIIIXXI +IIIIIIIIIIIIIIIIIIIIIXXII +IIIIIIIIIIIIIIIIIIIIIIIXX diff --git a/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_31_1_7.txt b/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_31_1_7.txt new file mode 100644 index 000000000..ea427be97 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/check_matrix/flag_at_origin/cc_31_1_7.txt @@ -0,0 +1,30 @@ +ZIZIZZIIIIIIIIIIIIIIIIIIIIIIIII +ZZZZIIIIIIIIIIIIIIIIIIIIIIIIIII +IIIIZZIIZZIIIIIIIIIIIIIIIIIIIII +IIZZIZZIIZZIIIZZIIIIIIIIIIIIIII +IIIIIIZZIIZZIIIIIIIIIIIIIIIIIII +IIIIIIIZIIIZIIIIZZIIIIIIIIIIIII +IIIIIIIIIIIIZIIIIIZIIIIIZZIIIII +IIIIIIIIIIIIZZIIIIZZIIIIIIIIIII +IIIIIIIIZZIIIZZIIIIZZIIIIIZZIII +IIIIIIIIIIIIIIZZIIIIZZIIIIIIIII +IIIIIIIIIIZZIIIZZIIIIZZIIIIIZZI +IIIIIIIIIIIIIIIIZZIIIIZZIIIIIII +IIIIIIIIIIIIIIIIIIZZIIIIIZZIIII +IIIIIIIIIIIIIIIIIIIIZZIIIIIZZII +IIIIIIIIIIIIIIIIIIIIIIZZIIIIIZZ +XIXIXXIIIIIIIIIIIIIIIIIIIIIIIII +XXXXIIIIIIIIIIIIIIIIIIIIIIIIIII +IIIIXXIIXXIIIIIIIIIIIIIIIIIIIII +IIXXIXXIIXXIIIXXIIIIIIIIIIIIIII +IIIIIIXXIIXXIIIIIIIIIIIIIIIIIII +IIIIIIIXIIIXIIIIXXIIIIIIIIIIIII +IIIIIIIIIIIIXIIIIIXIIIIIXXIIIII +IIIIIIIIIIIIXXIIIIXXIIIIIIIIIII +IIIIIIIIXXIIIXXIIIIXXIIIIIXXIII +IIIIIIIIIIIIIIXXIIIIXXIIIIIIIII +IIIIIIIIIIXXIIIXXIIIIXXIIIIIXXI +IIIIIIIIIIIIIIIIXXIIIIXXIIIIIII +IIIIIIIIIIIIIIIIIIXXIIIIIXXIIII +IIIIIIIIIIIIIIIIIIIIXXIIIIIXXII +IIIIIIIIIIIIIIIIIIIIIIXXIIIIIXX diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_0.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_0.qasm new file mode 100644 index 000000000..f5eed9e67 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_0.qasm @@ -0,0 +1,34 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[17]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +h q[9]; +h q[10]; +cx q[4],q[8]; +cx q[10],q[15]; +cx q[4],q[6]; +cx q[9],q[15]; +cx q[5],q[12]; +cx q[4],q[7]; +cx q[3],q[14]; +cx q[2],q[6]; +cx q[14],q[16]; +cx q[10],q[13]; +cx q[9],q[11]; +cx q[8],q[5]; +cx q[3],q[7]; +cx q[1],q[4]; +cx q[0],q[2]; +cx q[12],q[9]; +cx q[1],q[13]; +cx q[0],q[3]; +cx q[15],q[8]; +cx q[6],q[16]; +cx q[5],q[11]; +cx q[4],q[10]; +cx q[2],q[14]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_1.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_1.qasm new file mode 100644 index 000000000..02bb49cb2 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_1.qasm @@ -0,0 +1,34 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[17]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +cx q[1],q[4]; +cx q[3],q[7]; +h q[8]; +cx q[8],q[5]; +cx q[8],q[7]; +cx q[5],q[11]; +cx q[11],q[4]; +h q[12]; +h q[13]; +cx q[13],q[10]; +cx q[4],q[10]; +cx q[3],q[14]; +h q[15]; +cx q[15],q[9]; +cx q[12],q[9]; +cx q[13],q[15]; +cx q[1],q[13]; +cx q[15],q[8]; +cx q[9],q[11]; +cx q[2],q[16]; +cx q[2],q[6]; +cx q[0],q[2]; +cx q[0],q[3]; +cx q[2],q[14]; +cx q[5],q[6]; +cx q[12],q[5]; +cx q[7],q[16]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_2.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_2.qasm new file mode 100644 index 000000000..f5eed9e67 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_2.qasm @@ -0,0 +1,34 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[17]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +h q[9]; +h q[10]; +cx q[4],q[8]; +cx q[10],q[15]; +cx q[4],q[6]; +cx q[9],q[15]; +cx q[5],q[12]; +cx q[4],q[7]; +cx q[3],q[14]; +cx q[2],q[6]; +cx q[14],q[16]; +cx q[10],q[13]; +cx q[9],q[11]; +cx q[8],q[5]; +cx q[3],q[7]; +cx q[1],q[4]; +cx q[0],q[2]; +cx q[12],q[9]; +cx q[1],q[13]; +cx q[0],q[3]; +cx q[15],q[8]; +cx q[6],q[16]; +cx q[5],q[11]; +cx q[4],q[10]; +cx q[2],q[14]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_3.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_3.qasm new file mode 100644 index 000000000..02bb49cb2 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5/cc_4_8_8_d5_heuristic_3.qasm @@ -0,0 +1,34 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[17]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +cx q[1],q[4]; +cx q[3],q[7]; +h q[8]; +cx q[8],q[5]; +cx q[8],q[7]; +cx q[5],q[11]; +cx q[11],q[4]; +h q[12]; +h q[13]; +cx q[13],q[10]; +cx q[4],q[10]; +cx q[3],q[14]; +h q[15]; +cx q[15],q[9]; +cx q[12],q[9]; +cx q[13],q[15]; +cx q[1],q[13]; +cx q[15],q[8]; +cx q[9],q[11]; +cx q[2],q[16]; +cx q[2],q[6]; +cx q[0],q[2]; +cx q[0],q[3]; +cx q[2],q[14]; +cx q[5],q[6]; +cx q[12],q[5]; +cx q[7],q[16]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_0.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_0.qasm new file mode 100644 index 000000000..e9d889887 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_0.qasm @@ -0,0 +1,34 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[17]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[9]; +h q[10]; +h q[12]; +cx q[10],q[15]; +cx q[4],q[7]; +cx q[2],q[16]; +cx q[9],q[15]; +cx q[7],q[8]; +cx q[4],q[5]; +cx q[3],q[14]; +cx q[2],q[6]; +cx q[12],q[9]; +cx q[10],q[13]; +cx q[8],q[11]; +cx q[5],q[6]; +cx q[3],q[7]; +cx q[1],q[4]; +cx q[0],q[2]; +cx q[12],q[5]; +cx q[1],q[13]; +cx q[0],q[3]; +cx q[15],q[8]; +cx q[9],q[11]; +cx q[7],q[16]; +cx q[4],q[10]; +cx q[2],q[14]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_1.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_1.qasm new file mode 100644 index 000000000..b0d89c145 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_1.qasm @@ -0,0 +1,34 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[17]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +cx q[4],q[8]; +cx q[4],q[6]; +cx q[2],q[6]; +cx q[0],q[2]; +cx q[4],q[7]; +cx q[1],q[4]; +h q[9]; +h q[10]; +cx q[5],q[12]; +cx q[8],q[5]; +cx q[3],q[14]; +cx q[3],q[7]; +cx q[0],q[3]; +cx q[10],q[15]; +cx q[10],q[13]; +cx q[1],q[13]; +cx q[4],q[10]; +cx q[9],q[15]; +cx q[15],q[8]; +cx q[9],q[11]; +cx q[12],q[9]; +cx q[5],q[11]; +cx q[14],q[16]; +cx q[2],q[14]; +cx q[6],q[16]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_2.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_2.qasm new file mode 100644 index 000000000..830bbc790 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_2.qasm @@ -0,0 +1,34 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[17]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +h q[9]; +h q[13]; +cx q[13],q[15]; +cx q[4],q[8]; +cx q[9],q[15]; +cx q[8],q[10]; +cx q[5],q[12]; +cx q[4],q[7]; +cx q[3],q[14]; +cx q[2],q[6]; +cx q[14],q[16]; +cx q[9],q[11]; +cx q[8],q[6]; +cx q[4],q[5]; +cx q[3],q[7]; +cx q[1],q[13]; +cx q[0],q[2]; +cx q[12],q[9]; +cx q[1],q[4]; +cx q[0],q[3]; +cx q[15],q[8]; +cx q[13],q[10]; +cx q[6],q[16]; +cx q[5],q[11]; +cx q[2],q[14]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_3.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_3.qasm new file mode 100644 index 000000000..1f87fe4f1 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d5_v1/cc_4_8_8_heuristic_3.qasm @@ -0,0 +1,34 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[17]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[9]; +h q[10]; +h q[12]; +cx q[10],q[15]; +cx q[4],q[7]; +cx q[9],q[15]; +cx q[7],q[8]; +cx q[4],q[5]; +cx q[3],q[14]; +cx q[2],q[6]; +cx q[14],q[16]; +cx q[12],q[9]; +cx q[10],q[13]; +cx q[8],q[11]; +cx q[5],q[6]; +cx q[3],q[7]; +cx q[1],q[4]; +cx q[0],q[2]; +cx q[12],q[5]; +cx q[1],q[13]; +cx q[0],q[3]; +cx q[15],q[8]; +cx q[9],q[11]; +cx q[6],q[16]; +cx q[4],q[10]; +cx q[2],q[14]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_0.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_0.qasm new file mode 100644 index 000000000..3c36afa8b --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_0.qasm @@ -0,0 +1,64 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[31]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +h q[6]; +h q[8]; +h q[9]; +h q[10]; +h q[11]; +h q[12]; +h q[17]; +h q[19]; +h q[20]; +cx q[9],q[30]; +cx q[5],q[22]; +cx q[22],q[29]; +cx q[12],q[23]; +cx q[9],q[14]; +cx q[5],q[16]; +cx q[4],q[27]; +cx q[3],q[24]; +cx q[24],q[26]; +cx q[19],q[25]; +cx q[16],q[12]; +cx q[10],q[27]; +cx q[9],q[15]; +cx q[8],q[23]; +cx q[6],q[14]; +cx q[3],q[21]; +cx q[2],q[5]; +cx q[1],q[4]; +cx q[0],q[29]; +cx q[26],q[16]; +cx q[25],q[28]; +cx q[24],q[14]; +cx q[21],q[0]; +cx q[20],q[9]; +cx q[19],q[22]; +cx q[17],q[2]; +cx q[15],q[1]; +cx q[11],q[3]; +cx q[10],q[13]; +cx q[8],q[18]; +cx q[6],q[7]; +cx q[20],q[18]; +cx q[17],q[19]; +cx q[14],q[16]; +cx q[11],q[13]; +cx q[29],q[6]; +cx q[27],q[21]; +cx q[23],q[30]; +cx q[12],q[15]; +cx q[9],q[8]; +cx q[5],q[28]; +cx q[4],q[26]; +cx q[3],q[10]; +cx q[2],q[25]; +cx q[1],q[24]; +cx q[0],q[7]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_1.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_1.qasm new file mode 100644 index 000000000..7669ce99f --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_1.qasm @@ -0,0 +1,70 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[31]; +h q[0]; +h q[2]; +h q[7]; +cx q[7],q[6]; +h q[9]; +cx q[9],q[8]; +cx q[8],q[6]; +h q[11]; +h q[13]; +h q[16]; +cx q[16],q[14]; +h q[17]; +h q[19]; +h q[20]; +cx q[16],q[22]; +cx q[0],q[16]; +cx q[0],q[7]; +h q[23]; +cx q[23],q[15]; +cx q[22],q[15]; +cx q[15],q[12]; +cx q[19],q[22]; +cx q[17],q[19]; +h q[24]; +h q[26]; +cx q[24],q[26]; +cx q[24],q[21]; +cx q[13],q[21]; +cx q[11],q[13]; +cx q[9],q[24]; +cx q[9],q[16]; +cx q[16],q[6]; +cx q[9],q[15]; +h q[27]; +cx q[27],q[10]; +cx q[10],q[3]; +cx q[10],q[21]; +cx q[13],q[10]; +cx q[27],q[26]; +cx q[26],q[24]; +cx q[27],q[1]; +cx q[1],q[4]; +cx q[24],q[1]; +cx q[26],q[4]; +cx q[27],q[7]; +cx q[21],q[27]; +cx q[2],q[28]; +cx q[28],q[25]; +cx q[19],q[25]; +cx q[22],q[28]; +cx q[0],q[29]; +cx q[6],q[29]; +cx q[7],q[0]; +h q[30]; +cx q[30],q[18]; +cx q[14],q[30]; +cx q[14],q[5]; +cx q[15],q[30]; +cx q[18],q[23]; +cx q[2],q[5]; +cx q[17],q[2]; +cx q[20],q[18]; +cx q[18],q[8]; +cx q[20],q[9]; +cx q[3],q[14]; +cx q[11],q[3]; +cx q[16],q[14]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_2.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_2.qasm new file mode 100644 index 000000000..4d2c2d5c8 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_2.qasm @@ -0,0 +1,75 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[31]; +h q[1]; +h q[4]; +h q[6]; +h q[7]; +h q[8]; +h q[9]; +h q[10]; +h q[11]; +h q[13]; +h q[14]; +h q[15]; +h q[17]; +h q[19]; +h q[23]; +h q[25]; +cx q[23],q[0]; +cx q[13],q[3]; +cx q[1],q[27]; +cx q[6],q[28]; +cx q[15],q[30]; +cx q[14],q[16]; +cx q[7],q[16]; +cx q[8],q[30]; +cx q[19],q[28]; +cx q[25],q[2]; +cx q[9],q[21]; +cx q[11],q[13]; +cx q[15],q[18]; +cx q[23],q[27]; +cx q[6],q[29]; +cx q[1],q[21]; +cx q[3],q[24]; +cx q[9],q[30]; +cx q[0],q[15]; +cx q[19],q[25]; +cx q[4],q[26]; +cx q[17],q[5]; +cx q[10],q[27]; +cx q[16],q[23]; +cx q[13],q[28]; +cx q[4],q[27]; +cx q[9],q[20]; +cx q[10],q[21]; +cx q[18],q[12]; +cx q[0],q[29]; +cx q[1],q[24]; +cx q[11],q[26]; +cx q[7],q[28]; +cx q[14],q[30]; +cx q[16],q[15]; +cx q[13],q[23]; +cx q[25],q[17]; +cx q[11],q[24]; +cx q[8],q[18]; +cx q[26],q[21]; +cx q[13],q[15]; +cx q[29],q[30]; +cx q[25],q[22]; +cx q[16],q[27]; +cx q[28],q[17]; +cx q[23],q[20]; +cx q[5],q[22]; +cx q[3],q[26]; +cx q[2],q[28]; +cx q[6],q[16]; +cx q[7],q[29]; +cx q[10],q[13]; +cx q[11],q[27]; +cx q[30],q[23]; +cx q[20],q[21]; +cx q[15],q[18]; +cx q[17],q[25]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_3.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_3.qasm new file mode 100644 index 000000000..4038cabde --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7/cc_4_8_8_d7_heuristic_3.qasm @@ -0,0 +1,79 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[31]; +h q[0]; +h q[1]; +h q[3]; +h q[6]; +h q[9]; +h q[11]; +h q[13]; +h q[14]; +h q[16]; +h q[17]; +h q[18]; +h q[19]; +h q[25]; +h q[26]; +h q[30]; +cx q[30],q[12]; +cx q[6],q[23]; +cx q[18],q[30]; +cx q[0],q[29]; +cx q[18],q[8]; +cx q[6],q[20]; +cx q[14],q[23]; +cx q[26],q[21]; +cx q[29],q[18]; +cx q[11],q[20]; +cx q[0],q[23]; +cx q[16],q[28]; +cx q[17],q[7]; +cx q[25],q[5]; +cx q[3],q[27]; +cx q[6],q[17]; +cx q[16],q[2]; +cx q[14],q[29]; +cx q[13],q[10]; +cx q[27],q[18]; +cx q[1],q[21]; +cx q[9],q[23]; +cx q[20],q[25]; +cx q[14],q[16]; +cx q[6],q[18]; +cx q[1],q[24]; +cx q[3],q[13]; +cx q[19],q[25]; +cx q[7],q[21]; +cx q[11],q[27]; +cx q[2],q[17]; +cx q[23],q[20]; +cx q[7],q[20]; +cx q[5],q[28]; +cx q[26],q[4]; +cx q[9],q[15]; +cx q[17],q[16]; +cx q[12],q[23]; +cx q[11],q[18]; +cx q[3],q[25]; +cx q[13],q[21]; +cx q[27],q[24]; +cx q[7],q[25]; +cx q[12],q[15]; +cx q[16],q[18]; +cx q[1],q[26]; +cx q[3],q[20]; +cx q[28],q[22]; +cx q[29],q[21]; +cx q[27],q[17]; +cx q[23],q[30]; +cx q[24],q[26]; +cx q[16],q[29]; +cx q[12],q[30]; +cx q[5],q[17]; +cx q[19],q[22]; +cx q[11],q[13]; +cx q[18],q[23]; +cx q[20],q[15]; +cx q[25],q[28]; +cx q[21],q[27]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_0.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_0.qasm new file mode 100644 index 000000000..3c36afa8b --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_0.qasm @@ -0,0 +1,64 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[31]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +h q[6]; +h q[8]; +h q[9]; +h q[10]; +h q[11]; +h q[12]; +h q[17]; +h q[19]; +h q[20]; +cx q[9],q[30]; +cx q[5],q[22]; +cx q[22],q[29]; +cx q[12],q[23]; +cx q[9],q[14]; +cx q[5],q[16]; +cx q[4],q[27]; +cx q[3],q[24]; +cx q[24],q[26]; +cx q[19],q[25]; +cx q[16],q[12]; +cx q[10],q[27]; +cx q[9],q[15]; +cx q[8],q[23]; +cx q[6],q[14]; +cx q[3],q[21]; +cx q[2],q[5]; +cx q[1],q[4]; +cx q[0],q[29]; +cx q[26],q[16]; +cx q[25],q[28]; +cx q[24],q[14]; +cx q[21],q[0]; +cx q[20],q[9]; +cx q[19],q[22]; +cx q[17],q[2]; +cx q[15],q[1]; +cx q[11],q[3]; +cx q[10],q[13]; +cx q[8],q[18]; +cx q[6],q[7]; +cx q[20],q[18]; +cx q[17],q[19]; +cx q[14],q[16]; +cx q[11],q[13]; +cx q[29],q[6]; +cx q[27],q[21]; +cx q[23],q[30]; +cx q[12],q[15]; +cx q[9],q[8]; +cx q[5],q[28]; +cx q[4],q[26]; +cx q[3],q[10]; +cx q[2],q[25]; +cx q[1],q[24]; +cx q[0],q[7]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_1.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_1.qasm new file mode 100644 index 000000000..7669ce99f --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_1.qasm @@ -0,0 +1,70 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[31]; +h q[0]; +h q[2]; +h q[7]; +cx q[7],q[6]; +h q[9]; +cx q[9],q[8]; +cx q[8],q[6]; +h q[11]; +h q[13]; +h q[16]; +cx q[16],q[14]; +h q[17]; +h q[19]; +h q[20]; +cx q[16],q[22]; +cx q[0],q[16]; +cx q[0],q[7]; +h q[23]; +cx q[23],q[15]; +cx q[22],q[15]; +cx q[15],q[12]; +cx q[19],q[22]; +cx q[17],q[19]; +h q[24]; +h q[26]; +cx q[24],q[26]; +cx q[24],q[21]; +cx q[13],q[21]; +cx q[11],q[13]; +cx q[9],q[24]; +cx q[9],q[16]; +cx q[16],q[6]; +cx q[9],q[15]; +h q[27]; +cx q[27],q[10]; +cx q[10],q[3]; +cx q[10],q[21]; +cx q[13],q[10]; +cx q[27],q[26]; +cx q[26],q[24]; +cx q[27],q[1]; +cx q[1],q[4]; +cx q[24],q[1]; +cx q[26],q[4]; +cx q[27],q[7]; +cx q[21],q[27]; +cx q[2],q[28]; +cx q[28],q[25]; +cx q[19],q[25]; +cx q[22],q[28]; +cx q[0],q[29]; +cx q[6],q[29]; +cx q[7],q[0]; +h q[30]; +cx q[30],q[18]; +cx q[14],q[30]; +cx q[14],q[5]; +cx q[15],q[30]; +cx q[18],q[23]; +cx q[2],q[5]; +cx q[17],q[2]; +cx q[20],q[18]; +cx q[18],q[8]; +cx q[20],q[9]; +cx q[3],q[14]; +cx q[11],q[3]; +cx q[16],q[14]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_2.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_2.qasm new file mode 100644 index 000000000..4d2c2d5c8 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_2.qasm @@ -0,0 +1,75 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[31]; +h q[1]; +h q[4]; +h q[6]; +h q[7]; +h q[8]; +h q[9]; +h q[10]; +h q[11]; +h q[13]; +h q[14]; +h q[15]; +h q[17]; +h q[19]; +h q[23]; +h q[25]; +cx q[23],q[0]; +cx q[13],q[3]; +cx q[1],q[27]; +cx q[6],q[28]; +cx q[15],q[30]; +cx q[14],q[16]; +cx q[7],q[16]; +cx q[8],q[30]; +cx q[19],q[28]; +cx q[25],q[2]; +cx q[9],q[21]; +cx q[11],q[13]; +cx q[15],q[18]; +cx q[23],q[27]; +cx q[6],q[29]; +cx q[1],q[21]; +cx q[3],q[24]; +cx q[9],q[30]; +cx q[0],q[15]; +cx q[19],q[25]; +cx q[4],q[26]; +cx q[17],q[5]; +cx q[10],q[27]; +cx q[16],q[23]; +cx q[13],q[28]; +cx q[4],q[27]; +cx q[9],q[20]; +cx q[10],q[21]; +cx q[18],q[12]; +cx q[0],q[29]; +cx q[1],q[24]; +cx q[11],q[26]; +cx q[7],q[28]; +cx q[14],q[30]; +cx q[16],q[15]; +cx q[13],q[23]; +cx q[25],q[17]; +cx q[11],q[24]; +cx q[8],q[18]; +cx q[26],q[21]; +cx q[13],q[15]; +cx q[29],q[30]; +cx q[25],q[22]; +cx q[16],q[27]; +cx q[28],q[17]; +cx q[23],q[20]; +cx q[5],q[22]; +cx q[3],q[26]; +cx q[2],q[28]; +cx q[6],q[16]; +cx q[7],q[29]; +cx q[10],q[13]; +cx q[11],q[27]; +cx q[30],q[23]; +cx q[20],q[21]; +cx q[15],q[18]; +cx q[17],q[25]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_3.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_3.qasm new file mode 100644 index 000000000..7e5d1256e --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_4_8_8_d7_v1/cc_4_8_8_d7_heuristic_3.qasm @@ -0,0 +1,90 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[31]; +h q[0]; +h q[1]; +h q[2]; +h q[4]; +h q[6]; +h q[7]; +h q[8]; +h q[9]; +h q[11]; +h q[12]; +h q[13]; +h q[15]; +h q[19]; +h q[22]; +h q[24]; +cx q[6],q[21]; +cx q[15],q[20]; +cx q[0],q[21]; +cx q[13],q[10]; +cx q[2],q[28]; +cx q[6],q[25]; +cx q[19],q[17]; +cx q[24],q[21]; +cx q[11],q[13]; +cx q[22],q[27]; +cx q[7],q[25]; +cx q[9],q[23]; +cx q[15],q[14]; +cx q[6],q[28]; +cx q[17],q[29]; +cx q[10],q[21]; +cx q[9],q[30]; +cx q[14],q[16]; +cx q[7],q[23]; +cx q[0],q[29]; +cx q[11],q[28]; +cx q[27],q[5]; +cx q[24],q[3]; +cx q[12],q[18]; +cx q[17],q[13]; +cx q[6],q[15]; +cx q[1],q[21]; +cx q[24],q[13]; +cx q[2],q[17]; +cx q[7],q[28]; +cx q[11],q[22]; +cx q[3],q[27]; +cx q[12],q[15]; +cx q[10],q[23]; +cx q[4],q[26]; +cx q[29],q[30]; +cx q[25],q[16]; +cx q[12],q[23]; +cx q[2],q[14]; +cx q[5],q[25]; +cx q[1],q[24]; +cx q[8],q[18]; +cx q[0],q[15]; +cx q[4],q[21]; +cx q[19],q[22]; +cx q[9],q[20]; +cx q[3],q[28]; +cx q[6],q[29]; +cx q[16],q[27]; +cx q[8],q[23]; +cx q[2],q[22]; +cx q[11],q[24]; +cx q[1],q[26]; +cx q[3],q[25]; +cx q[6],q[9]; +cx q[19],q[10]; +cx q[0],q[20]; +cx q[18],q[30]; +cx q[21],q[27]; +cx q[17],q[16]; +cx q[28],q[15]; +cx q[11],q[5]; +cx q[19],q[6]; +cx q[7],q[29]; +cx q[24],q[26]; +cx q[13],q[23]; +cx q[22],q[27]; +cx q[14],q[30]; +cx q[16],q[21]; +cx q[25],q[17]; +cx q[28],q[20]; +cx q[15],q[18]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_0.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_0.qasm new file mode 100644 index 000000000..c7bfbf84d --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_0.qasm @@ -0,0 +1,39 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[19]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +h q[6]; +h q[10]; +h q[12]; +cx q[6],q[16]; +cx q[4],q[13]; +cx q[3],q[7]; +cx q[12],q[17]; +cx q[10],q[18]; +cx q[7],q[11]; +cx q[6],q[3]; +cx q[4],q[8]; +cx q[2],q[16]; +cx q[1],q[15]; +cx q[0],q[14]; +cx q[11],q[12]; +cx q[10],q[13]; +cx q[8],q[9]; +cx q[6],q[0]; +cx q[5],q[2]; +cx q[4],q[3]; +cx q[1],q[7]; +cx q[17],q[18]; +cx q[14],q[15]; +cx q[5],q[9]; +cx q[16],q[4]; +cx q[13],q[11]; +cx q[12],q[10]; +cx q[7],q[6]; +cx q[2],q[8]; +cx q[0],q[1]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_1.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_1.qasm new file mode 100644 index 000000000..88577d33c --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_1.qasm @@ -0,0 +1,39 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[19]; +h q[2]; +h q[4]; +cx q[4],q[3]; +h q[5]; +h q[6]; +cx q[6],q[0]; +cx q[0],q[1]; +cx q[6],q[3]; +h q[7]; +cx q[4],q[9]; +cx q[5],q[9]; +h q[12]; +cx q[12],q[11]; +cx q[11],q[3]; +h q[13]; +cx q[13],q[10]; +cx q[4],q[13]; +cx q[13],q[11]; +h q[14]; +cx q[7],q[15]; +cx q[12],q[7]; +cx q[14],q[15]; +cx q[14],q[0]; +cx q[15],q[1]; +cx q[2],q[16]; +cx q[2],q[8]; +cx q[5],q[2]; +cx q[6],q[16]; +cx q[16],q[4]; +cx q[7],q[6]; +cx q[9],q[8]; +h q[17]; +cx q[17],q[12]; +cx q[10],q[18]; +cx q[12],q[10]; +cx q[17],q[18]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_2.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_2.qasm new file mode 100644 index 000000000..b151c0b3e --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_2.qasm @@ -0,0 +1,39 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[19]; +h q[6]; +h q[7]; +h q[9]; +h q[10]; +h q[12]; +h q[13]; +h q[14]; +h q[15]; +h q[16]; +cx q[7],q[3]; +cx q[13],q[3]; +cx q[6],q[3]; +cx q[7],q[11]; +cx q[13],q[4]; +cx q[9],q[5]; +cx q[12],q[17]; +cx q[15],q[7]; +cx q[16],q[2]; +cx q[10],q[18]; +cx q[6],q[1]; +cx q[14],q[15]; +cx q[4],q[9]; +cx q[10],q[13]; +cx q[11],q[12]; +cx q[1],q[0]; +cx q[6],q[16]; +cx q[2],q[8]; +cx q[5],q[2]; +cx q[14],q[0]; +cx q[17],q[18]; +cx q[13],q[11]; +cx q[7],q[6]; +cx q[16],q[4]; +cx q[12],q[10]; +cx q[9],q[8]; +cx q[15],q[1]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_3.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_3.qasm new file mode 100644 index 000000000..856657b85 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5/cc_6_6_6_d5_heuristic_3.qasm @@ -0,0 +1,39 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[19]; +h q[2]; +h q[5]; +h q[6]; +h q[9]; +h q[10]; +h q[12]; +h q[14]; +h q[15]; +h q[17]; +cx q[9],q[3]; +cx q[6],q[0]; +cx q[12],q[3]; +cx q[2],q[16]; +cx q[12],q[11]; +cx q[6],q[3]; +cx q[15],q[7]; +cx q[9],q[4]; +cx q[10],q[13]; +cx q[14],q[15]; +cx q[5],q[9]; +cx q[17],q[12]; +cx q[10],q[18]; +cx q[11],q[7]; +cx q[0],q[16]; +cx q[4],q[13]; +cx q[6],q[1]; +cx q[2],q[8]; +cx q[5],q[2]; +cx q[14],q[0]; +cx q[17],q[18]; +cx q[13],q[11]; +cx q[7],q[6]; +cx q[16],q[4]; +cx q[12],q[10]; +cx q[9],q[8]; +cx q[15],q[1]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5_v1/cc_6_6_6_heuristic_0.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5_v1/cc_6_6_6_heuristic_0.qasm new file mode 100644 index 000000000..3d4a04424 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5_v1/cc_6_6_6_heuristic_0.qasm @@ -0,0 +1,39 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[19]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +h q[10]; +h q[14]; +h q[17]; +cx q[3],q[11]; +cx q[4],q[13]; +cx q[2],q[16]; +cx q[1],q[15]; +cx q[0],q[3]; +cx q[11],q[12]; +cx q[10],q[18]; +cx q[4],q[8]; +cx q[1],q[7]; +cx q[0],q[16]; +cx q[3],q[6]; +cx q[17],q[12]; +cx q[14],q[0]; +cx q[11],q[7]; +cx q[10],q[13]; +cx q[8],q[9]; +cx q[5],q[2]; +cx q[4],q[3]; +cx q[1],q[6]; +cx q[17],q[18]; +cx q[14],q[15]; +cx q[5],q[9]; +cx q[16],q[4]; +cx q[13],q[11]; +cx q[12],q[10]; +cx q[2],q[8]; +cx q[0],q[1]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5_v1/cc_6_6_6_heuristic_1.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5_v1/cc_6_6_6_heuristic_1.qasm new file mode 100644 index 000000000..b2a0392a5 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5_v1/cc_6_6_6_heuristic_1.qasm @@ -0,0 +1,39 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[19]; +h q[1]; +h q[3]; +h q[5]; +cx q[3],q[6]; +cx q[6],q[0]; +h q[8]; +cx q[8],q[2]; +h q[9]; +cx q[9],q[3]; +cx q[3],q[4]; +h q[11]; +cx q[11],q[7]; +cx q[11],q[10]; +cx q[11],q[3]; +cx q[10],q[12]; +h q[14]; +cx q[14],q[0]; +cx q[1],q[15]; +cx q[1],q[7]; +cx q[0],q[1]; +cx q[14],q[15]; +cx q[8],q[16]; +cx q[6],q[16]; +cx q[7],q[6]; +cx q[8],q[4]; +h q[17]; +h q[18]; +cx q[18],q[13]; +cx q[17],q[18]; +cx q[17],q[12]; +cx q[18],q[10]; +cx q[9],q[13]; +cx q[13],q[11]; +cx q[5],q[9]; +cx q[5],q[2]; +cx q[9],q[8]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5_v1/cc_6_6_6_heuristic_2.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5_v1/cc_6_6_6_heuristic_2.qasm new file mode 100644 index 000000000..c9918cbc7 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d5_v1/cc_6_6_6_heuristic_2.qasm @@ -0,0 +1,39 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[19]; +h q[12]; +h q[10]; +h q[15]; +h q[3]; +h q[6]; +h q[14]; +h q[8]; +h q[17]; +h q[5]; +cx q[3],q[4]; +cx q[6],q[16]; +cx q[15],q[7]; +cx q[10],q[18]; +cx q[12],q[3]; +cx q[4],q[9]; +cx q[8],q[2]; +cx q[6],q[1]; +cx q[10],q[13]; +cx q[12],q[7]; +cx q[3],q[11]; +cx q[5],q[9]; +cx q[17],q[12]; +cx q[4],q[13]; +cx q[8],q[16]; +cx q[1],q[0]; +cx q[14],q[15]; +cx q[6],q[3]; +cx q[10],q[11]; +cx q[5],q[2]; +cx q[17],q[18]; +cx q[14],q[0]; +cx q[7],q[6]; +cx q[16],q[4]; +cx q[9],q[8]; +cx q[15],q[1]; +cx q[12],q[10]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_0.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_0.qasm new file mode 100644 index 000000000..f373d1dec --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_0.qasm @@ -0,0 +1,81 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[37]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +h q[6]; +h q[7]; +h q[8]; +h q[10]; +h q[11]; +h q[15]; +h q[17]; +h q[18]; +h q[20]; +h q[25]; +h q[28]; +h q[33]; +cx q[10],q[16]; +cx q[8],q[26]; +cx q[5],q[35]; +cx q[4],q[34]; +cx q[3],q[36]; +cx q[25],q[35]; +cx q[18],q[31]; +cx q[11],q[23]; +cx q[10],q[4]; +cx q[8],q[16]; +cx q[7],q[13]; +cx q[6],q[12]; +cx q[5],q[29]; +cx q[3],q[22]; +cx q[0],q[32]; +cx q[33],q[6]; +cx q[23],q[34]; +cx q[22],q[26]; +cx q[18],q[24]; +cx q[17],q[10]; +cx q[15],q[19]; +cx q[13],q[25]; +cx q[12],q[3]; +cx q[11],q[7]; +cx q[8],q[14]; +cx q[5],q[9]; +cx q[2],q[30]; +cx q[1],q[27]; +cx q[0],q[29]; +cx q[32],q[26]; +cx q[31],q[33]; +cx q[28],q[9]; +cx q[22],q[23]; +cx q[20],q[17]; +cx q[18],q[21]; +cx q[15],q[12]; +cx q[14],q[24]; +cx q[11],q[1]; +cx q[8],q[7]; +cx q[5],q[3]; +cx q[2],q[13]; +cx q[0],q[16]; +cx q[28],q[19]; +cx q[27],q[30]; +cx q[20],q[31]; +cx q[16],q[24]; +cx q[7],q[23]; +cx q[3],q[29]; +cx q[35],q[36]; +cx q[34],q[8]; +cx q[33],q[32]; +cx q[25],q[22]; +cx q[17],q[21]; +cx q[13],q[11]; +cx q[12],q[5]; +cx q[10],q[18]; +cx q[9],q[15]; +cx q[6],q[0]; +cx q[4],q[14]; +cx q[1],q[2]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_1.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_1.qasm new file mode 100644 index 000000000..e2d73cc66 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_1.qasm @@ -0,0 +1,81 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[37]; +h q[0]; +h q[1]; +h q[6]; +h q[7]; +h q[10]; +h q[13]; +h q[15]; +h q[18]; +h q[20]; +h q[21]; +h q[22]; +h q[27]; +h q[28]; +h q[29]; +h q[30]; +h q[33]; +h q[34]; +h q[35]; +cx q[7],q[8]; +cx q[13],q[7]; +cx q[6],q[3]; +cx q[10],q[24]; +cx q[33],q[6]; +cx q[0],q[24]; +cx q[18],q[31]; +cx q[29],q[5]; +cx q[22],q[23]; +cx q[3],q[12]; +cx q[8],q[26]; +cx q[1],q[11]; +cx q[13],q[25]; +cx q[10],q[4]; +cx q[5],q[3]; +cx q[31],q[24]; +cx q[35],q[25]; +cx q[30],q[13]; +cx q[34],q[4]; +cx q[11],q[2]; +cx q[0],q[32]; +cx q[29],q[9]; +cx q[15],q[12]; +cx q[18],q[33]; +cx q[22],q[36]; +cx q[23],q[26]; +cx q[8],q[16]; +cx q[21],q[10]; +cx q[28],q[9]; +cx q[0],q[29]; +cx q[20],q[31]; +cx q[1],q[34]; +cx q[15],q[19]; +cx q[8],q[14]; +cx q[22],q[3]; +cx q[2],q[23]; +cx q[27],q[30]; +cx q[21],q[17]; +cx q[11],q[7]; +cx q[5],q[35]; +cx q[18],q[16]; +cx q[32],q[26]; +cx q[27],q[1]; +cx q[20],q[17]; +cx q[28],q[19]; +cx q[24],q[16]; +cx q[3],q[29]; +cx q[7],q[23]; +cx q[12],q[5]; +cx q[25],q[22]; +cx q[35],q[36]; +cx q[10],q[18]; +cx q[34],q[8]; +cx q[30],q[2]; +cx q[13],q[11]; +cx q[4],q[14]; +cx q[31],q[21]; +cx q[6],q[0]; +cx q[9],q[15]; +cx q[33],q[32]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_2.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_2.qasm new file mode 100644 index 000000000..ee88e6550 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_2.qasm @@ -0,0 +1,98 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[37]; +h q[1]; +h q[3]; +h q[4]; +h q[5]; +h q[6]; +h q[7]; +h q[8]; +h q[10]; +h q[11]; +h q[18]; +h q[19]; +h q[20]; +h q[22]; +h q[25]; +h q[28]; +h q[30]; +h q[32]; +h q[34]; +cx q[30],q[13]; +cx q[32],q[16]; +cx q[11],q[30]; +cx q[1],q[26]; +cx q[34],q[36]; +cx q[20],q[24]; +cx q[7],q[14]; +cx q[32],q[33]; +cx q[3],q[23]; +cx q[25],q[9]; +cx q[4],q[14]; +cx q[7],q[23]; +cx q[22],q[36]; +cx q[19],q[35]; +cx q[5],q[29]; +cx q[34],q[2]; +cx q[11],q[27]; +cx q[8],q[20]; +cx q[18],q[31]; +cx q[13],q[26]; +cx q[3],q[25]; +cx q[33],q[0]; +cx q[10],q[32]; +cx q[35],q[15]; +cx q[28],q[12]; +cx q[0],q[29]; +cx q[9],q[23]; +cx q[22],q[25]; +cx q[1],q[27]; +cx q[8],q[16]; +cx q[6],q[33]; +cx q[5],q[19]; +cx q[24],q[17]; +cx q[31],q[32]; +cx q[2],q[14]; +cx q[26],q[36]; +cx q[30],q[20]; +cx q[10],q[24]; +cx q[22],q[35]; +cx q[3],q[29]; +cx q[8],q[34]; +cx q[17],q[21]; +cx q[12],q[36]; +cx q[6],q[16]; +cx q[5],q[25]; +cx q[15],q[32]; +cx q[9],q[28]; +cx q[30],q[23]; +cx q[33],q[26]; +cx q[27],q[14]; +cx q[20],q[31]; +cx q[5],q[36]; +cx q[2],q[26]; +cx q[10],q[20]; +cx q[18],q[21]; +cx q[12],q[29]; +cx q[27],q[34]; +cx q[33],q[24]; +cx q[25],q[35]; +cx q[19],q[23]; +cx q[30],q[16]; +cx q[28],q[32]; +cx q[14],q[31]; +cx q[2],q[30]; +cx q[10],q[21]; +cx q[5],q[28]; +cx q[15],q[25]; +cx q[4],q[16]; +cx q[12],q[19]; +cx q[6],q[29]; +cx q[13],q[27]; +cx q[7],q[34]; +cx q[14],q[20]; +cx q[36],q[35]; +cx q[32],q[33]; +cx q[23],q[26]; +cx q[31],q[24]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_3.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_3.qasm new file mode 100644 index 000000000..01d706cb5 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/cc_6_6_6_d7/cc_6_6_6_d7_heuristic_3.qasm @@ -0,0 +1,98 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[37]; +h q[4]; +h q[6]; +h q[7]; +h q[10]; +h q[11]; +h q[12]; +h q[13]; +h q[14]; +h q[15]; +h q[16]; +h q[21]; +h q[25]; +h q[28]; +h q[29]; +h q[30]; +h q[33]; +h q[34]; +h q[36]; +cx q[14],q[27]; +cx q[36],q[5]; +cx q[25],q[35]; +cx q[29],q[36]; +cx q[14],q[1]; +cx q[29],q[3]; +cx q[34],q[31]; +cx q[16],q[0]; +cx q[13],q[27]; +cx q[5],q[35]; +cx q[7],q[14]; +cx q[28],q[36]; +cx q[12],q[26]; +cx q[33],q[18]; +cx q[11],q[23]; +cx q[7],q[23]; +cx q[21],q[31]; +cx q[11],q[27]; +cx q[30],q[2]; +cx q[6],q[16]; +cx q[33],q[20]; +cx q[1],q[35]; +cx q[28],q[26]; +cx q[12],q[29]; +cx q[1],q[24]; +cx q[11],q[30]; +cx q[20],q[31]; +cx q[4],q[14]; +cx q[13],q[35]; +cx q[26],q[33]; +cx q[16],q[29]; +cx q[15],q[36]; +cx q[10],q[20]; +cx q[13],q[31]; +cx q[12],q[35]; +cx q[25],q[22]; +cx q[4],q[26]; +cx q[11],q[16]; +cx q[6],q[33]; +cx q[34],q[8]; +cx q[7],q[24]; +cx q[5],q[29]; +cx q[30],q[14]; +cx q[4],q[34]; +cx q[28],q[9]; +cx q[13],q[16]; +cx q[15],q[33]; +cx q[11],q[31]; +cx q[21],q[17]; +cx q[25],q[23]; +cx q[5],q[19]; +cx q[0],q[32]; +cx q[36],q[35]; +cx q[20],q[24]; +cx q[14],q[26]; +cx q[5],q[28]; +cx q[10],q[33]; +cx q[13],q[23]; +cx q[6],q[32]; +cx q[12],q[19]; +cx q[2],q[35]; +cx q[15],q[26]; +cx q[34],q[16]; +cx q[20],q[21]; +cx q[30],q[24]; +cx q[14],q[31]; +cx q[36],q[25]; +cx q[13],q[30]; +cx q[12],q[28]; +cx q[15],q[19]; +cx q[35],q[36]; +cx q[25],q[23]; +cx q[14],q[34]; +cx q[29],q[26]; +cx q[33],q[32]; +cx q[16],q[24]; +cx q[31],q[20]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_0.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_0.qasm new file mode 100644 index 000000000..afd1f0bdb --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_0.qasm @@ -0,0 +1,52 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[20]; +h q[0]; +h q[1]; +h q[2]; +h q[3]; +h q[4]; +h q[5]; +h q[6]; +h q[7]; +h q[8]; +cx q[6],q[10]; +cx q[7],q[11]; +cx q[7],q[9]; +cx q[4],q[13]; +cx q[8],q[14]; +cx q[5],q[14]; +cx q[3],q[14]; +cx q[2],q[14]; +cx q[5],q[10]; +cx q[4],q[10]; +cx q[14],q[10]; +cx q[6],q[15]; +cx q[2],q[15]; +cx q[1],q[16]; +cx q[1],q[13]; +cx q[3],q[16]; +cx q[8],q[17]; +cx q[3],q[17]; +cx q[11],q[18]; +cx q[4],q[18]; +cx q[15],q[18]; +cx q[1],q[18]; +cx q[6],q[11]; +cx q[0],q[19]; +cx q[0],q[12]; +cx q[0],q[14]; +cx q[13],q[12]; +cx q[14],q[15]; +cx q[17],q[12]; +cx q[5],q[19]; +cx q[19],q[16]; +cx q[10],q[16]; +cx q[16],q[17]; +cx q[19],q[11]; +cx q[12],q[19]; +cx q[2],q[11]; +cx q[5],q[9]; +cx q[13],q[9]; +cx q[0],q[9]; +cx q[10],q[13]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_1.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_1.qasm new file mode 100644 index 000000000..8edc30c1a --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_1.qasm @@ -0,0 +1,48 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[20]; +h q[1]; +h q[4]; +h q[6]; +h q[7]; +h q[8]; +h q[9]; +cx q[9],q[0]; +cx q[7],q[9]; +cx q[0],q[12]; +cx q[1],q[13]; +cx q[4],q[13]; +cx q[13],q[11]; +h q[14]; +cx q[14],q[2]; +cx q[6],q[15]; +cx q[2],q[15]; +cx q[15],q[11]; +h q[16]; +cx q[16],q[17]; +cx q[17],q[3]; +cx q[8],q[16]; +cx q[16],q[10]; +cx q[16],q[14]; +cx q[4],q[10]; +cx q[15],q[10]; +cx q[1],q[18]; +cx q[6],q[18]; +cx q[7],q[18]; +cx q[2],q[18]; +cx q[4],q[18]; +h q[19]; +cx q[19],q[5]; +cx q[13],q[19]; +cx q[16],q[19]; +cx q[5],q[12]; +cx q[12],q[17]; +cx q[11],q[17]; +cx q[12],q[14]; +cx q[14],q[15]; +cx q[17],q[16]; +cx q[19],q[12]; +cx q[5],q[9]; +cx q[13],q[9]; +cx q[10],q[13]; +cx q[9],q[11]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_2.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_2.qasm new file mode 100644 index 000000000..d6d612ae7 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_2.qasm @@ -0,0 +1,49 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[20]; +h q[3]; +h q[6]; +h q[7]; +h q[9]; +cx q[9],q[4]; +h q[12]; +cx q[12],q[0]; +h q[13]; +cx q[13],q[10]; +cx q[13],q[11]; +h q[15]; +cx q[15],q[14]; +cx q[14],q[2]; +cx q[6],q[15]; +cx q[15],q[11]; +cx q[4],q[11]; +h q[16]; +cx q[16],q[17]; +cx q[16],q[8]; +cx q[17],q[10]; +cx q[0],q[17]; +cx q[15],q[17]; +cx q[3],q[10]; +cx q[3],q[16]; +cx q[7],q[18]; +cx q[13],q[18]; +cx q[13],q[1]; +cx q[4],q[13]; +h q[19]; +cx q[19],q[5]; +cx q[5],q[12]; +cx q[12],q[14]; +cx q[16],q[14]; +cx q[9],q[19]; +cx q[10],q[19]; +cx q[11],q[10]; +cx q[10],q[13]; +cx q[18],q[9]; +cx q[12],q[9]; +cx q[15],q[18]; +cx q[14],q[15]; +cx q[19],q[17]; +cx q[17],q[16]; +cx q[19],q[12]; +cx q[4],q[18]; +cx q[9],q[11]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_3.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_3.qasm new file mode 100644 index 000000000..ecb709500 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/eve_20_2_6/eve_20_2_6_heuristic_3.qasm @@ -0,0 +1,54 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[20]; +h q[2]; +h q[4]; +h q[5]; +h q[10]; +cx q[10],q[1]; +cx q[5],q[11]; +h q[12]; +h q[13]; +cx q[13],q[3]; +h q[15]; +cx q[3],q[16]; +h q[17]; +cx q[17],q[6]; +cx q[4],q[17]; +cx q[4],q[10]; +cx q[6],q[14]; +cx q[2],q[14]; +h q[18]; +cx q[18],q[9]; +cx q[18],q[7]; +cx q[2],q[18]; +cx q[10],q[18]; +cx q[4],q[9]; +cx q[7],q[11]; +cx q[15],q[19]; +cx q[12],q[15]; +cx q[12],q[0]; +cx q[19],q[8]; +cx q[1],q[19]; +cx q[5],q[15]; +cx q[5],q[19]; +cx q[3],q[19]; +cx q[4],q[19]; +cx q[5],q[12]; +cx q[12],q[9]; +cx q[19],q[12]; +cx q[6],q[15]; +cx q[15],q[17]; +cx q[3],q[15]; +cx q[6],q[18]; +cx q[8],q[13]; +cx q[1],q[13]; +cx q[1],q[9]; +cx q[14],q[13]; +cx q[13],q[17]; +cx q[13],q[10]; +cx q[14],q[11]; +cx q[0],q[11]; +cx q[15],q[14]; +cx q[8],q[16]; +cx q[17],q[16]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_17_1_5.stim b/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_17_1_5.stim new file mode 100644 index 000000000..53079b8f0 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_17_1_5.stim @@ -0,0 +1,63 @@ +H 3 4 6 8 14 15 16 18 20 21 22 23 27 29 33 35 37 +TICK +CX 21 2 3 31 4 32 33 5 6 34 35 7 8 36 37 9 22 10 23 13 14 24 15 25 16 26 27 17 18 28 29 19 20 30 +TICK +CX 21 1 23 12 +TICK +CX 21 0 1 28 23 11 +TICK +CX 1 30 21 31 23 32 +TICK +CX 12 30 21 36 27 31 +TICK +CX 21 2 12 28 29 30 +TICK +CX 21 25 27 28 +TICK +M 2 +CX 18 28 21 34 23 25 27 32 +TICK +CX 21 1 23 13 27 17 +H 18 +CX 35 25 +TICK +M 18 +CX 21 24 23 36 29 25 35 26 +TICK +M 1 13 17 +CX 21 0 15 25 23 34 29 26 37 36 +TICK +CX 8 36 23 12 +H 15 +CX 29 19 37 31 35 34 +TICK +M 0 15 +CX 35 7 +H 8 +CX 23 24 37 32 33 34 +TICK +M 8 12 19 +CX 6 34 37 9 23 11 22 32 33 30 +TICK +M 7 +CX 4 32 +H 6 +CX 20 30 22 31 33 26 +TICK +M 6 9 11 +CX 3 31 +H 4 +CX 33 5 16 26 +H 20 +CX 22 24 +TICK +M 4 20 +H 3 +CX 22 10 14 24 +H 16 +TICK +M 3 5 16 +H 14 +TICK +M 10 14 +TICK diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_20_2_6.stim b/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_20_2_6.stim new file mode 100644 index 000000000..8bd194d9a --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_20_2_6.stim @@ -0,0 +1,154 @@ +H 4 5 6 7 9 10 11 12 13 14 15 36 37 38 39 40 41 42 44 45 47 48 49 54 56 59 64 65 66 +TICK +CX 47 3 5 57 7 58 59 8 10 60 12 61 14 62 15 63 64 19 65 23 66 27 48 31 49 35 36 50 38 51 40 52 42 53 54 43 45 55 56 46 +TICK +CX 47 1 4 57 6 58 9 60 11 61 13 62 64 17 65 21 66 25 48 29 49 33 37 51 39 52 41 53 44 55 +TICK +CX 47 7 65 55 59 60 +TICK +CX 47 40 +TICK +CX 47 2 +TICK +CX 47 0 +TICK +CX 47 5 +TICK +CX 47 3 56 5 +TICK +CX 47 38 +TICK +M 3 +CX 47 10 +TICK +CX 47 2 48 10 +TICK +CX 48 40 47 50 +TICK +M 2 +CX 47 1 48 30 +TICK +CX 47 12 48 28 +TICK +M 1 +CX 47 0 48 7 59 12 +TICK +CX 48 31 +TICK +M 0 +CX 48 42 +TICK +M 31 +CX 66 42 48 45 +TICK +CX 48 30 56 45 66 61 +TICK +CX 48 14 66 26 56 58 +TICK +M 30 +CX 59 14 66 24 48 29 56 46 +TICK +CX 59 8 48 50 66 63 +TICK +M 29 46 +CX 66 27 48 28 65 63 +TICK +M 8 +CX 65 22 66 58 +TICK +M 27 28 +CX 7 58 65 20 66 62 +TICK +H 7 +CX 66 26 65 53 +TICK +M 7 +CX 65 23 66 52 +TICK +M 26 +CX 66 25 65 58 +TICK +M 23 +CX 6 58 65 38 66 57 +TICK +M 25 +H 6 +CX 65 22 66 24 64 57 +TICK +M 6 +CX 5 57 65 60 64 62 +TICK +M 22 24 +H 5 +CX 10 60 14 62 64 18 65 21 +TICK +M 5 +H 10 14 +CX 64 16 65 61 +TICK +M 10 14 21 +CX 12 61 65 20 64 60 +TICK +CX 9 60 +H 12 +CX 64 19 49 61 +TICK +M 12 20 +H 9 +CX 11 61 49 53 64 52 +TICK +M 9 19 +H 11 +CX 49 34 40 52 42 53 64 51 +TICK +M 11 +CX 64 18 49 32 +H 40 42 +TICK +M 40 42 +CX 49 62 64 55 +TICK +M 18 +CX 13 62 64 17 49 35 45 55 +TICK +H 13 45 +CX 49 55 64 63 +TICK +M 13 17 35 45 +CX 15 63 64 16 44 55 49 50 +TICK +H 15 +CX 49 34 36 50 +H 44 +TICK +M 15 16 44 +H 36 +CX 49 57 +TICK +M 34 36 +CX 4 57 49 33 +TICK +H 4 +CX 49 51 +TICK +M 4 33 +CX 49 32 38 51 +TICK +H 38 +CX 54 51 +TICK +M 32 38 +CX 37 51 54 52 +TICK +H 37 +CX 39 52 54 53 +TICK +M 37 +H 39 +CX 41 53 54 43 +TICK +M 39 +H 41 +TICK +M 41 43 +TICK diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_25_1_5.stim b/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_25_1_5.stim new file mode 100644 index 000000000..c439db46a --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_25_1_5.stim @@ -0,0 +1,75 @@ +H 2 3 5 6 7 17 19 21 22 23 24 25 26 28 29 30 37 38 41 45 46 47 48 49 51 +TICK +CX 28 0 38 1 2 39 3 40 41 4 5 42 6 43 7 44 45 8 46 10 47 13 29 14 48 15 49 16 17 50 51 18 19 52 30 20 21 31 22 32 23 33 24 34 25 35 26 36 37 27 +TICK +CX 46 9 47 12 28 34 48 44 +TICK +CX 47 11 12 52 28 35 38 34 48 43 +TICK +CX 6 43 12 39 28 31 38 33 47 42 48 50 +TICK +CX 28 0 5 42 +H 6 +CX 48 15 23 33 30 31 38 39 47 50 +TICK +M 0 6 15 +CX 38 1 +H 5 +CX 47 13 30 20 +H 23 +CX 37 31 46 39 49 50 +TICK +M 1 5 13 20 23 +CX 49 16 37 32 47 35 46 50 +TICK +M 16 +CX 17 50 22 32 47 36 +TICK +CX 47 12 +H 17 22 +TICK +M 12 17 22 +CX 47 44 +TICK +CX 10 44 47 11 +TICK +M 11 +CX 10 40 45 44 +TICK +CX 7 44 46 10 45 40 +TICK +M 10 +H 7 +CX 45 39 41 40 46 52 +TICK +M 7 +CX 2 39 3 40 45 8 46 9 41 36 51 52 +TICK +M 8 9 +H 2 3 +CX 51 18 19 52 41 35 37 36 +TICK +M 2 3 18 +CX 41 4 +H 19 +CX 26 36 37 27 29 35 +TICK +M 4 19 27 +CX 25 35 +H 26 +CX 29 34 +TICK +M 26 +CX 24 34 +H 25 +CX 29 31 +TICK +M 25 +CX 29 14 21 31 +H 24 +TICK +M 14 24 +H 21 +TICK +M 21 +TICK diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_31_1_7.stim b/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_31_1_7.stim new file mode 100644 index 000000000..65c1c74db --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/flag_at_origin/cc_31_1_7.stim @@ -0,0 +1,202 @@ +H 8 9 10 11 16 17 18 19 20 21 22 24 29 32 33 34 35 37 43 44 45 47 53 54 55 56 57 58 59 64 65 66 68 69 70 71 75 77 79 82 85 87 89 92 94 95 97 99 +TICK +CX 69 3 79 7 10 80 11 81 82 15 18 83 22 84 85 23 24 86 87 28 29 88 70 30 89 31 34 90 35 91 92 36 37 93 94 41 95 42 45 96 97 46 47 98 71 51 99 52 53 72 56 73 59 74 75 63 66 76 77 67 68 78 +TICK +CX 69 1 79 5 9 80 82 13 17 83 20 84 87 26 33 90 94 39 44 96 71 49 55 73 58 74 75 61 65 76 85 86 92 91 +TICK +CX 8 80 16 83 32 90 43 96 54 73 70 55 57 74 64 76 85 65 69 72 94 81 +TICK +CX 85 9 77 55 69 78 70 72 94 96 +TICK +CX 69 2 92 9 85 23 94 40 45 96 70 74 77 78 +TICK +M 23 +CX 69 0 70 30 94 38 +H 45 +CX 77 58 59 74 92 65 +TICK +M 30 45 +CX 92 36 +H 59 +CX 77 67 69 76 +TICK +M 59 67 36 +CX 69 3 66 76 +TICK +M 3 +H 66 +CX 69 83 +TICK +M 66 +CX 18 83 69 73 +TICK +CX 69 2 +H 18 +CX 56 73 +TICK +M 2 18 +H 56 +CX 69 80 94 73 +TICK +M 56 +CX 69 1 10 80 94 41 +TICK +M 1 41 +H 10 +CX 69 84 75 80 94 90 +TICK +M 10 +CX 69 0 75 33 34 90 94 84 +TICK +M 0 +CX 21 84 +H 34 +CX 94 40 75 62 +TICK +M 34 40 +CX 19 84 94 58 75 60 +TICK +CX 94 39 75 86 87 84 +TICK +M 39 +CX 22 84 75 63 87 96 94 88 +TICK +M 63 +CX 75 17 +H 22 +CX 87 27 94 38 95 88 97 96 +TICK +M 22 38 +CX 87 25 75 91 95 81 +TICK +CX 75 62 79 91 87 88 95 93 +TICK +M 62 +CX 87 28 29 88 35 91 95 42 75 44 +TICK +M 28 42 +H 29 35 +CX 75 61 87 74 +TICK +M 61 29 35 +CX 87 73 75 98 +TICK +CX 87 27 55 73 75 60 79 98 +TICK +M 60 27 +CX 79 6 +H 55 +CX 87 93 99 98 +TICK +M 55 +CX 79 4 87 26 47 98 82 93 +TICK +M 26 +CX 79 17 37 93 +H 47 +CX 82 73 87 90 +TICK +M 47 +CX 79 7 82 14 87 25 +H 37 +CX 54 73 +TICK +M 7 25 37 +CX 82 12 79 33 +H 54 +TICK +M 54 +CX 79 44 +TICK +CX 79 6 44 96 +TICK +M 6 +H 44 +CX 79 86 +TICK +M 44 +CX 79 5 24 86 +TICK +M 5 +H 24 +CX 79 76 +TICK +M 24 +CX 79 4 99 76 +TICK +M 4 +CX 65 76 99 80 +TICK +CX 9 80 99 52 +H 65 +CX 71 76 +TICK +M 65 52 +H 9 +CX 64 76 71 80 +TICK +M 9 +CX 8 80 71 50 +H 64 +TICK +M 64 +H 8 +CX 71 48 +TICK +M 8 +CX 71 84 +TICK +CX 71 51 97 84 +TICK +M 51 +CX 21 84 71 74 +TICK +H 21 +CX 58 74 71 83 89 84 +TICK +M 21 +CX 20 84 71 50 +H 58 +CX 82 74 97 83 +TICK +M 50 58 +CX 82 15 17 83 +H 20 +CX 97 46 57 74 71 78 +TICK +M 15 20 46 +H 17 +CX 71 49 +H 57 +CX 68 78 82 81 89 83 +TICK +M 49 57 17 +CX 11 81 16 83 +H 68 +CX 71 72 82 84 89 90 +TICK +M 68 +H 11 +CX 82 14 +H 16 +CX 19 84 89 31 33 90 71 48 53 72 +TICK +M 48 11 14 16 31 +H 19 33 53 +CX 82 96 +TICK +M 53 19 33 +CX 82 13 43 96 +TICK +M 13 +H 43 +CX 82 90 +TICK +M 43 +CX 82 12 32 90 +TICK +M 12 +H 32 +TICK +M 32 +TICK diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_0.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_0.qasm new file mode 100644 index 000000000..6a4a6d92c --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_0.qasm @@ -0,0 +1,43 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[25]; +h q[0]; +h q[2]; +h q[4]; +h q[5]; +h q[6]; +cx q[2],q[8]; +h q[9]; +cx q[5],q[10]; +cx q[6],q[12]; +cx q[6],q[7]; +cx q[0],q[6]; +cx q[0],q[5]; +cx q[0],q[1]; +cx q[7],q[11]; +cx q[2],q[7]; +cx q[2],q[3]; +cx q[9],q[14]; +cx q[9],q[13]; +cx q[9],q[8]; +cx q[4],q[9]; +h q[15]; +cx q[15],q[16]; +cx q[15],q[10]; +cx q[16],q[11]; +h q[17]; +cx q[17],q[18]; +cx q[17],q[12]; +cx q[18],q[13]; +h q[19]; +cx q[19],q[14]; +h q[20]; +cx q[20],q[15]; +h q[21]; +cx q[21],q[22]; +cx q[21],q[16]; +cx q[22],q[17]; +h q[23]; +cx q[23],q[24]; +cx q[23],q[18]; +cx q[24],q[19]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_1.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_1.qasm new file mode 100644 index 000000000..6a4a6d92c --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_1.qasm @@ -0,0 +1,43 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[25]; +h q[0]; +h q[2]; +h q[4]; +h q[5]; +h q[6]; +cx q[2],q[8]; +h q[9]; +cx q[5],q[10]; +cx q[6],q[12]; +cx q[6],q[7]; +cx q[0],q[6]; +cx q[0],q[5]; +cx q[0],q[1]; +cx q[7],q[11]; +cx q[2],q[7]; +cx q[2],q[3]; +cx q[9],q[14]; +cx q[9],q[13]; +cx q[9],q[8]; +cx q[4],q[9]; +h q[15]; +cx q[15],q[16]; +cx q[15],q[10]; +cx q[16],q[11]; +h q[17]; +cx q[17],q[18]; +cx q[17],q[12]; +cx q[18],q[13]; +h q[19]; +cx q[19],q[14]; +h q[20]; +cx q[20],q[15]; +h q[21]; +cx q[21],q[22]; +cx q[21],q[16]; +cx q[22],q[17]; +h q[23]; +cx q[23],q[24]; +cx q[23],q[18]; +cx q[24],q[19]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_2.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_2.qasm new file mode 100644 index 000000000..6a4a6d92c --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_2.qasm @@ -0,0 +1,43 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[25]; +h q[0]; +h q[2]; +h q[4]; +h q[5]; +h q[6]; +cx q[2],q[8]; +h q[9]; +cx q[5],q[10]; +cx q[6],q[12]; +cx q[6],q[7]; +cx q[0],q[6]; +cx q[0],q[5]; +cx q[0],q[1]; +cx q[7],q[11]; +cx q[2],q[7]; +cx q[2],q[3]; +cx q[9],q[14]; +cx q[9],q[13]; +cx q[9],q[8]; +cx q[4],q[9]; +h q[15]; +cx q[15],q[16]; +cx q[15],q[10]; +cx q[16],q[11]; +h q[17]; +cx q[17],q[18]; +cx q[17],q[12]; +cx q[18],q[13]; +h q[19]; +cx q[19],q[14]; +h q[20]; +cx q[20],q[15]; +h q[21]; +cx q[21],q[22]; +cx q[21],q[16]; +cx q[22],q[17]; +h q[23]; +cx q[23],q[24]; +cx q[23],q[18]; +cx q[24],q[19]; diff --git a/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_3.qasm b/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_3.qasm new file mode 100644 index 000000000..6a4a6d92c --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/circuits/rotated_surface_d5/rotated_surface_d5_heuristic_3.qasm @@ -0,0 +1,43 @@ +OPENQASM 2.0; +include "qelib1.inc"; +qreg q[25]; +h q[0]; +h q[2]; +h q[4]; +h q[5]; +h q[6]; +cx q[2],q[8]; +h q[9]; +cx q[5],q[10]; +cx q[6],q[12]; +cx q[6],q[7]; +cx q[0],q[6]; +cx q[0],q[5]; +cx q[0],q[1]; +cx q[7],q[11]; +cx q[2],q[7]; +cx q[2],q[3]; +cx q[9],q[14]; +cx q[9],q[13]; +cx q[9],q[8]; +cx q[4],q[9]; +h q[15]; +cx q[15],q[16]; +cx q[15],q[10]; +cx q[16],q[11]; +h q[17]; +cx q[17],q[18]; +cx q[17],q[12]; +cx q[18],q[13]; +h q[19]; +cx q[19],q[14]; +h q[20]; +cx q[20],q[15]; +h q[21]; +cx q[21],q[22]; +cx q[21],q[16]; +cx q[22],q[17]; +h q[23]; +cx q[23],q[24]; +cx q[23],q[18]; +cx q[24],q[19]; diff --git a/scripts/ft_stateprep/eval_circ_mod/estimate_logical_error_rate.py b/scripts/ft_stateprep/eval_circ_mod/estimate_logical_error_rate.py new file mode 100644 index 000000000..17626eaea --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/estimate_logical_error_rate.py @@ -0,0 +1,112 @@ +# Copyright (c) 2023 - 2026 Chair for Design Automation, TUM +# All rights reserved. +# +# SPDX-License-Identifier: MIT +# +# Licensed under the MIT License + +# ruff: noqa: S301, S403 + +"""Estimate logical error rate for CSS state preparation circuits for a given code and physical error rate.""" + +from __future__ import annotations + +import argparse +import pickle +from pathlib import Path + +from qiskit import QuantumCircuit + +from mqt.qecc import CSSCode +from mqt.qecc.circuit_synthesis.noise import CircuitLevelNoiseIdlingParallel +from mqt.qecc.circuit_synthesis.simulation import SteaneNDFTStatePrepSimulator +from mqt.qecc.codes import HexagonalColorCode, RotatedSurfaceCode, SquareOctagonColorCode + + +def main() -> None: + """Run the logical error rate estimation for a given code and physical error rate.""" + available_codes = ["eve_20_2_6"] + parser = argparse.ArgumentParser(description="Estimate logical error rate for CSS state preparation circuits") + parser.add_argument( + "code", + type=str, + help="Code for which to estimate logical error rate. Available codes: " + ", ".join(available_codes), + ) + parser.add_argument("-p", "--p_error", type=float, help="Physical error rate") + parser.add_argument("-p_idle_factor", "--p_idle_factor", type=float, default=0.01, help="Idling error rate") + parser.add_argument("--zero_state", default=True, action="store_true", help="Synthesize logical |0> state.") + parser.add_argument( + "--plus_state", default=False, dest="zero_state", action="store_false", help="Synthesize logical |+> state." + ) + parser.add_argument("--x_errors", default=True, action="store_true", help="Calculate error rates for X-errors") + parser.add_argument( + "--z_errors", default=False, dest="x_errors", action="store_false", help="Calculate error rates for Z errors" + ) + parser.add_argument("-n", "--n_errors", type=int, default=500, help="Number of errors to sample") + parser.add_argument( + "-d", "--distance", type=int, default=3, help="Code Distance (only required for surface and color codes)" + ) + + args = parser.parse_args() + code_name = args.code + decoder = None + if "surface" in code_name: + d = args.distance + code = RotatedSurfaceCode(d) + code_name = f"rotated_surface_d{d}" + elif code_name == "cc_4_8_8_d7": + d = 7 + code = SquareOctagonColorCode(d) + lut_path = (Path("__file__") / "../../eval/luts/decoder_488_7.pickle").resolve() + if lut_path.exists(): + with lut_path.open("rb") as f: + decoder = pickle.load(f) + else: + msg = "LUT file not found." + raise ValueError(msg) + elif code_name == "cc_6_6_6_d7": + d = 7 + code = HexagonalColorCode(d) + elif code_name == "cc_4_8_8_d5": + d = 5 + code = SquareOctagonColorCode(d) + elif code_name == "cc_6_6_6_d5": + d = 5 + code = HexagonalColorCode(d) + elif code_name in available_codes: + prefix = (Path(__file__) / "../check_matrix/").resolve() + matrix_file = prefix / (code_name + ".txt") + code = CSSCode.from_file(matrix_file) + else: + raise ValueError("Code " + code_name + " not available. Available codes: " + ", ".join(available_codes)) + + prefix = (Path(__file__) / "../circuits/").resolve() + circ_file_core = f"{code_name}_heuristic_" + + circuits = [] + # load circuit from file + for id_ in [0, 1, 2, 3]: + circ_file = circ_file_core + str(id_) + path = prefix / code_name / (circ_file + ".qasm") + circuits.append(QuantumCircuit.from_qasm_file(path)) + + sim = SteaneNDFTStatePrepSimulator( + circ1=circuits[0], + circ2=circuits[1], + code=code, + circ3=circuits[2], + circ4=circuits[3], + decoder=decoder, + ) + p = args.p_error + noise = CircuitLevelNoiseIdlingParallel(p, p, p * 2 / 3, p, p * args.p_idle_factor) + if args.x_errors: + res = sim.logical_error_rate(noise=noise, min_errors=args.n_errors) + else: + res = sim.secondary_logical_error_rate(noise=noise, p=p, min_errors=args.n_errors) + + print(",".join([str(x) for x in res])) + + +if __name__ == "__main__": + main() diff --git a/scripts/ft_stateprep/eval_circ_mod/estimate_logical_error_rate_fao.py b/scripts/ft_stateprep/eval_circ_mod/estimate_logical_error_rate_fao.py new file mode 100644 index 000000000..0e1bbbade --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/estimate_logical_error_rate_fao.py @@ -0,0 +1,182 @@ +# Copyright (c) 2023 - 2026 Chair for Design Automation, TUM +# All rights reserved. +# +# SPDX-License-Identifier: MIT +# +# Licensed under the MIT License + +"""Estimate logical error rates for CSS state preparation circuits.""" + +from __future__ import annotations + +import argparse +from pathlib import Path + +import stim + +from mqt.qecc import CSSCode +from mqt.qecc.circuit_synthesis.circuit_utils import relabel_qubits +from mqt.qecc.circuit_synthesis.noise import CircuitLevelNoiseIdlingParallel +from mqt.qecc.circuit_synthesis.simulation import VerificationNDFTStatePrepSimulator + +AVAILABLE_CODES: list[str] = [ + "cc_17_1_5", + "cc_20_2_6", + "cc_25_1_5", + "cc_31_1_7", +] + + +def parse_args() -> argparse.Namespace: + """Parse command-line arguments.""" + parser = argparse.ArgumentParser(description="Estimate logical error rate for a given code.") + + parser.add_argument( + "code", + type=str, + help="Code name. Available: " + ", ".join(AVAILABLE_CODES), + ) + parser.add_argument("-p", "--p_error", type=float, required=True, help="Physical error rate p.") + parser.add_argument( + "-p_idle_factor", + "--p_idle_factor", + type=float, + default=0.01, + help="Multiplier for idle error probability.", + ) + parser.add_argument("--zero_state", default=True, action="store_true", help="Prepare logical |0>.") + parser.add_argument( + "--plus_state", + default=False, + dest="zero_state", + action="store_false", + help="Prepare logical |+> instead.", + ) + parser.add_argument("--x_errors", default=True, action="store_true", help="Compute X-error LER.") + parser.add_argument( + "--z_errors", + default=False, + dest="x_errors", + action="store_false", + help="Compute Z-error LER.", + ) + parser.add_argument( + "-n", + "--n_errors", + type=int, + default=500, + help="Minimum number of errors for Monte Carlo estimator.", + ) + parser.add_argument( + "--check-matrix-path", + type=Path, + default=Path(__file__).resolve().parent / "check_matrix" / "flag_at_origin", + ) + parser.add_argument( + "--circuits-path", + type=Path, + default=Path(__file__).resolve().parent / "circuits" / "flag_at_origin", + ) + + return parser.parse_args() + + +# --------------------------------------------------------------------------- +# Core simulation with remapping (your new requirement) +# --------------------------------------------------------------------------- +def run_simulation( + code_name: str, + p: float, + p_idle_factor: float, + min_errors: int, + zero_state: bool, + x_errors: bool, + check_matrix_path: Path, + circuits_path: Path, +) -> tuple[float, float, int, int]: + """Runs the simulation for a given code and returns (p_L, acceptance, errors, shots).""" + # Load code + code_file = check_matrix_path / f"{code_name}.txt" + if not code_file.exists(): + msg = f"Code file not found: {code_file}" + raise FileNotFoundError(msg) + code = CSSCode.from_file(str(code_file)) + + # Load circuit + circ_file = circuits_path / f"{code_name}.stim" + if not circ_file.exists(): + msg = f"Circuit file not found: {circ_file}" + raise FileNotFoundError(msg) + + circuit = stim.Circuit.from_file(str(circ_file)) + + # Build noise model + noise = CircuitLevelNoiseIdlingParallel( + p, + p, + p * 2 / 3, # same as before + p, + p * p_idle_factor, + ) + + # ---------------------------------------------------------------------- + # NEW: Apply noise & remap qubits (your colleague's fix) + # ---------------------------------------------------------------------- + noisy = noise.apply(circuit) + + n_measured = noisy.num_measurements + n_code = code.n + + # mapping: measurement qubits go to the end; data qubits go to front + mapping = {i: i + n_code for i in range(n_measured)} | { + i: i - n_measured for i in range(n_measured, n_measured + n_code) + } + + circuit_relabelled = relabel_qubits(circuit, mapping) + + # Create simulator + sim = VerificationNDFTStatePrepSimulator( + state_prep_circ=circuit_relabelled, + code=code, + zero_state=zero_state, + ) + + # Run Monte-Carlo + if x_errors: + # returns: (p_L, acceptance_rate, num_errors, shots) + result = sim.logical_error_rate(noise=noise, min_errors=min_errors) + else: + result = sim.secondary_logical_error_rate(noise=noise, p=p, min_errors=min_errors) + + return ( + float(result[0]), + float(result[1]), + int(result[2]), + int(result[3]), + ) + + +# --------------------------------------------------------------------------- +# Entry point (CSV output for bash) +# --------------------------------------------------------------------------- +def main() -> None: + """Main function to parse arguments and run the simulation.""" + args = parse_args() + + p_logical, acceptance, errors, shots = run_simulation( + code_name=args.code, + p=args.p_error, + p_idle_factor=args.p_idle_factor, + min_errors=args.n_errors, + zero_state=args.zero_state, + x_errors=args.x_errors, + check_matrix_path=args.check_matrix_path, + circuits_path=args.circuits_path, + ) + + # CSV-formatted output: p_L, acceptance, errors, shots + print(f"{p_logical},{acceptance},{errors},{shots}") + + +if __name__ == "__main__": + main() diff --git a/scripts/ft_stateprep/eval_circ_mod/results/all_acceptance.pdf b/scripts/ft_stateprep/eval_circ_mod/results/all_acceptance.pdf new file mode 100644 index 000000000..1d00a4546 Binary files /dev/null and b/scripts/ft_stateprep/eval_circ_mod/results/all_acceptance.pdf differ diff --git a/scripts/ft_stateprep/eval_circ_mod/results/all_error.pdf b/scripts/ft_stateprep/eval_circ_mod/results/all_error.pdf new file mode 100644 index 000000000..477ece504 Binary files /dev/null and b/scripts/ft_stateprep/eval_circ_mod/results/all_error.pdf differ diff --git a/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d5_n250_z.csv b/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d5_n250_z.csv new file mode 100644 index 000000000..736800910 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d5_n250_z.csv @@ -0,0 +1,17 @@ +p p_l acceptance errors runs p_l_error acceptance_error +0.009,0.0007890339097207587,0.161573,255,2000000,4.9394323025686795e-05,0.0002602567632848376 +0.01,0.0011265701109701436,0.132713,299,2000000,6.511223632910568e-05,0.0002398960812841677 +0.007,0.00040734497233834896,0.24223566666666665,296,3000000,2.367080548162525e-05,0.00024735773585451916 +0.03,0.025298360285963748,0.002608749999999993,264,4000000,0.0015372192285635726,2.5504629106485224e-05 +0.005,0.00015490446723033228,0.3629295555555556,253,4500000,9.73824970047213e-06,0.00022667239858429193 +0.003,3.526640834883042e-05,0.5439522962962963,259,13500000,2.191420229100756e-06,0.00013555597330999815 +0.05,0.0940370801139355,6.871794871794202e-05,252,39000000,0.005638159819334154,1.3273573761953313e-06 +0.001,1.28694527985199e-06,0.8161162689075634,250,238000000,8.139828692263711e-08,2.51107215820172e-05 +0.07,0.15134538152610452,3.144578313229873e-06,250,415000000,0.009920757178871009,8.704753478938209e-08 +0.0009,9.236335175530411e-07,0.8328545476923083,250,325000000,5.8414865420648934e-08,2.069617951221164e-05 +0.0007,4.305385983106496e-07,0.8673773054518295,250,669500000,2.7228682928316697e-08,1.3108037055857542e-05 +0.09,0.04252726497288748,3.344909522863836e-07,250,2735500000,0.006670930060891094,1.105792793462423e-08 +0.0005,1.5508647826796515e-07,0.9033607671616706,250,1784500000,9.808397197275573e-09,6.994377580909208e-06 +0.1,0.023195458231954538,1.5201946471647367e-07,250,5137500000,0.005386166773271978,5.4396837178443764e-09 +0.0003,3.359863926833596e-08,0.9408375637880885,250,7909000000,2.1249206895028857e-09,2.6528919455898927e-06 +0.3,0.0037853775395813435,1.4865093136788645e-08,250,32559500000,0.0027913119551415313,6.75686046659029e-10 diff --git a/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d5_n500.csv b/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d5_n500.csv new file mode 100644 index 000000000..a29d10852 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d5_n500.csv @@ -0,0 +1,16 @@ +p p_l acceptance errors runs p_l_error acceptance_error +0.01,9.218831846556789e-05,0.13254195121951215,501,41000000,4.1185971923604335e-06,5.2955246264994925e-05 +0.009,7.262618113061721e-05,0.16196414117647068,500,42500000,3.2480816039759583e-06,5.651272800923366e-05 +0.03,0.003720151668562525,0.002588865384615384,501,52000000,0.00016592605586369122,7.0467711654614775e-06 +0.007,3.243637487425767e-05,0.24230985937500002,503,64000000,1.446217399192766e-06,5.3560099337197216e-05 +0.005,1.0898580634137458e-05,0.36273152569169953,500,126500000,4.873541742426324e-07,4.274729179976205e-05 +0.05,0.028145157917956277,6.771428571427743e-05,500,262500000,0.001240502779149001,5.078796276201399e-07 +0.003,2.356820377636626e-06,0.5439301410256411,500,390000000,1.0540443007681193e-07,2.5220572733358653e-05 +0.07,0.09330624726955027,3.210275229333553e-06,500,1362500000,0.004397909453968927,4.854026928225435e-08 +0.09,0.04242396142433262,3.3104599405770117e-07,500,5392000000,0.0047706014350106084,7.835544019815783e-09 +0.001,8.007557321019628e-08,0.8161107885243768,500,7651000000,3.5810991888278188e-09,4.428876639908826e-06 +0.1,0.02612321764864141,1.5356470271342852e-07,500,9292500000,0.004222341481762964,4.065176285614761e-09 +0.0009,5.85463849870974e-08,0.8328619964891738,500,10254000000,2.6182845920077193e-09,3.684490756813379e-06 +0.0007,2.7829723626588102e-08,0.8673898085697025,500,20712500000,1.2446035128124707e-09,2.356564590995231e-06 +0.0005,1.0122197889987248e-08,0.9033639369422166,500,54680000000,4.526804949359123e-10,1.2635334274500818e-06 +0.3,0.003476022111850033,1.4731879787473781e-08,500,71274000000,0.0018163121669546821,4.5463567714636175e-10 diff --git a/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d7_n100_z.csv b/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d7_n100_z.csv new file mode 100644 index 000000000..85649d481 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d7_n100_z.csv @@ -0,0 +1,20 @@ +p p_l acceptance errors runs p_l_error acceptance_error +0.0045,1.3573076826600939e-05,0.07549517766497459,101,98500000,1.3510097562836812e-06,2.6619266297483295e-05 +0.004,9.457369520293033e-06,0.09315614096916303,100,113500000,9.457567508433822e-07,2.7281866041455697e-05 +0.0035,5.654685237202446e-06,0.11485035714285716,100,154000000,5.65426884725871e-07,2.569296136458228e-05 +0.0055,3.196532440667811e-05,0.04964860317460319,100,63000000,3.1967511119253596e-06,2.7366883990034952e-05 +0.005,2.4567795632771825e-05,0.06122878195488722,100,66500000,2.4563436613968633e-06,2.9399968854571018e-05 +0.003,3.2596582814900336e-06,0.1416752101616627,100,216500000,3.259938793913312e-07,2.369975248477873e-05 +0.0065,6.368380048029067e-05,0.032715958333333316,100,48000000,6.3679583678746175e-06,2.5676523163057322e-05 +0.006,4.008180761851039e-05,0.04026288709677416,100,62000000,4.006975106797245e-06,2.4965068182267546e-05 +0.0075,0.00013786540461655192,0.021533117647058824,101,34000000,1.3721601282817423e-05,2.4893563124688387e-05 +0.007,8.587741385749338e-05,0.026480409090909075,100,44000000,8.584838836919335e-06,2.420518212044271e-05 +0.008,0.00012611105279930666,0.017428000000000006,100,45500000,1.2610134398132381e-05,1.9399934754620094e-05 +0.0085,0.0001451553649005154,0.01419868041237113,100,48500000,1.4517444092436165e-05,1.6988217801175462e-05 +0.009,0.0001907700370466462,0.011509161290322582,102,46500000,1.8878406715073358e-05,1.564161838608225e-05 +0.0095,0.00027551103425869173,0.009290025316455697,101,39500000,2.7396978397177037e-05,1.526452057904983e-05 +0.01,0.00031472483572281414,0.007583166666666673,100,42000000,3.143020470306398e-05,1.338590432220208e-05 +0.0025,1.3021529151473805e-06,0.17477571331058023,100,439500000,1.3019992368073743e-07,1.8115365563653318e-05 +0.002,8.034466296474356e-07,0.21564181975736574,100,577000000,8.035704197588435e-08,1.7121263160666823e-05 +0.0015,2.2843480567621631e-07,0.26607329626253384,100,1645500000,2.2841861834897323e-08,1.089376610472284e-05 +0.001,5.591894993621767e-08,0.32829813159585275,100,5448500000,5.59122292874432e-09,6.3618585111570534e-06 diff --git a/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d7_n50.csv b/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d7_n50.csv new file mode 100644 index 000000000..274d7d03e --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/cc_4_8_8_d7_n50.csv @@ -0,0 +1,19 @@ +p p_l acceptance errors runs p_l_error acceptance_error +0.0035,1.5629615702318374e-07,0.229716,50,2785000000,2.2104503601247943e-08,6.041914956975274e-06 +0.004,2.675827576250103e-07,0.186256,50,2007500000,3.783218442121689e-08,6.4861212459856e-06 +0.003,7.340905106041707e-08,0.28337,50,4807000000,1.0381874786483958e-08,5.0297712117440816e-06 +0.005,6.587037349691292e-07,0.122468,50,1239500000,9.315921004558004e-08,6.810065632844989e-06 +0.0045,3.845754510138509e-07,0.15101,50,1723000000,5.437018700670401e-08,6.3649782765250135e-06 +0.0055,9.369180174916529e-07,0.0993315,50,1075500000,1.3243928302398234e-07,6.624628728056182e-06 +0.006,1.4470001584741443e-06,0.0805286,50,858500000,2.0459907718438362e-07,6.709124123984448e-06 +0.0025,3.84397786882249e-08,0.349571,50,7441500000,5.43635217858893e-09,4.402565307141466e-06 +0.0065,1.742268418397229e-06,0.0653417,50,880000000,2.4617026939954625e-07,5.9927480379013065e-06 +0.007,2.5695715618854345e-06,0.0529984,50,735000000,3.632200988075673e-07,5.9243505601818925e-06 +0.0075,3.4389083299547123e-06,0.042996,50,676000000,4.864485760908777e-07,5.578363029883245e-06 +0.008,4.710767639800748e-06,0.0348964,50,606500000,6.671968760736622e-07,5.316645887060986e-06 +0.009,9.437897446141872e-06,0.0230034,50,461000000,1.3341473504038595e-06,4.96613834708669e-06 +0.0085,4.7947891619421245e-06,0.0283412,50,737500000,6.773431454939097e-07,4.3522500262120755e-06 +0.0095,1.3296113182756149e-05,0.0186803,50,401000000,1.884127565032174e-06,4.8036025752503285e-06 +0.01,9.743927863013015e-06,0.0151467,50,682000000,1.3735006470877545e-06,3.319715615742008e-06 +0.002,1.5469142513658964e-08,0.43128,50,14983500000,2.1880723888434886e-09,3.3598186859801094e-06 +0.001,1.3165880428483928e-09,0.672270784776989,10,11301300000 diff --git a/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d5_n250_z.csv b/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d5_n250_z.csv new file mode 100644 index 000000000..b34815298 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d5_n250_z.csv @@ -0,0 +1,16 @@ +p p_l acceptance errors runs p_l_error acceptance_error +0.01,0.0009778274050677425,0.098837,290,3000000,5.739819842372078e-05,0.00017230616881102467 +0.009,0.0007090423594105948,0.12409171428571428,308,3500000,4.0390260596630766e-05,0.00017622466239867703 +0.007,0.00040357336913175447,0.19681057142857145,278,3500000,2.4199999909641746e-05,0.00021251969347570767 +0.005,0.00012578466322879397,0.3131226153846154,256,6500000,7.860906558908823e-06,0.00018190312008120976 +0.03,0.025467282832721788,0.0011004444444444469,253,9000000,0.0015830119811089235,1.1051563320630446e-05 +0.003,2.7590035087361427e-05,0.49757318918918914,254,18500000,1.7312340507761101e-06,0.00011624626947557744 +0.05,0.09041813314890233,1.691076923075781e-05,252,162500000,0.005470667260195092,3.225903165759399e-07 +0.001,1.0981197493133006e-06,0.7922804852686305,251,288500000,6.931260549084407e-08,2.3883898692334507e-05 +0.0009,7.279800614410727e-07,0.8108509539551356,250,423500000,4.6042867258437486e-08,1.9030311025356355e-05 +0.0007,3.520090167132161e-07,0.849549428229666,250,836000000,2.2262777860745065e-08,1.2364828825952747e-05 +0.07,0.04229661627069819,5.234635774484799e-07,250,2546500000,0.005512558976492087,1.433742900874978e-08 +0.0005,1.3526549225632763e-07,0.8900454312545167,250,2076500000,8.555027776688416e-09,6.865098291511959e-06 +0.0003,2.8770993251443568e-08,0.9324939543893578,250,9318000000,1.8196717627525266e-09,2.599159873361169e-06 +0.09,0.0059512258231450964,4.5653017658426775e-08,250,20612000000,0.0025073343497520307,1.4882458082542598e-09 +0.1,0.003377781402492907,2.0470578639921255e-08,250,36784500000,0.00211438254336325,7.459893484157298e-10 diff --git a/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d5_n500_2.csv b/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d5_n500_2.csv new file mode 100644 index 000000000..cb43a2b37 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d5_n500_2.csv @@ -0,0 +1,15 @@ +p p_l acceptance errors runs p_l_error acceptance_error +0.01,9.866330769887207e-05,0.09860619417475726,501,51500000,4.407585006423178e-06,4.1543756939907155e-05 +0.009,7.107868247437325e-05,0.12412936842105263,503,57000000,3.169418209390482e-06,4.36736839780926e-05 +0.007,3.2537643646738084e-05,0.19699447435897444,500,78000000,1.455163055405479e-06,4.50338407557919e-05 +0.03,0.0035457334783736234,0.0010925813953488372,500,129000000,0.00015832881955495329,2.9086714264424753e-06 +0.005,1.0803671027990734e-05,0.3128853131313131,502,148500000,4.822003419231253e-07,3.804906401535613e-05 +0.003,2.3999166656689416e-06,0.4976432157330151,501,419500000,1.0721919276735499e-07,2.4411765933953025e-05 +0.05,0.027620167597544997,1.7164898746374388e-05,500,1037000000,0.0012283471570248246,1.2865525129676879e-07 +0.07,0.02927296202306218,5.349272071482121e-07,500,7487000000,0.002663671338258735,8.452658261264776e-09 +0.001,9.175767817534946e-08,0.7922410119220732,500,6878000000,4.103566179324987e-09,4.891899038906775e-06 +0.0009,6.321772138813842e-08,0.8109010898093065,500,9754000000,2.827118989114016e-09,3.9649441969164225e-06 +0.0007,2.762634545429089e-08,0.8495549571441898,500,21304000000,1.2354790833427618e-09,2.4493683607975084e-06 +0.09,0.006827750320336813,4.5853926412855893e-08,500,36420000000,0.002015082671084253,1.1220656931890295e-09 +0.0005,1.0252811904476834e-08,0.8900551751339285,500,54789500000,4.5852641455932803e-10,1.3364330037574505e-06 +0.1,0.003476578654087435,1.9499681079471632e-08,500,71334500000,0.0015781788535898355,5.228341410372749e-10 diff --git a/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d7_n100_z.csv b/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d7_n100_z.csv new file mode 100644 index 000000000..ae20c2edc --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d7_n100_z.csv @@ -0,0 +1,20 @@ +p p_l acceptance errors runs p_l_error acceptance_error +0.003,1.6353205408596861e-06,0.21004745578231285,101,294000000,1.6273040783660753e-07,2.375666910314864e-05 +0.0025,8.578457087211598e-07,0.27239435981308435,100,428000000,8.577949108943518e-08,2.1519154288609316e-05 +0.0035,2.905027060840175e-06,0.1619982870588233,100,212500000,2.9049574929349506e-07,2.527540930477502e-05 +0.004,5.143052299257098e-06,0.12498345980707389,100,155500000,5.144200478883155e-07,2.651973657822248e-05 +0.002,4.543109852144457e-07,0.35326880417335454,100,623000000,4.543388275600683e-08,1.9150077057763258e-05 +0.0045,1.0127194308976122e-05,0.09638287804878044,100,102500000,1.0124661082979137e-06,2.914944150706491e-05 +0.0015,1.027460847753464e-07,0.45813480348317204,100,2124500000,1.0274426936159529e-08,1.0809706535675973e-05 +0.005,1.3653283038461288e-05,0.07438920812182741,100,98500000,1.3650309512562874e-06,2.6439367248016373e-05 +0.0055,1.7081363413858337e-05,0.05739366666666663,100,102000000,1.7081479562523264e-06,2.303016642622943e-05 +0.006,3.206600305612109e-05,0.04426473758865249,100,70500000,3.2054716939174546e-06,2.4496452368669627e-05 +0.0065,4.308124858656152e-05,0.03414388235294117,100,68000000,4.307486039703069e-06,2.2022073702514164e-05 +0.007,5.708847259091935e-05,0.02633772932330828,100,66500000,5.709023453392754e-06,1.9637333378454107e-05 +0.0075,6.153210199459431e-05,0.0203528198757764,101,80500000,6.128120253501175e-06,1.573798766954389e-05 +0.008,7.200858443054991e-05,0.015718259887005676,100,88500000,7.194533378227276e-06,1.322179171646422e-05 +0.0085,0.00010359286784963502,0.012124968553459122,100,79500000,1.0366175500805244e-05,1.2274611365089499e-05 +0.009,0.00013530322890710302,0.009380886075949358,100,79000000,1.3511053732828062e-05,1.0845803629018605e-05 +0.0095,0.00016198553117793902,0.007234292397660815,100,85500000,1.6181614407888447e-05,9.165124215469314e-06 +0.01,0.00021558354467736613,0.005581523809523803,101,84000000,2.1440995808471576e-05,8.128704577787699e-06 +0.001,2.0670905502746648e-08,0.5942447387298809,100,8141000000,2.067084337457061e-09,5.442217258126517e-06 diff --git a/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d7_n50.csv b/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d7_n50.csv new file mode 100644 index 000000000..3b0c0308e --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/cc_6_6_6_d7_n50.csv @@ -0,0 +1,20 @@ +p p_l acceptance errors runs p_l_error acceptance_error +0.003,5.581531044934655e-08,0.21005382690278057,50,4263500000,7.894565410598742e-09,6.238510569144442e-06 +0.0025,3.09235031377766e-08,0.2724012753159238,50,5935000000,4.373502777885096e-09,5.778833359729731e-06 +0.0035,1.0959906196456912e-07,0.1619983526904631,50,2815500000,1.5501378824893388e-08,6.943844225036534e-06 +0.004,1.6215409021088684e-07,0.12494724893660145,50,2468500000,2.2928941368595758e-08,6.655242744891259e-06 +0.002,1.3034382205317407e-08,0.3532516295818731,50,10858000000,1.8434366488522054e-09,4.58706442575362e-06 +0.0045,2.7749964138669766e-07,0.09640374478330654,50,1869000000,3.924456774961247e-08,6.826993866373717e-06 +0.0015,3.3447093947298544e-09,0.45815411957170493,50,32641500000,4.729207202250708e-10,2.757773740241302e-06 +0.005,5.900969780670109e-07,0.07435519175076784,50,1139500000,8.34543066723393e-08,7.771783055161378e-06 +0.0055,7.601132403839991e-07,0.057362219512195056,50,1148000000,1.074372951922989e-07,6.863007137752974e-06 +0.006,9.708548916500824e-07,0.0442639965606191,50,1163000000,1.3732884949269628e-07,6.0312096843983316e-06 +0.0065,1.529459685268571e-06,0.03415583795086254,50,956500000,2.1636834615033673e-07,5.872777059156254e-06 +0.007,2.5526981775950828e-06,0.02636876902356897,50,742500000,3.6108215258533955e-07,5.880225040214863e-06 +0.0075,2.763367878589058e-06,0.020343047725996617,50,890500000,3.9056541335994514e-07,4.730728883827416e-06 +0.008,3.8772513177591825e-06,0.015717927007299303,50,822000000,5.478070178448924e-07,4.338319297647003e-06 +0.0085,4.489260194474157e-06,0.012126884531590425,50,918000000,6.350244575083712e-07,3.612466794767582e-06 +0.009,6.1086658480480524e-06,0.009363507727532907,50,873500000,8.642136406651013e-07,3.2587045952170578e-06 +0.0095,7.438530933592207e-06,0.007227393451422449,50,931500000,1.0511378939840536e-06,2.7753918710550012e-06 +0.01,8.79373304173127e-06,0.005584056918547608,50,1019000000,1.2431476658628543e-06,2.3343816758439952e-06 +0.001,6.070592256706501e-10,0.6122929354556778,10,26888500000 diff --git a/scripts/ft_stateprep/eval_circ_mod/results/eve_20_2_6_n500.csv b/scripts/ft_stateprep/eval_circ_mod/results/eve_20_2_6_n500.csv new file mode 100644 index 000000000..19f394b52 --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/eve_20_2_6_n500.csv @@ -0,0 +1,4 @@ +p p_l acceptance errors runs +0.005 9.92059717153481e-06,0.260845300207039,500,96600000 +0.003 2.139867560142971e-06,0.44602791523482266,500,261900000 +0.001 7.906034195883512e-08,0.7638020118357469,500,4140000000 diff --git a/scripts/ft_stateprep/eval_circ_mod/results/rotated_surface_d5_n500.csv b/scripts/ft_stateprep/eval_circ_mod/results/rotated_surface_d5_n500.csv new file mode 100644 index 000000000..daab4e6fd --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/results/rotated_surface_d5_n500.csv @@ -0,0 +1,4 @@ +p p_l acceptance errors runs +0.005 7.795083600558489e-06,0.27994052378873857,500,229100000 +0.003 1.5981376232359126e-06,0.4650167518953414,500,672700000 +0.001 6.58429316469888e-08,0.7743411262823141,500,9806600000 diff --git a/scripts/ft_stateprep/eval_circ_mod/run_eval_on_code.sh b/scripts/ft_stateprep/eval_circ_mod/run_eval_on_code.sh new file mode 100755 index 000000000..0ad9c87ca --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/run_eval_on_code.sh @@ -0,0 +1,24 @@ +#!/bin/bash +# Copyright (c) 2023 - 2026 Chair for Design Automation, TUM +# All rights reserved. +# +# SPDX-License-Identifier: MIT +# +# Licensed under the MIT License + +# Description: Estimate logical error rates for given code in parallel. Results are saved in a csv file described by the first argument. All other arguments are passed to the python script. + +# declare -a p=("0.5" "0.3" "0.1" "0.09" "0.07" "0.05" "0.03" "0.01" "0.009" "0.007" "0.005" "0.003" "0.001" "0.0009" "0.0007" "0.0005" "0.0003" "0.0001") +declare -a p=("0.001" "0.003" "0.005") + +echo "p p_l acceptance errors runs" > "$1.csv" + +run_and_write() { + local res=$(python estimate_logical_error_rate.py ${@:2:$#-2} "-p" "${@: -1}") + local line="${@: -1} ${res}" + (flock -e 200 echo $line >> "$1.csv") 200>lock +} + +export -f run_and_write + +parallel --load 16 --link run_and_write $@ ::: ${p[@]} diff --git a/scripts/ft_stateprep/eval_circ_mod/run_eval_on_code_d7.sh b/scripts/ft_stateprep/eval_circ_mod/run_eval_on_code_d7.sh new file mode 100755 index 000000000..381611f4d --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/run_eval_on_code_d7.sh @@ -0,0 +1,23 @@ +#!/bin/bash +# Copyright (c) 2023 - 2026 Chair for Design Automation, TUM +# All rights reserved. +# +# SPDX-License-Identifier: MIT +# +# Licensed under the MIT License + +# Description: Estimate logical error rates for given code in parallel. Results are saved in a csv file described by the first argument. All other arguments are passed to the python script. + +declare -a p=("0.001" "0.0015" "0.002" "0.0025" "0.003" "0.0035" "0.004" "0.0045" "0.005" "0.0055" "0.006" "0.0065" "0.007" "0.0075" "0.008" "0.0085" "0.009" "0.0095" "0.01") + +echo "p p_l acceptance errors runs p_l_error acceptance_error" > "$1.csv" + +run_and_write() { + local res=$(python estimate_logical_error_rate.py ${@:2:$#-2} "-p" "${@: -1}") + local line="${@: -1} ${res}" + (flock -e 200 echo $line >> "$1.csv") 200>lock +} + +export -f run_and_write + +parallel --load 16 --link run_and_write $@ ::: ${p[@]} diff --git a/scripts/ft_stateprep/eval_circ_mod/run_eval_on_code_mac.sh b/scripts/ft_stateprep/eval_circ_mod/run_eval_on_code_mac.sh new file mode 100755 index 000000000..9505b690a --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/run_eval_on_code_mac.sh @@ -0,0 +1,25 @@ +#!/bin/bash +# Copyright (c) 2023 - 2026 Chair for Design Automation, TUM +# All rights reserved. +# +# SPDX-License-Identifier: MIT +# +# Licensed under the MIT License + +# Description: Estimate logical error rates for given code in parallel. Results are saved in a csv file described by the first argument. All other arguments are passed to the python script. + +# declare -a p=("0.01" "0.009" "0.007" "0.005" "0.003" "0.001" "0.0009" "0.0007") +# declare -a p=("0.003" "0.0025" "0.0035" "0.002" "0.004" "0.0015" "0.0045" "0.001" "0.005" "0.0055" "0.006" "0.0065" "0.007" "0.0075" "0.008" "0.0085" "0.009" "0.0095" "0.01") +declare -a p=("0.001") + +echo "p p_l acceptance errors runs" > "$1.csv" + +run_and_write() { + local res=$(python estimate_logical_error_rate.py ${@:2:$#-2} "-p" "${@: -1}") + local line="${@: -1} ${res}" + (flock -e 200 echo $line >> "$1.csv") 200>lock +} + +export -f run_and_write + +parallel -j 6 --link run_and_write $@ ::: ${p[@]} diff --git a/scripts/ft_stateprep/eval_circ_mod/run_eval_on_fao.sh b/scripts/ft_stateprep/eval_circ_mod/run_eval_on_fao.sh new file mode 100755 index 000000000..c16ad2fcf --- /dev/null +++ b/scripts/ft_stateprep/eval_circ_mod/run_eval_on_fao.sh @@ -0,0 +1,52 @@ +#!/bin/bash +# Copyright (c) 2023 - 2026 Chair for Design Automation, TUM +# All rights reserved. +# +# SPDX-License-Identifier: MIT +# +# Licensed under the MIT License + +set -euo pipefail + +if [ "$#" -lt 1 ]; then + echo "Usage: $0 OUTPUT_PREFIX [extra python flags...]" + exit 1 +fi + +# First argument = output CSV file name (without .csv) +OUT="$1.csv" +shift 1 # remove output file name; remaining args are forwarded to python + +# Join remaining args into a single exported string +EXTRA_ARGS_STR="$*" +export EXTRA_ARGS_STR + +# arrays of jobs +CODES=("cc_17_1_5" "cc_20_2_6" "cc_25_1_5" "cc_31_1_7") +P_VALUES=("0.001") + +echo "code,p,p_logical,acceptance,errors,shots" > "$OUT" + +run_and_write() { + # This function will be run by GNU parallel in a new shell. + # Reconstruct EXTRA_ARGS array locally from the exported string. + read -r -a EXTRA_ARR <<< "$EXTRA_ARGS_STR" + + local code="$1" + local p="$2" + + # call python with reconstructed array (handles multiple flags) + local result + result=$(python3 estimate_logical_error_rate_fao.py "$code" -p "$p" "${EXTRA_ARR[@]}") + + local line="$code,$p,$result" + + # append atomically + ( flock -e 200; echo "$line" >> "$OUT" ) 200>lockfile +} + +export -f run_and_write +export OUT + +# Run parallel: Cartesian product of CODES x P_VALUES +parallel --jobs 2 run_and_write ::: "${CODES[@]}" ::: "${P_VALUES[@]}" diff --git a/src/mqt/qecc/circuit_synthesis/encoding.py b/src/mqt/qecc/circuit_synthesis/encoding.py index 5b3f4cd8e..c6c5c84eb 100644 --- a/src/mqt/qecc/circuit_synthesis/encoding.py +++ b/src/mqt/qecc/circuit_synthesis/encoding.py @@ -21,7 +21,10 @@ from ..codes.pauli import StabilizerTableau from .circuits import CNOTCircuit -from .synthesis_utils import heuristic_gaussian_elimination, optimal_elimination +from .synthesis_utils import ( + EliminationCNOTSynthesizer, + optimal_elimination, +) if TYPE_CHECKING: # pragma: no cover import numpy.typing as npt @@ -51,10 +54,11 @@ def heuristic_encoding_circuit(code: CSSCode, optimize_depth: bool = True, balan if balance_checks: _balance_matrix(logicals) - checks, cnots = heuristic_gaussian_elimination( - np.vstack((checks, logicals)), - parallel_elimination=optimize_depth, + ge = EliminationCNOTSynthesizer( + matrix=np.vstack((checks, logicals)), code=code, parallel_elimination=optimize_depth ) + ge.greedy_synthesis() + checks, cnots = ge.matrix, ge.eliminations # after reduction there still might be some overlap between initialized qubits and encoding qubits, we simply perform CNOTs to correct this encoding_qubits = np.where(checks[n_checks:, :].sum(axis=0) != 0)[0] diff --git a/src/mqt/qecc/circuit_synthesis/noise.py b/src/mqt/qecc/circuit_synthesis/noise.py index ace224b46..d71734a3f 100644 --- a/src/mqt/qecc/circuit_synthesis/noise.py +++ b/src/mqt/qecc/circuit_synthesis/noise.py @@ -260,7 +260,7 @@ def _add_idling_noise_to_layers_alap( uninitialized_qubits -= non_idling_non_resets initialized_qubits = initialized_qubits.union(non_idling_non_resets) - for q in idling: + for q in idling - noise.ideal_qubits: noisy_layer.append_operation("DEPOLARIZE1", q, p_idle) noisy_circ += noisy_layer @@ -282,7 +282,7 @@ def _add_idling_noise_to_layers_asap( uninitialized_qubits -= non_idling - for q in idling: + for q in idling - noise.ideal_qubits: noisy_layer.append_operation("DEPOLARIZE1", q, p_idle) noisy_circ += noisy_layer diff --git a/src/mqt/qecc/circuit_synthesis/simulation.py b/src/mqt/qecc/circuit_synthesis/simulation.py index 2a107a583..4cb142289 100644 --- a/src/mqt/qecc/circuit_synthesis/simulation.py +++ b/src/mqt/qecc/circuit_synthesis/simulation.py @@ -311,7 +311,7 @@ def plot_state_prep( # pragma: no cover if plot_primary: results = [ self.logical_error_rate( - CircuitLevelNoiseIdlingParallel(p, p, p, p, p * p_idle_factor, True), + CircuitLevelNoiseIdlingParallel(p, p, p, p * 2 / 3, p * p_idle_factor, True), min_errors=min_errors, ) for p in ps @@ -484,11 +484,17 @@ def __init__( combined.cx(self._data_range, self._first_ancilla_range) else: combined.cx(self._first_ancilla_range, self._data_range) - else: + elif zero_state: combined.cx(self._data_range, self._first_ancilla_range) combined.cx(self._second_ancilla_range, self._third_ancilla_range) combined.cx(self._second_ancilla_range, self._data_range) combined.h(self._second_ancilla_range) # second ancilla is measured in X basis + else: + combined.cx(self._first_ancilla_range, self._data_range) + combined.cx(self._third_ancilla_range, self._second_ancilla_range) + combined.cx(self._data_range, self._second_ancilla_range) + combined.h(self._first_ancilla_range) # first ancilla is measured in X basis + combined.h(self._third_ancilla_range) # third ancilla is measured in X basis combined.barrier() # need the barrier to retain order of measurements @@ -527,7 +533,7 @@ def _filter_runs(self, samples: npt.NDArray[np.int8]) -> npt.NDArray[np.int8]: qubit_to_meas = {q: i for i, q in enumerate(measured)} idx1 = [qubit_to_meas[q] for q in self.anc_1] anc_1 = samples[:, idx1] - check_anc_1 = (anc_1 @ self.z_checks.T) % 2 + check_anc_1 = anc_1 @ self.z_checks.T % 2 if self.zero_state else anc_1 @ self.x_checks.T % 2 if not self.has_one_ancilla: idx2 = [qubit_to_meas[q] for q in self.anc_2] @@ -535,8 +541,12 @@ def _filter_runs(self, samples: npt.NDArray[np.int8]) -> npt.NDArray[np.int8]: anc_2 = samples[:, idx2] anc_3 = samples[:, idx3] - check_anc_2 = (anc_2 @ self.x_checks.T) % 2 - check_anc_3 = (anc_3 @ self.z_checks.T) % 2 + if self.zero_state: + check_anc_2 = (anc_2 @ self.x_checks.T) % 2 + check_anc_3 = (anc_3 @ self.z_checks.T) % 2 + else: + check_anc_2 = (anc_2 @ self.z_checks.T) % 2 + check_anc_3 = (anc_3 @ self.x_checks.T) % 2 index_array = np.where(np.all(np.hstack((check_anc_1, check_anc_2, check_anc_3)) == 0, axis=1))[0] else: index_array = np.where(np.all(check_anc_1 == 0, axis=1))[0] diff --git a/src/mqt/qecc/circuit_synthesis/state_prep.py b/src/mqt/qecc/circuit_synthesis/state_prep.py index 03df3a4ca..1998eec66 100644 --- a/src/mqt/qecc/circuit_synthesis/state_prep.py +++ b/src/mqt/qecc/circuit_synthesis/state_prep.py @@ -19,10 +19,11 @@ import z3 from qiskit.circuit import AncillaRegister, ClassicalRegister, QuantumCircuit, QuantumRegister +from ..codes.css_code import InvalidCSSCodeError from .circuits import CNOTCircuit from .faults import PureFaultSet, coset_leader, product_fault_set from .synthesis_utils import ( - heuristic_gaussian_elimination, + EliminationCNOTSynthesizer, iterative_search_with_timeout, measure_flagged, odd_overlap, @@ -57,7 +58,7 @@ def __init__(self, circ: CNOTCircuit, max_x_errors: int, max_z_errors: int) -> N raise ValueError(msg) self.circ = circ - code = circ.get_code() + self.code = circ.get_code() self.num_qubits = circ.num_qubits() self.max_x_errors = max_x_errors self.max_z_errors = max_z_errors @@ -70,8 +71,8 @@ def __init__(self, circ: CNOTCircuit, max_x_errors: int, max_z_errors: int) -> N stacklevel=2, ) - self.x_checks = code.Hx - self.z_checks = code.Hz + self.x_checks = self.code.Hx + self.z_checks = self.code.Hz self.x_fault_sets: list[PureFaultSet] = [] self.z_fault_sets: list[PureFaultSet] = [] self.x_fault_sets_unreduced: list[PureFaultSet] = [] @@ -209,9 +210,60 @@ def heuristic_prep_circuit( checks = code.Hx if zero_state else code.Hz assert checks is not None - checks, cnots = heuristic_gaussian_elimination(checks, parallel_elimination=optimize_depth) + ge = EliminationCNOTSynthesizer(matrix=checks, code=code, parallel_elimination=optimize_depth) + ge.greedy_synthesis() - circ = _build_state_prep_circuit_from_back(checks, cnots, zero_state) + circ = _build_state_prep_circuit_from_back(ge.matrix, ge.eliminations, zero_state) + return FaultyStatePrepCircuit(circ, code.x_distance // 2, code.z_distance // 2) + + +def heuristic_reference_prep_circuit( + code: CSSCode, + optimize_depth: bool = True, + zero_state: bool = True, + penalty_cnots: list[tuple[int, int]] | None = None, + guide_by_x: bool = True, + ref_x_fs: npt.NDArray[np.int8] | None = None, + ref_z_fs: npt.NDArray[np.int8] | None = None, + ref_x_1fs: npt.NDArray[np.int8] | None = None, + ref_z_1fs: npt.NDArray[np.int8] | None = None, +) -> FaultyStatePrepCircuit: + """Return a circuit that prepares the +1 eigenstate of the code w.r.t. the Z or X basis and based on (a) reference fault set(s). + + Args: + code: The CSS code to prepare the state for. + optimize_depth: If True, optimize the depth of the circuit. This may lead to a higher number of CNOTs. + zero_state: If True, prepare the +1 eigenstate of the Z basis. If False, prepare the +1 eigenstate of the X basis. + penalty_cnots: tuples of CNOTs (control, target) which are initially added to the failed_cnots list and hence can only be applied once the control qubit has been used elsewhere + guide_by_x: Flag that decides whether dismissed CNOTs are free to placement again after either the control (x guided) or the target (z guided) has been used elsewhere + ref_x_fs: (Optional) reference x fault set which influences the construction of the circuit + ref_z_fs: (Optional) reference z fault set which influences the construction of the circuit + ref_x_1fs: (Optional) reference one error x fault set which ensures that no two error event of the newly constructed circuit cancels a one error event of the reference circuit + ref_z_1fs: (Optional) reference one error z fault set which ensures that no two error event of the newly constructed circuit cancels a one error event of the reference circuit + """ + if penalty_cnots is None: + penalty_cnots = [] + logger.info("Starting heuristic state preparation.") + if code.Hx is None or code.Hz is None: # type: ignore[redundant-expr] + msg = "The code must have both X and Z stabilizers defined." # type: ignore[unreachable] + raise InvalidCSSCodeError(msg) + + checks = code.Hx if zero_state else code.Hz + assert checks is not None + ge = EliminationCNOTSynthesizer( + matrix=checks, + parallel_elimination=optimize_depth, + code=code, + ) + ge.fault_set_guided_synthesis( + ref_x_fs=ref_x_fs, + ref_z_fs=ref_z_fs, + ref_x_1fs=ref_x_1fs, + ref_z_1fs=ref_z_1fs, + penalty_cnots=penalty_cnots, + guide_by_x=guide_by_x, + ) + circ = _build_state_prep_circuit_from_back(ge.matrix, ge.eliminations, zero_state) return FaultyStatePrepCircuit(circ, code.x_distance // 2, code.z_distance // 2) diff --git a/src/mqt/qecc/circuit_synthesis/synthesis_utils.py b/src/mqt/qecc/circuit_synthesis/synthesis_utils.py index 56dbf11a6..ee695da4f 100644 --- a/src/mqt/qecc/circuit_synthesis/synthesis_utils.py +++ b/src/mqt/qecc/circuit_synthesis/synthesis_utils.py @@ -11,6 +11,7 @@ import functools import logging +from enum import Enum, auto from typing import TYPE_CHECKING, Any import ldpc.mod2.mod2_numpy as mod2 @@ -25,6 +26,9 @@ import numpy.typing as npt from qiskit.circuit import AncillaQubit, Clbit, Qubit + from mqt.qecc.circuit_synthesis.state_prep import FaultyStatePrepCircuit + from mqt.qecc.codes.css_code import CSSCode + logger = logging.getLogger(__name__) @@ -89,73 +93,471 @@ def iterative_search_with_timeout( return None, max_param -def heuristic_gaussian_elimination( - matrix: npt.NDArray[np.int8], parallel_elimination: bool = True -) -> tuple[npt.NDArray[np.int8], list[tuple[int, int]]]: - """Perform Gaussian elimination on the column space of a matrix using as few eliminations as possible. +class CandidateAction(Enum): + """Class to help distinguish the control flow of the reference based heuristic gaussian elimination.""" + + SKIP = auto() # Ignore this candidate and continue the loop + RESTART_SEARCH = auto() # Reset used_columns and break to restart the search + TRIGGER_BACKTRACK = auto() # Call backtrack() and break + EVALUATE = auto() # Proceed with full validation (overlap checks) + + +class EliminationCNOTSynthesizer: + """Synthesizes a CNOT circuit through check matrix reduction via eliminations. + + This class implements algorithms to find a sequence of CNOT gates that + transforms a given binary matrix (e.g., a stabilizer generator matrix + from a quantum error-correcting code) into a reduced row echelon form. + The core mechanism is based on Gaussian elimination, where CNOT gates + correspond to column operations. - The algorithm utilizes a greedy heuristic to select the columns to eliminate in order to minimize the number of eliminations required. + Two primary synthesis strategies are provided: + 1. `greedy_synthesis`: A fast, purely cost-based algorithm that always + chooses the CNOT gate that reduces the column weights the most. + 2. `fault_set_guided_synthesis`: A more advanced algorithm that uses a + backtracking search guided by reference fault sets. This ensures the + synthesized circuit adheres to specific fault-tolerance constraints, + with respect to the reference fault sets given. - The matrix is reduced until there are exactly rnk(matrix) columns with non-zero entries. + """ + + def __init__( + self, + matrix: npt.NDArray[np.int8], + code: CSSCode, + parallel_elimination: bool = True, + ) -> None: + """Initialiser for the basic functionality.""" + self.matrix = matrix.copy() + self.parallel_elimination = parallel_elimination + self.code = code + self.rank = mod2.rank(self.matrix) + self.eliminations: list[tuple[int, int]] = [] + self.used_columns: list[int] = [] + self.costs = self._compute_cost_matrix() + + def _ref_based_init( + self, + ref_x_fs: npt.NDArray[np.int8] | None = None, + ref_z_fs: npt.NDArray[np.int8] | None = None, + ref_x_1fs: npt.NDArray[np.int8] | None = None, + ref_z_1fs: npt.NDArray[np.int8] | None = None, + penalty_cnots: list[tuple[int, int]] | None = None, + guide_by_x: bool = True, + ) -> None: + def _default_array(arr: npt.NDArray[np.int8] | None) -> npt.NDArray[np.int8]: + return arr if arr is not None else np.empty((0,), dtype=np.int8) + + self.ref_x_fs = _default_array(ref_x_fs) + self.ref_z_fs = _default_array(ref_z_fs) + self.ref_x_1fs = _default_array(ref_x_1fs) + self.ref_z_1fs = _default_array(ref_z_1fs) + self.guide_by_x = guide_by_x + self.failed_cnots: list[tuple[int, int]] = ( + penalty_cnots or [] + ) # NOTE: this is already a feature and not necessarily default + self.x_propagation_matrix: npt.NDArray[np.int8] = np.eye(self.matrix.shape[1], dtype=np.int8) + self.z_propagation_matrix: npt.NDArray[np.int8] = np.eye(self.matrix.shape[1], dtype=np.int8) + self.backtrack_required: bool = False + self.overlapping_errors_x: set[tuple[np.int8, ...]] = set() + self.overlapping_errors_z: set[tuple[np.int8, ...]] = set() + self.stack: list[ + tuple[ + npt.NDArray[np.int8], + npt.NDArray[np.int8], + list[int], + npt.NDArray[np.int8], + npt.NDArray[np.int8], + list[tuple[int, int]], + list[tuple[int, int]], + ] + ] = [] + self.current_x_fs: npt.NDArray[np.int8] = np.eye(self.matrix.shape[1], dtype=np.int8) + self.current_z_fs: npt.NDArray[np.int8] = np.eye(self.matrix.shape[1], dtype=np.int8) + self.used_cnots: list[tuple[int, int]] = [] + + def greedy_synthesis(self) -> None: + """Basic heuristic Gaussian elimination. + + Calculates CNOTS and Check matrix. + """ + while not self.is_reduced(): + costs_unused = self._mask_out_used_qubits() + if self._reset_if_stuck(costs_unused): + continue + i, j = np.unravel_index(np.argmin(costs_unused), self.costs.shape) + self._apply_cnot_to_matrix(int(i), int(j)) + + def fault_set_guided_synthesis( + self, + ref_x_fs: npt.NDArray[np.int8] | None = None, + ref_z_fs: npt.NDArray[np.int8] | None = None, + ref_x_1fs: npt.NDArray[np.int8] | None = None, + ref_z_1fs: npt.NDArray[np.int8] | None = None, + penalty_cnots: list[tuple[int, int]] | None = None, + guide_by_x: bool = True, + ) -> None: + """Reference based heuristic Gaussian elimination. + + This version takes reference fault sets into consideration and only applies cnots that + do not cause an overlap of the reference fault set and the fault set of the newly + created circuit. + """ + self._ref_based_init( + ref_x_fs=ref_x_fs, + ref_z_fs=ref_z_fs, + ref_x_1fs=ref_x_1fs, + ref_z_1fs=ref_z_1fs, + penalty_cnots=penalty_cnots, + guide_by_x=guide_by_x, + ) + self._validate_inputs() + while not self.is_reduced(): + costs_unused = self._mask_out_used_qubits() + if self._reset_if_stuck(costs_unused): + continue + candidate_pairs = self._get_candidate_pairs(costs_unused) + for i, j in candidate_pairs: + action = self._get_candidate_action(i, j, costs_unused[i, j]) + if action == CandidateAction.SKIP: + continue + if action == CandidateAction.RESTART_SEARCH: + self.used_columns = [] + self.backtrack_required = True + break + + if action == CandidateAction.TRIGGER_BACKTRACK: + if self.stack: + self._backtrack() + else: + # This case means we backtracked to the beginning and still failed. + logger.error("Backtracking stack is empty. No solution found.") + break + + if action == CandidateAction.EVALUATE: + is_valid, new_errors = self._cnot_is_valid_against_references(i, j) + if is_valid: + self.used_cnots.append((int(i), int(j))) + self._commit_to_cnot(i, j, new_errors) + self._apply_cnot_to_matrix(int(i), int(j)) + break + self.failed_cnots.append((int(i), int(j))) + continue + + def is_reduced(self) -> bool: + """Method decides if the Gaussian elimination has successfully ended. + + The matrix is considered reduced when the number of columns actually turned into + all-zeros matches the number of linearly depended columns. + """ + return bool(len(np.where(np.all(self.matrix == 0, axis=0))[0]) == self.matrix.shape[1] - self.rank) + + def _get_candidate_action(self, i: int, j: int, costs: int) -> CandidateAction: + if (int(i), int(j)) in self.failed_cnots or (int(i), int(j)) in self.used_cnots: + return CandidateAction.SKIP + + if costs >= 0: + if self.backtrack_required: + return CandidateAction.TRIGGER_BACKTRACK + return CandidateAction.RESTART_SEARCH + return CandidateAction.EVALUATE + + def _cnot_is_valid_against_references(self, i: int, j: int) -> tuple[bool, dict[str, npt.NDArray[np.int8] | bool]]: + found_cnot: bool = False + new_x_error, next_x_propagation_matrix = get_next_error( + propagation_matrix=self.x_propagation_matrix.copy(), cnot_gate=(int(i), int(j)) + ) + new_z_error, next_z_propagation_matrix = get_next_error( + propagation_matrix=self.z_propagation_matrix.copy(), cnot_gate=(int(i), int(j)), x_error=False + ) + + if self._check_error_existence(new_x_error, self.overlapping_errors_x): + return found_cnot, {} + if self._check_error_existence(new_z_error, self.overlapping_errors_z): + return found_cnot, {} + + new_x_error = np.expand_dims(new_x_error, axis=0) + new_z_error = np.expand_dims(new_z_error, axis=0) + + new_z_error_tuple = tuple(new_z_error.flatten()) + new_x_error_tuple = tuple(new_x_error.flatten()) + + x_overlap = self._check_overlap(self.ref_x_fs, self.ref_x_1fs, self.current_x_fs, new_x_error) + z_overlap = self._check_overlap(self.ref_z_fs, self.ref_z_1fs, self.current_z_fs, new_z_error, x_error=False) + + if self.ref_x_fs.size and self.ref_z_fs.size: + # Both sets provided: Enter if **both** overlaps fail + found_cnot = not (x_overlap or z_overlap) + if not found_cnot: + self.overlapping_errors_x.add(new_x_error_tuple) + self.overlapping_errors_z.add(new_z_error_tuple) + elif self.ref_x_fs.size: + # Only x-set provided: Enter if **x_overlap** fails + found_cnot = not x_overlap + if not found_cnot: + self.overlapping_errors_x.add(new_x_error_tuple) + elif self.ref_z_fs.size: + # Only z-set provided: Enter if **z_overlap** fails + found_cnot = not z_overlap + if not found_cnot: + self.overlapping_errors_z.add(new_z_error_tuple) + if found_cnot: + self.x_propagation_matrix = next_x_propagation_matrix + self.z_propagation_matrix = next_z_propagation_matrix + return found_cnot, { + "new_x_error": new_x_error, + "new_z_error": new_z_error, + "x_overlap": x_overlap, + "z_overlap": z_overlap, + } + + def _commit_to_cnot(self, i: int, j: int, new_errors: dict[str, npt.NDArray[np.int8] | bool]) -> None: + self.stack.append(( + self.x_propagation_matrix.copy(), + self.z_propagation_matrix.copy(), + self.used_columns.copy(), + self.matrix.copy(), + self.costs.copy(), + self.used_cnots.copy(), + self.failed_cnots.copy(), + )) + if self.guide_by_x: + self.failed_cnots = [fcnot for fcnot in self.failed_cnots if int(i) != fcnot[0]] + else: + self.failed_cnots = [fcnot for fcnot in self.failed_cnots if int(j) != fcnot[1]] + + if self.ref_x_fs.size and not new_errors["x_overlap"]: + self.current_x_fs = np.vstack((self.current_x_fs, new_errors["new_x_error"]), dtype=np.int8) + if self.ref_z_fs.size and not new_errors["z_overlap"]: + self.current_z_fs = np.vstack((self.current_z_fs, new_errors["new_z_error"]), dtype=np.int8) + + def _backtrack(self) -> None: + ( + self.x_propagation_matrix, + self.z_propagation_matrix, + self.used_columns, + self.matrix, + self.costs, + self.used_cnots, + _, + ) = self.stack.pop() + removed_cnot = self.eliminations.pop() + if self.guide_by_x: + self.failed_cnots = [fcnot for fcnot in self.failed_cnots if removed_cnot[0] != fcnot[0]] + else: + self.failed_cnots = [fcnot for fcnot in self.failed_cnots if removed_cnot[1] != fcnot[1]] + self.failed_cnots.append(removed_cnot) + # print_dynamic_eliminations(eliminations, failed_cnots) + self.backtrack_required = False + + def _validate_inputs(self) -> None: + """Here are some checks that ensure that the reference based construction can actually be executed.""" + has_refs = bool(self.ref_x_fs.size or self.ref_z_fs.size) + has_code = self.code is not None + if has_refs != has_code: + msg = "Must provide either both a reference fault set and CSS code, or neither." + raise ValueError(msg) + + def _reset_if_stuck(self, costs_unused: npt.NDArray[np.int8]) -> bool: + """Handles local minima or full column usage. Returns True if reset occurred.""" + if np.all(costs_unused >= 0) or len(self.used_columns) == self.matrix.shape[1]: + if not self.used_columns: # Local minimum + self._triangular_reset() + else: + self.used_columns = [] + return True + return False + + def _triangular_reset(self) -> None: + logger.warning("Local minimum reached. Making matrix triangular.") + self.matrix = mod2.row_echelon(self.matrix, full=True)[0] + self.costs = self._compute_cost_matrix() + + def _apply_cnot_to_matrix(self, i: int, j: int) -> None: + self.eliminations.append((i, j)) + if self.parallel_elimination: + self.used_columns.append(i) + self.used_columns.append(j) + # update matrix + self.matrix[:, j] = (self.matrix[:, i] + self.matrix[:, j]) % 2 + # update costs + new_weights = np.sum((self.matrix[:, j][:, np.newaxis] + self.matrix) % 2, axis=0) + self.costs[j, :] = new_weights - np.sum(self.matrix, axis=0) + self.costs[:, j] = new_weights - np.sum(self.matrix[:, j]) + np.fill_diagonal(self.costs, 1) + + def _compute_cost_matrix(self) -> npt.NDArray[np.int8]: + costs = np.array([ + [np.sum((self.matrix[:, i] + self.matrix[:, j]) % 2) for j in range(self.matrix.shape[1])] + for i in range(self.matrix.shape[1]) + ]) + costs -= np.sum(self.matrix, axis=0) + np.fill_diagonal(costs, 1) + return costs + + def _mask_out_used_qubits(self) -> npt.NDArray[np.int8]: + m = np.zeros((self.matrix.shape[1], self.matrix.shape[1]), dtype=bool) # type: npt.NDArray[np.bool_] + m[self.used_columns, :] = True + m[:, self.used_columns] = True + return np.ma.array(self.costs, mask=m) + + def _get_candidate_pairs(self, costs_unused: npt.NDArray[np.int8]) -> list[tuple[int, int]]: + # Get all valid (i, j) pairs sorted by cost + candidate_indices = np.argsort(costs_unused.flatten()) # Flatten and sort by value + return [(int(i), int(j)) for idx in candidate_indices for i, j in [np.unravel_index(idx, self.costs.shape)]] + # return [np.unravel_index(idx, self.costs.shape) for idx in candidate_indices] + + def _check_overlap( + self, + ref_fs: npt.NDArray[np.int8], + ref_1_fs: npt.NDArray[np.int8], + current_fs: npt.NDArray[np.int8], + new_error: npt.NDArray[np.int8], + x_error: bool = True, + ) -> bool: + overlap: bool = True + if ref_fs.size: + overlap = self.code.check_fs_overlap(ref_fs, new_error, x_error=x_error) + if ref_1_fs.size and not overlap: + trial_2_fs = (current_fs + new_error) % 2 + trial_2_fs = self._filter_fault_set(trial_2_fs, int((self.code.distance - 1) / 2)) + overlap = self.code.check_fs_overlap(ref_1_fs, trial_2_fs, x_error=x_error) + return overlap + + @staticmethod + def _check_error_existence(error: npt.NDArray[np.int8], error_memory: set[tuple[np.int8, ...]]) -> bool: + # INFO: Quickly check if new error is known to cause overlap. This saves another long overlap check. + error_tuple = tuple(error.flatten()) + return error_tuple in error_memory + + @staticmethod + def _filter_fault_set(fault_set: npt.NDArray[np.int8], threshold: int) -> npt.NDArray[np.int8]: + """Filter fault sets based on a sum threshold.""" + return fault_set[np.where(fault_set.sum(axis=1) > threshold)] + + +def get_next_error( + propagation_matrix: npt.NDArray[np.int8], cnot_gate: tuple[int, int], x_error: bool = True +) -> tuple[npt.NDArray[np.int8], npt.NDArray[np.int8]]: + """Propagates a single X or Z error through a CNOT gate in the circuit. + + This function updates the error propagation matrix when a new CNOT gate is applied. + Each row in the matrix represents the propagated error if a single X or Z error occurs on that qubit. Args: - matrix: The matrix to perform Gaussian elimination on. - parallel_elimination: Whether to prioritize elimination steps that act on disjoint columns. + propagation_matrix (npt.NDArray[np.int8]): + Current error propagation matrix (shape: [n_qubits, n_qubits]). + cnot_gate (Tuple[int, int]): + A tuple representing the new CNOT gate (control, target). + x_error (bool, optional): + Flag indicating whether to propagate X errors (True) or Z errors (False). + Defaults to True. Returns: - The reduced matrix and a list of the elimination steps taken. The elimination steps are represented as tuples of the form (i, j) where i is the column being eliminated with and j is the column being eliminated. + Tuple[npt.NDArray[np.int8], npt.NDArray[np.int8]]: + - The propagated error (affected row of the matrix). + - The updated error propagation matrix. + """ - matrix = matrix.copy() - rank = mod2.rank(matrix) + # NOTE: This implementation assumes single error events only. For higher-order errors, adjustments are required. + control, target = cnot_gate - def is_reduced() -> bool: - return bool(len(np.where(np.all(matrix == 0, axis=0))[0]) == matrix.shape[1] - rank) + control_row = propagation_matrix[control] + target_row = propagation_matrix[target] - costs = np.array([ - [np.sum((matrix[:, i] + matrix[:, j]) % 2) for j in range(matrix.shape[1])] for i in range(matrix.shape[1]) - ]) + if x_error: + propagation_matrix[control] = np.bitwise_xor(control_row, target_row) + return propagation_matrix[control], propagation_matrix - costs -= np.sum(matrix, axis=0) - np.fill_diagonal(costs, 1) - - used_columns = [] # type: list[np.int_] - eliminations = [] # type: list[tuple[int, int]] - while not is_reduced(): - m = np.zeros((matrix.shape[1], matrix.shape[1]), dtype=bool) # type: npt.NDArray[np.bool_] - m[used_columns, :] = True - m[:, used_columns] = True - - costs_unused = np.ma.array(costs, mask=m) # type: ignore[no-untyped-call, unused-ignore] - if np.all(costs_unused >= 0) or len(used_columns) == matrix.shape[1]: # no more reductions possible - if used_columns == []: # local minimum => get out by making matrix triangular - logger.warning("Local minimum reached. Making matrix triangular.") - matrix = mod2.row_echelon(matrix, full=True)[0] - costs = np.array([ - [np.sum((matrix[:, i] + matrix[:, j]) % 2) for j in range(matrix.shape[1])] - for i in range(matrix.shape[1]) - ]) - costs -= np.sum(matrix, axis=0) - np.fill_diagonal(costs, 1) - else: # try to move onto the next layer - used_columns = [] - continue + propagation_matrix[target] = np.bitwise_xor(control_row, target_row) + return propagation_matrix[target], propagation_matrix - i, j = np.unravel_index(np.argmin(costs_unused), costs.shape) - eliminations.append((int(i), int(j))) - if parallel_elimination: - used_columns.append(i) - used_columns.append(j) +def check_mutually_disjointness_spcs( + c_spcs: list[FaultyStatePrepCircuit], p_spcs: list[FaultyStatePrepCircuit], x_error: bool = True +) -> list[FaultyStatePrepCircuit]: + """Check if potential SPCs have mutually disjoint fault set with all current SPCs. - # update matrix - matrix[:, j] = (matrix[:, i] + matrix[:, j]) % 2 - # update costs - new_weights = np.sum((matrix[:, j][:, np.newaxis] + matrix) % 2, axis=0) - costs[j, :] = new_weights - np.sum(matrix, axis=0) - costs[:, j] = new_weights - np.sum(matrix[:, j]) - np.fill_diagonal(costs, 1) + Take list of SPCs with already mutually disjoint fault sets and another list of potential candidates for new SPCs that + have a mutually disjoint fault set with all current SPCs. + + Args: + c_spcs: current SPCs that are already mutually disjoint in terms of fault sets + p_spcs: potential SPCs that shall be tested for mutually disjointness against the current set + x_error: flag that decides if check happens for x errors or z errors + """ + i = 0 + while i < len(p_spcs): + pspc = p_spcs[i] + # NOTE: check if it is not better to use the big fault set of the current SPC here as those sets have already been + # calculated and do not need to be calculated again + # FIX: big fs calculation should be only done for the current elements if there are more candidates than current elements + px_fs, pz_fs = get_fs_based_on_d(pspc) + + # Check against *all* existing and newly added elements in c_spcs + for spc in c_spcs: + # NOTE: for distance 5 and 7 we only compare against the 1 error fault set. + # This might need adjustments for different distances. + x_fs = spc.compute_fault_set() + z_fs = spc.compute_fault_set(x_errors=False) + if x_error: + if spc.code.check_fs_overlap(x_fs.faults, px_fs): + break + elif spc.code.check_fs_overlap(z_fs.faults, pz_fs, x_error=False): + break # Stop checking if there's an overlap + else: # No overlap found, so add pspc + c_spcs.append(pspc) + + i += 1 # Move to next element in p_spcs + return c_spcs + + +def get_fs_based_on_d(spc: FaultyStatePrepCircuit) -> tuple[npt.NDArray[np.int8], npt.NDArray[np.int8]]: + """Get fault sets based on the code distance. + + Only the faults sets that are of interest for the fault tolerant state preparation are being returned. + Supported are code distance 5 and 7. + + Args: + spc: State Prep Circiut of which the fault set is to be returned. + + Returns: + tuple: first entry the x fault set and second entry the z fault set. + """ + + def compute_fault_sets(level: int = 1) -> tuple[npt.NDArray[np.int8], npt.NDArray[np.int8]]: + """Helper function to compute fault sets at a given level.""" + spc.compute_fault_set(level) + spc.compute_fault_set(level, x_errors=False) + return spc.x_fault_sets[level - 1].faults, spc.z_fault_sets[level - 1].faults + + def filter_fault_set(fault_set: npt.NDArray[np.int8], threshold: int) -> npt.NDArray[np.int8]: + """Filter fault sets based on a sum threshold.""" + return fault_set[np.where(fault_set.sum(axis=1) > threshold)] + + fault_set_x_1, fault_set_z_1 = compute_fault_sets(1) + + if spc.code.distance == 3: + return fault_set_x_1, fault_set_z_1 + + if spc.code.distance == 5: + return filter_fault_set(fault_set_x_1, 2), filter_fault_set(fault_set_z_1, 2) + + if spc.code.distance == 7: + fault_set_x_2, fault_set_z_2 = compute_fault_sets(2) + return ( + np.vstack([ + filter_fault_set(fault_set_x_1, 2), + filter_fault_set(fault_set_x_2, 3), + ]), + np.vstack([ + filter_fault_set(fault_set_z_1, 2), + filter_fault_set(fault_set_z_2, 3), + ]), + ) - return matrix, eliminations + msg = f"Unsupported code distance: {spc.code.distance}" + raise ValueError(msg) def gaussian_elimination_min_column_ops( @@ -321,7 +723,8 @@ def build_css_circuit_from_cnot_list(n: int, cnots: list[tuple[int, int]], hadam The quantum circuit. """ circ = QuantumCircuit(n) - circ.h(hadamards) + if hadamards: + circ.h(hadamards) for i, j in cnots: circ.cx(i, j) return circ diff --git a/src/mqt/qecc/codes/css_code.py b/src/mqt/qecc/codes/css_code.py index 41e6bbcee..d28d8370b 100644 --- a/src/mqt/qecc/codes/css_code.py +++ b/src/mqt/qecc/codes/css_code.py @@ -148,12 +148,31 @@ def stabilizer_eq_z_error(self, error_1: npt.NDArray[np.int8], error_2: npt.NDAr m3 = np.vstack([self.Hz, error_1, error_2]) return bool(mod2.rank(m1) == mod2.rank(m2) == mod2.rank(m3)) + def stabilizer_eq_z_error_with_logical(self, error_1: npt.NDArray[np.int8], error_2: npt.NDArray[np.int8]) -> bool: + """Check if two Z errors are in the same coset.""" + z_checks = np.vstack((self.Lz.copy(), self.Hz.copy())) + if self.Hz.shape[0] == 0: + return bool(np.array_equal(error_1, error_2)) + m1 = np.vstack([z_checks, error_1]) + m2 = np.vstack([z_checks, error_2]) + m3 = np.vstack([z_checks, error_1, error_2]) + return bool(mod2.rank(m1) == mod2.rank(m2) == mod2.rank(m3)) + def is_self_dual(self) -> bool: """Check if the code is self-dual.""" return bool( self.Hx.shape[0] == self.Hz.shape[0] and mod2.rank(self.Hx) == mod2.rank(np.vstack([self.Hx, self.Hz])) ) + def check_fs_overlap(self, fs_1: npt.NDArray[np.int8], fs_2: npt.NDArray[np.int8], x_error: bool = True) -> bool: + """Returns True if there is an overlap between both fault sets.""" + # TODO: add method docstring and argument descriptions + # check if one of the fault sets is empty. If so, default is no overlap + if not fs_1.size or not fs_2.size: + return False + check_fn = self.stabilizer_eq_x_error if x_error else self.stabilizer_eq_z_error_with_logical + return any(check_fn(f1, f2) for f1 in fs_1 for f2 in fs_2) + @staticmethod def _check_valid_check_matrices(Hx: npt.NDArray[np.int8] | None, Hz: npt.NDArray[np.int8] | None) -> None: # noqa: N803 """Check if the code is a valid CSS code.""" diff --git a/tests/circuit_synthesis/test_gaussian_elimination.py b/tests/circuit_synthesis/test_gaussian_elimination.py new file mode 100644 index 000000000..271a0c6e2 --- /dev/null +++ b/tests/circuit_synthesis/test_gaussian_elimination.py @@ -0,0 +1,327 @@ +# Copyright (c) 2023 - 2026 Chair for Design Automation, TUM +# All rights reserved. +# +# SPDX-License-Identifier: MIT +# +# Licensed under the MIT License + +# ruff: noqa: SLF001 + +"""Test implementations of EliminationCNOTSynthesizer class.""" + +from __future__ import annotations + +from typing import TYPE_CHECKING + +import numpy as np +import pytest + +if TYPE_CHECKING: # pragma: no cover + import numpy.typing as npt +from mqt.qecc.circuit_synthesis.synthesis_utils import CandidateAction, EliminationCNOTSynthesizer +from mqt.qecc.codes.css_code import CSSCode + +STEANE_CHECK_MATRIX = np.array([[1, 1, 0, 0, 1, 1, 0], [1, 0, 1, 0, 1, 0, 1], [0, 0, 0, 1, 1, 1, 1]], dtype=np.int8) +STEANE_CODE = CSSCode(Hx=STEANE_CHECK_MATRIX) + + +@pytest.fixture +def get_instance(): + """A basic fixture to provide a fresh GaussianElimination instance for each test.""" + return EliminationCNOTSynthesizer(matrix=STEANE_CHECK_MATRIX.copy(), code=STEANE_CODE) + + +# Use parametrize to test all logical branches +@pytest.mark.parametrize( + ("cost", "backtrack_required", "used_cnots", "failed_cnots", "expected_action"), + [ + # Case 1: Greedy step, should evaluate + (-1, False, [], [], CandidateAction.EVALUATE), + # Case 2: Already used, should skip + (-1, False, [(0, 1)], [], CandidateAction.SKIP), + # Case 3: Already failed, should skip + (-1, False, [], [(0, 1)], CandidateAction.SKIP), + # Case 4: First time hitting non-negative cost, should restart search + (0, False, [], [], CandidateAction.RESTART_SEARCH), + (1, False, [], [], CandidateAction.RESTART_SEARCH), + # Case 5: Already in backtrack mode and hitting non-negative cost, should trigger backtrack + (0, True, [], [], CandidateAction.TRIGGER_BACKTRACK), + (1, True, [], [], CandidateAction.TRIGGER_BACKTRACK), + ], +) +def test_get_candidate_action(get_instance, cost, backtrack_required, used_cnots, failed_cnots, expected_action): + """Verify that _get_candidate_action returns the correct action based on state.""" + # Arrange: Set up the instance state for the test case + get_instance.backtrack_required = backtrack_required + get_instance.used_cnots = used_cnots + get_instance.failed_cnots = failed_cnots + + # Act: Call the method + action = get_instance._get_candidate_action(i=0, j=1, costs=cost) + + # Assert: Check the result + assert action == expected_action + + +def test_apply_cnot_to_matrix_updates_matrix_and_costs_correctly(get_instance): + """Verify the target column of the matrix is correctly updated after a CNOT.""" + expected_matrix = np.array([[1, 1, 0, 0, 0, 1, 0], [1, 0, 1, 0, 0, 0, 1], [0, 0, 0, 1, 1, 1, 1]], dtype=np.int8) + get_instance._apply_cnot_to_matrix(i=0, j=4) + np.testing.assert_array_equal(get_instance.matrix, expected_matrix) + expected_instance = EliminationCNOTSynthesizer(matrix=expected_matrix, code=CSSCode(expected_matrix)) + expected_costs = expected_instance.costs + np.testing.assert_array_equal(get_instance.costs, expected_costs) + + +def test_mask_out_used_qubits(get_instance): + """Check that the matrix is masked out cleanly based on the used columns.""" + used_qubit_index = 1 + unused_qubit_index = 0 + get_instance.used_columns.append(used_qubit_index) + masked_costs = get_instance._mask_out_used_qubits() + # 1. Is the data of the masked array still the same as the original costs? + np.testing.assert_array_equal(masked_costs.data, get_instance.costs) + + # 2. Is the entire row for the used qubit masked? + assert np.all(masked_costs.mask[used_qubit_index, :]), "Row for used qubit should be fully masked" + + # 3. Is the entire column for the used qubit masked? + assert np.all(masked_costs.mask[:, used_qubit_index]), "Column for used qubit should be fully masked" + + # 4. Is a cell NOT involving the used qubit left unmasked? + assert not masked_costs.mask[unused_qubit_index, unused_qubit_index], "Unused cell should not be masked" + + +@pytest.mark.parametrize( + ( + "scenario", + "initial_used_cols", + "costs_are_positive", + "expected_return", + "expect_reset_called", + "expected_final_used_cols", + ), + [ + # Scenario 1: Stagnated and no used columns -> should call triangular_reset + ("local_minimum", [], True, True, True, []), + # Scenario 2: Stagnated with used columns -> should clear used_columns + ("parallel_deadend", [1, 2], True, True, False, []), + # Scenario 3: Not stagnated (negative cost exists) -> should do nothing + ("not_stagnated", [1, 2], False, False, False, [1, 2]), + ], +) +def test_reset_if_stuck( + get_instance, + monkeypatch, + scenario, # noqa: ARG001 + initial_used_cols, + costs_are_positive, + expected_return, + expect_reset_called, + expected_final_used_cols, +): + """Verify that _reset_if_stuck behaves correctly in all scenarios.""" + costs_unused = np.array([[0, 1], [1, 0]]) if costs_are_positive else np.array([[0, -1], [1, 0]]) + get_instance.used_columns = initial_used_cols + + reset_call_log = [] # This list will act as our spy. + # We replace the real, complex _triangular_reset with a fake function + # that just appends to our log list when it's called. + monkeypatch.setattr(get_instance, "_triangular_reset", lambda: reset_call_log.append(True)) + + return_value = get_instance._reset_if_stuck(costs_unused) + + assert return_value == expected_return + assert get_instance.used_columns == expected_final_used_cols + + if expect_reset_called: + assert len(reset_call_log) == 1 + else: + assert len(reset_call_log) == 0 + + +def test_greedy_synthesis_integration_with_known_matrix(get_instance): + """Tests the full greedy_synthesis method from start to finish. + + It verifies that the correct sequence of eliminations is produced + and that the matrix is fully reduced at the end. + """ + expected_final_matrix = np.array( + [[0, 1, 0, 0, 0, 0, 0], [1, 0, 0, 0, 0, 0, 0], [0, 0, 0, 1, 0, 0, 0]], dtype=np.int8 + ) + + expected_eliminations = [(0, 4), (1, 5), (2, 6), (1, 0), (3, 4), (5, 6), (0, 2), (3, 5)] + + get_instance.greedy_synthesis() + + # 1. Did it produce the correct sequence of operations? + assert get_instance.eliminations == expected_eliminations + + # 2. Is the algorithm correctly reporting that it's finished? + assert get_instance.is_reduced() is True + + # 3. Is the final matrix what we expect? + np.testing.assert_array_equal(get_instance.matrix, expected_final_matrix) + + +@pytest.mark.parametrize( + ("guide_by_x", "expected_failed_cnots"), + [ + # Scenario 1: Guided by the control qubit (X-errors) + (True, [(6, 4), (3, 4)]), + # Scenario 2: Guided by the target qubit (Z-errors) + (False, [(3, 5), (3, 4)]), + ], +) +def test_backtrack_restores_state_and_updates_failed_cnots(get_instance, guide_by_x, expected_failed_cnots): + """Verify that _backtrack correctly pops state from the stack, restores it, and updates the failed_cnots list based on the guide_by_x flag.""" + # ARRANGE + prev_x_propagation_matrix = np.array([[-1]]) + prev_z_propagation_matrix = np.array([[-2]]) + prev_matrix = np.array([[-3]]) + prev_costs = np.array([[-4]]) + prev_used_cols = [-5] + prev_used_cnots = [(-6, -6)] + + previous_state_tuple = ( + prev_x_propagation_matrix, + prev_z_propagation_matrix, + prev_used_cols, + prev_matrix, + prev_costs, + prev_used_cnots, + None, + ) + + get_instance._ref_based_init() + get_instance.matrix = np.array([[99]]) + get_instance.costs = np.array([[98]]) + get_instance.used_columns = [97] + get_instance.used_cnots = [(96, 96)] + get_instance.x_propagation_matrix = [(95, 95)] + get_instance.z_propagation_matrix = [(94, 94)] + get_instance.eliminations = [(1, 2), (3, 4)] # Last element (3, 4) will be popped + get_instance.backtrack_required = True + get_instance.guide_by_x = guide_by_x + + get_instance.failed_cnots = [(3, 5), (6, 4)] + + get_instance.stack.append(previous_state_tuple) + + # ACT + get_instance._backtrack() + + # ASSERT + + # 1. Check that the core attributes were restored from the stack. + np.testing.assert_array_equal(get_instance.matrix, prev_matrix) + np.testing.assert_array_equal(get_instance.costs, prev_costs) + np.testing.assert_array_equal(get_instance.x_propagation_matrix, prev_x_propagation_matrix) + np.testing.assert_array_equal(get_instance.z_propagation_matrix, prev_z_propagation_matrix) + assert get_instance.used_columns == prev_used_cols + assert get_instance.used_cnots == prev_used_cnots + + # 2. Check that the backtrack flag was reset. + assert get_instance.backtrack_required is False + + # 3. Check that the eliminations list had the last item popped. + assert get_instance.eliminations == [(1, 2)] + + # 4. Check the conditional logic: Was failed_cnots updated correctly? + # The `_` in the pop restores `prev_failed_cnots`, but then the method + # recalculates it based on the popped elimination. + # NOTE: Your implementation replaces the list entirely, so we check against + # the expected final list, not the restored one. + assert get_instance.failed_cnots == expected_failed_cnots + + +def test_compute_cost_matrix_golden_master(): + """Tests if the cost matrix is calculatet correctly. + + The test is based on the initial check matrix of the Steane Code. + """ + input_matrix = np.array([[1, 1, 0, 0, 1, 1, 0], [1, 0, 1, 0, 1, 0, 1], [0, 0, 0, 1, 1, 1, 1]], dtype=np.int8) + expected_cost_matrix = np.array([ + [1, 0, 0, 2, -2, 0, 0], + [-1, 1, 1, 1, -1, -1, 1], + [-1, 1, 1, 1, -1, 1, -1], + [1, 1, 1, 1, -1, -1, -1], + [-1, 1, 1, 1, 1, -1, -1], + [0, 0, 2, 0, -2, 1, 0], + [0, 2, 0, 0, -2, 0, 1], + ]) + instance = EliminationCNOTSynthesizer(matrix=input_matrix, code=CSSCode(input_matrix)) + cost_matrix = instance._compute_cost_matrix() + np.testing.assert_array_equal(cost_matrix, expected_cost_matrix) + + +def test_compute_cost_matrix_diagonal_is_always_one(get_instance): + """Verify that the diagonal of the cost matrix is always 1.""" + cost_matrix = get_instance._compute_cost_matrix() + + assert np.all(np.diag(cost_matrix) == 1) + + +def test_compute_cost_matrix_off_diagonal_logic(get_instance): + """Verify the core logic for a single off-diagonal element of the cost matrix. + + cost(i->j) = sum(col_i + col_j) - weight(col_j) + """ + # Let's test the cost of applying column 0 onto column 1: costs[0, 1] + matrix = get_instance.matrix + col_0 = matrix[:, 0] + col_1 = matrix[:, 1] + + # Manually calculate the expected value for just one cell. + xor_sum: npt.NDArray[np.int8] = np.sum((col_0 + col_1) % 2) + weight_col_1: npt.NDArray[np.int8] = np.sum(col_1) + expected_cost_0_1 = xor_sum - weight_col_1 + + cost_matrix = get_instance._compute_cost_matrix() + + assert cost_matrix[0, 1] == expected_cost_0_1 + + +def test_fault_set_guided_synthesis_validation_error(get_instance): + """Verify that providing a code without reference fault sets raises an error.""" + with pytest.raises(ValueError, match=r"Must provide either both a reference fault set and CSS code, or neither."): + # get_instance already has a CSSCode, but we provide no reference fault sets + get_instance.fault_set_guided_synthesis() + + +def test_fault_set_guided_synthesis_happy_path(get_instance): + """Verify that the synthesis successfully reduces the matrix with valid inputs.""" + # Create dummy reference fault sets for the 7-qubit Steane code + ref_x_fs = np.zeros((1, 7), dtype=np.int8) + ref_z_fs = np.zeros((1, 7), dtype=np.int8) + + get_instance.fault_set_guided_synthesis(ref_x_fs=ref_x_fs, ref_z_fs=ref_z_fs) + + assert get_instance.is_reduced() is True + assert len(get_instance.eliminations) > 0 + assert len(get_instance.used_cnots) > 0 + + +def test_fault_set_guided_synthesis_with_penalties(get_instance): + """Verify that the synthesis avoids CNOTs specified in penalty_cnots.""" + ref_x_fs = np.zeros((1, 7), dtype=np.int8) + ref_z_fs = np.zeros((1, 7), dtype=np.int8) + + # The greedy approach normally picks (0, 4) first for the Steane code. + # We penalize it to ensure the algorithm finds an alternative path. + penalties = [(0, 4)] + + get_instance.fault_set_guided_synthesis(ref_x_fs=ref_x_fs, ref_z_fs=ref_z_fs, penalty_cnots=penalties) + + assert get_instance.is_reduced() is True + assert (0, 4) not in get_instance.eliminations + + +def test_fault_set_guided_synthesis_guide_by_z(get_instance): + """Verify that the synthesis completes when guided by Z errors instead of X.""" + ref_x_fs = np.zeros((1, 7), dtype=np.int8) + ref_z_fs = np.zeros((1, 7), dtype=np.int8) + + get_instance.fault_set_guided_synthesis(ref_x_fs=ref_x_fs, ref_z_fs=ref_z_fs, guide_by_x=False) + + assert get_instance.is_reduced() is True diff --git a/tests/circuit_synthesis/test_utils.py b/tests/circuit_synthesis/test_utils.py index aa9cfdd72..40c2ea265 100644 --- a/tests/circuit_synthesis/test_utils.py +++ b/tests/circuit_synthesis/test_utils.py @@ -30,9 +30,9 @@ ) from mqt.qecc.circuit_synthesis.state_prep import final_matrix_constraint from mqt.qecc.circuit_synthesis.synthesis_utils import ( + EliminationCNOTSynthesizer, gaussian_elimination_min_column_ops, gaussian_elimination_min_parallel_eliminations, - heuristic_gaussian_elimination, measure_flagged, measure_stab_unflagged, odd_overlap, @@ -41,6 +41,7 @@ symbolic_vector_eq, vars_to_stab, ) +from mqt.qecc.codes.css_code import CSSCode if TYPE_CHECKING: import numpy.typing as npt @@ -181,8 +182,13 @@ def test_heuristic_gaussian_elimination(test_vals: MatrixTest, request) -> None: """Test heuristic Gaussian elimination method.""" fixture = request.getfixturevalue(test_vals) matrix = fixture.matrix - res_seq = heuristic_gaussian_elimination(matrix, parallel_elimination=False) - res_parallel = heuristic_gaussian_elimination(matrix, parallel_elimination=True) + unused_code = CSSCode(n=1) + ge_false = EliminationCNOTSynthesizer(matrix, code=unused_code, parallel_elimination=False) + ge_true = EliminationCNOTSynthesizer(matrix, code=unused_code) + ge_false.greedy_synthesis() + ge_true.greedy_synthesis() + res_seq = (ge_false.matrix, ge_false.eliminations) + res_parallel = (ge_true.matrix, ge_true.eliminations) assert res_seq is not None reduced_seq, ops_seq = res_seq