def test_circuit_iadd(): c = stim.Circuit() alias = c c.append_operation("X", [1, 2]) c2 = stim.Circuit() c2.append_operation("Y", [3]) c2.append_operation("M", [4]) c += c2 assert c is alias assert str(c).strip() == """ X 1 2 Y 3 M 4 """.strip() c += c assert str(c).strip() == """ X 1 2 Y 3 M 4 X 1 2 Y 3 M 4 """.strip() assert c is alias
def test_circuit_clear(): c = stim.Circuit(""" X 0 M 0 """) c.clear() assert c == stim.Circuit()
def test_circuit_flattened_operations(): for e in stim.Circuit(''' H 0 REPEAT 3 { X_ERROR(0.125) 1 } CORRELATED_ERROR(0.25) X3 Y4 Z5 M 0 !1 DETECTOR rec[-1] ''').flattened_operations(): print(e) assert stim.Circuit(''' H 0 REPEAT 3 { X_ERROR(0.125) 1 } CORRELATED_ERROR(0.25) X3 Y4 Z5 M 0 !1 DETECTOR rec[-1] ''').flattened_operations() == [ ("H", [0], 0), ("X_ERROR", [1], 0.125), ("X_ERROR", [1], 0.125), ("X_ERROR", [1], 0.125), ("E", [("X", 3), ("Y", 4), ("Z", 5)], 0.25), ("M", [0, ("inv", 1)], 0), ("DETECTOR", [("rec", -1)], 0), ]
def test_circuit_mul(): c = stim.Circuit() c.append_operation("Y", [3]) c.append_operation("M", [4]) assert str(c * 2) == str(2 * c) == """ REPEAT 2 { Y 3 M 4 } """.strip() assert str((c * 2) * 3) == """ REPEAT 6 { Y 3 M 4 } """.strip() expected = """ REPEAT 3 { Y 3 M 4 } """.strip() assert str(c * 3) == str(3 * c) == expected c *= 3 assert str(c) == expected c *= 1 assert str(c) == expected c *= 0 assert str(c) == ""
def test_stim_circuit_to_cirq_circuit(): circuit = stimcirq.stim_circuit_to_cirq_circuit( stim.Circuit(""" X 0 CNOT 0 1 X_ERROR(0.125) 0 1 CORRELATED_ERROR(0.25) X0 Y1 Z2 M 1 M !1 MR 0 !1 """)) a, b, c = cirq.LineQubit.range(3) assert circuit == cirq.Circuit( cirq.X(a), cirq.CNOT(a, b), cirq.X.with_probability(0.125).on(a), cirq.X.with_probability(0.125).on(b), cirq.PauliString({ a: cirq.X, b: cirq.Y, c: cirq.Z }).with_probability(0.25), cirq.measure(b, key="0"), cirq.measure(b, key="1", invert_mask=(True, )), cirq.measure(a, key="2"), cirq.ResetChannel().on(a), cirq.measure(b, key="3", invert_mask=(True, )), cirq.ResetChannel().on(b), )
def test_circuit_compile_sampler(): c = stim.Circuit() s = c.compile_sampler() c.append_operation("M", [0]) print(repr(s)) assert repr(s) == "stim.CompiledMeasurementSampler(stim.Circuit())" s = c.compile_sampler() assert repr(s) == """ stim.CompiledMeasurementSampler(stim.Circuit(''' M 0 ''')) """.strip() c.append_operation("H", [0, 1, 2, 3, 4]) c.append_operation("M", [0, 1, 2, 3, 4]) s = c.compile_sampler() r = repr(s) assert r == """ stim.CompiledMeasurementSampler(stim.Circuit(''' M 0 H 0 1 2 3 4 M 0 1 2 3 4 ''')) """.strip() == str(stim.CompiledMeasurementSampler(c)) # Check that expression can be evaluated. _ = eval(r, {"stim": stim})
def assert_unitary_gate_converts_correctly(gate: cirq.Gate): n = gate.num_qubits() for pre, post in solve_tableau(gate).items(): # Create a circuit that measures pre before the gate times post after the gate. # If the gate is translated correctly, the measurement will always be zero. c = stim.Circuit() c.append_operation("H", range(n)) for i in range(n): c.append_operation("CNOT", [i, i + n]) c.append_operation("H", [2 * n]) for q, p in pre.items(): c.append_operation(f"C{p}", [2 * n, q.x]) qs = cirq.LineQubit.range(n) conv_gate, _ = cirq_circuit_to_stim_data(cirq.Circuit(gate(*qs)), q2i={q: q.x for q in qs}) c += conv_gate for q, p in post.items(): c.append_operation(f"C{p}", [2 * n, q.x]) if post.coefficient == -1: c.append_operation("Z", [2 * n]) c.append_operation("H", [2 * n]) c.append_operation("M", [2 * n]) correct = not np.any(c.compile_sampler().sample_bit_packed(10)) assert correct, f"{gate!r} failed to turn {pre} into {post}.\nConverted to:\n{conv_gate}\n"
def test_circuit_add(): c = stim.Circuit() c.append_operation("X", [1, 2]) c2 = stim.Circuit() c2.append_operation("Y", [3]) c2.append_operation("M", [4]) assert str(c + c2).strip() == """ X 1 2 Y 3 M 4 """.strip() assert str(c2 + c2).strip() == """ Y 3 M 4 Y 3 M 4 """.strip()
def test_circuit_repr(): v = stim.Circuit(""" X 0 M 0 """) r = repr(v) assert r == """stim.Circuit(''' X 0 M 0 ''')""" assert eval(r, {'stim': stim}) == v
def cirq_circuit_to_stim_data( circuit: cirq.Circuit, *, q2i: Optional[Dict[cirq.Qid, int]] = None ) -> Tuple[stim.Circuit, List[Tuple[str, int]]]: """Converts a Cirq circuit into a Stim circuit and also metadata about where measurements go.""" if q2i is None: q2i = {q: i for i, q in enumerate(sorted(circuit.all_qubits()))} out = stim.Circuit() key_out: List[Tuple[str, int]] = [] _c2s_helper(circuit.all_operations(), q2i, out, key_out) return out, key_out
def test_gates_present(name: str): t = stim.Tableau.from_named_gate(name) n = len(t) s1 = stim.TableauSimulator() s2 = stim.TableauSimulator() for k in range(n): s1.h(k) s2.h(k) s1.cnot(k, k + n) s2.cnot(k, k + n) getattr(s1, name)(*range(n)) s2.do(stim.Circuit(f"{name} " + " ".join(str(e) for e in range(n)))) assert s1.current_inverse_tableau() == s2.current_inverse_tableau()
def test_circuit_compile_detector_sampler(): c = stim.Circuit() s = c.compile_detector_sampler() c.append_operation("M", [0]) assert repr(s) == "stim.CompiledDetectorSampler(stim.Circuit())" c.append_operation("DETECTOR", [stim.target_rec(-1)]) s = c.compile_detector_sampler() r = repr(s) assert r == """ stim.CompiledDetectorSampler(stim.Circuit(''' M 0 DETECTOR rec[-1] ''')) """.strip() # Check that expression can be evaluated. _ = eval(r, {"stim": stim})
def test_circuit_append_operation(): c = stim.Circuit() with pytest.raises(IndexError, match="Gate not found"): c.append_operation("NOT_A_GATE", [0]) with pytest.raises(IndexError, match="even number of targets"): c.append_operation("CNOT", [0]) with pytest.raises(IndexError, match="doesn't take"): c.append_operation("X", [0], 0.5) with pytest.raises(IndexError, match="invalid flags"): c.append_operation("X", [stim.target_inv(0)]) with pytest.raises(IndexError, match="invalid flags"): c.append_operation("X", [stim.target_x(0)]) with pytest.raises(IndexError, match="lookback"): stim.target_rec(0) with pytest.raises(IndexError, match="lookback"): stim.target_rec(1) with pytest.raises(IndexError, match="lookback"): stim.target_rec(-2**30) assert stim.target_rec(-1) is not None assert stim.target_rec(-15) is not None c.append_operation("X", [0]) c.append_operation("X", [1, 2]) c.append_operation("X", [3]) c.append_operation("CNOT", [0, 1]) c.append_operation("M", [0, stim.target_inv(1)]) c.append_operation("X_ERROR", [0], 0.25) c.append_operation("CORRELATED_ERROR", [stim.target_x(0), stim.target_y(1)], 0.5) c.append_operation("DETECTOR", [stim.target_rec(-1)]) c.append_operation( "OBSERVABLE_INCLUDE", [stim.target_rec(-1), stim.target_rec(-2)], 5) assert str(c).strip() == """ X 0 1 2 3 CX 0 1 M 0 !1 X_ERROR(0.25) 0 E(0.5) X0 Y1 DETECTOR rec[-1] OBSERVABLE_INCLUDE(5) rec[-1] rec[-2] """.strip()
def test_circuit_init_num_measurements_num_qubits(): c = stim.Circuit() assert c.num_qubits == c.num_measurements == 0 assert str(c).strip() == "" c.append_operation("X", [3]) assert c.num_qubits == 4 assert c.num_measurements == 0 assert str(c).strip() == """ X 3 """.strip() c.append_operation("M", [0]) assert c.num_qubits == 4 assert c.num_measurements == 1 assert str(c).strip() == """ X 3 M 0 """.strip()
def test_compiled_measurement_sampler_sample(): c = stim.Circuit() c.append_operation("X", [1]) c.append_operation("M", [0, 1, 2, 3]) np.testing.assert_array_equal( c.compile_sampler().sample(5), np.array([ [0, 1, 0, 0], [0, 1, 0, 0], [0, 1, 0, 0], [0, 1, 0, 0], [0, 1, 0, 0], ], dtype=np.uint8)) np.testing.assert_array_equal( c.compile_sampler().sample_bit_packed(5), np.array([ [0b00010], [0b00010], [0b00010], [0b00010], [0b00010], ], dtype=np.uint8))
def test_circuit_eq(): a = """ X 0 M 0 """ b = """ Y 0 M 0 """ assert stim.Circuit() == stim.Circuit() assert stim.Circuit() != stim.Circuit(a) assert not (stim.Circuit() != stim.Circuit()) assert not (stim.Circuit() == stim.Circuit(a)) assert stim.Circuit(a) == stim.Circuit(a) assert stim.Circuit(b) == stim.Circuit(b) assert stim.Circuit(a) != stim.Circuit(b) assert stim.Circuit() != None assert stim.Circuit != object() assert stim.Circuit != "another type" assert not (stim.Circuit == None) assert not (stim.Circuit == object()) assert not (stim.Circuit == "another type")
def test_do(): s = stim.TableauSimulator() s.do(stim.Circuit(""" S 0 """)) assert s.current_inverse_tableau() == stim.Tableau.from_named_gate("S_DAG")
def test_copy(): c = stim.Circuit("H 0") c2 = c.copy() assert c == c2 assert c is not c2
def test_hash(): # stim.Circuit is mutable. It must not also be value-hashable. # Defining __hash__ requires defining a FrozenCircuit variant instead. with pytest.raises(TypeError, match="unhashable"): _ = hash(stim.Circuit())
def test_compiled_detector_sampler_sample(): c = stim.Circuit() c.append_operation("X_ERROR", [0], 1) c.append_operation("M", [0, 1, 2]) c.append_operation("DETECTOR", [stim.target_rec(-3), stim.target_rec(-2)]) c.append_operation("DETECTOR", [stim.target_rec(-3), stim.target_rec(-1)]) c.append_operation("DETECTOR", [stim.target_rec(-1), stim.target_rec(-2)]) c.append_from_stim_program_text(""" OBSERVABLE_INCLUDE(0) rec[-3] OBSERVABLE_INCLUDE(3) rec[-2] rec[-1] """) c.append_operation("OBSERVABLE_INCLUDE", [stim.target_rec(-2)], 0) np.testing.assert_array_equal( c.compile_detector_sampler().sample(5), np.array([ [1, 1, 0], [1, 1, 0], [1, 1, 0], [1, 1, 0], [1, 1, 0], ], dtype=np.uint8)) np.testing.assert_array_equal( c.compile_detector_sampler().sample(5, prepend_observables=True), np.array([ [1, 0, 0, 0, 1, 1, 0], [1, 0, 0, 0, 1, 1, 0], [1, 0, 0, 0, 1, 1, 0], [1, 0, 0, 0, 1, 1, 0], [1, 0, 0, 0, 1, 1, 0], ], dtype=np.uint8)) np.testing.assert_array_equal( c.compile_detector_sampler().sample(5, append_observables=True), np.array([ [1, 1, 0, 1, 0, 0, 0], [1, 1, 0, 1, 0, 0, 0], [1, 1, 0, 1, 0, 0, 0], [1, 1, 0, 1, 0, 0, 0], [1, 1, 0, 1, 0, 0, 0], ], dtype=np.uint8)) np.testing.assert_array_equal( c.compile_detector_sampler().sample(5, append_observables=True, prepend_observables=True), np.array([ [1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0], [1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0], [1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0], [1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0], [1, 0, 0, 0, 1, 1, 0, 1, 0, 0, 0], ], dtype=np.uint8)) np.testing.assert_array_equal( c.compile_detector_sampler().sample_bit_packed(5), np.array([ [0b011], [0b011], [0b011], [0b011], [0b011], ], dtype=np.uint8))
def test_circuit_eq(): a = """ X 0 M 0 """ b = """ Y 0 M 0 """ assert stim.Circuit() == stim.Circuit() assert stim.Circuit() != stim.Circuit(a) assert not (stim.Circuit() != stim.Circuit()) assert not (stim.Circuit() == stim.Circuit(a)) assert stim.Circuit(a) == stim.Circuit(a) assert stim.Circuit(b) == stim.Circuit(b) assert stim.Circuit(a) != stim.Circuit(b)