From d086d37edcfd2ed85f219daf23cb67d70dfe0454 Mon Sep 17 00:00:00 2001 From: Asa-Kosto-QTM <108833721+Asa-Kosto-QTM@users.noreply.github.com> Date: Tue, 17 Oct 2023 15:32:37 -0400 Subject: [PATCH] enforce relative ordering to prevent unnecessary swaps (#10) --- pytket/phir/place_and_route.py | 1 - pytket/phir/placement.py | 25 ++++++++++++------------- tests/e2e_test.py | 3 ++- 3 files changed, 14 insertions(+), 15 deletions(-) diff --git a/pytket/phir/place_and_route.py b/pytket/phir/place_and_route.py index 5105ed7..434e4e7 100644 --- a/pytket/phir/place_and_route.py +++ b/pytket/phir/place_and_route.py @@ -19,7 +19,6 @@ def place_and_route(machine: Machine, qasm: Circuit): shards = sharder.shard() shard_set = set(shards) circuit_rep, shard_layers = parse_shards_naive(shard_set) - # print(circuit_rep) initial_order = list(range(machine.size)) layer_num = 0 orders: list[list[int]] = [] diff --git a/pytket/phir/placement.py b/pytket/phir/placement.py index f028dfa..5c3f555 100644 --- a/pytket/phir/placement.py +++ b/pytket/phir/placement.py @@ -206,22 +206,21 @@ def optimized_place( # noqa: PLR0912 if len(sq_ops) > len(sq_zones) - 2 * len(tq_ops): # Because SQ zones are offsets of TQ zones, each tq op covers 2 sq zones raise GateOpportunitiesError - # place the tq ops order = place_tq_ops(tq_ops_sorted, placed_qubits, order, tq_zones, sq_zones) # run a check to avoid unnecessary swaps - for zone in tq_zones: - # this condition is true if there was a swap due to the order of qubits_used - # in the shard creating the TQ op, - # even if those two qubits were already in a TQ zone - # example: ops = [[0,1]] prev_state = [0,1,2,3] new order = [1,0,2,3] - # this check s to prevent the above situation - if (order[zone] == prev_state[zone + 1]) & ( - order[zone + 1] == prev_state[zone] - ): - swapped = order[zone + 1] - order[zone + 1] = order[zone] - order[zone] = swapped + prev_state_inv = inverse(prev_state) + for zone in tq_options: + # enforce the relative ordering of qubits to prevent uneseccasry swaps + # if the first qubit of a TQ gate was to the right of the second in prev_state + # then there has been an unnecessary swap + q0s = order[zone] + q1s = order[zone + 1] + if prev_state_inv[q0s] > prev_state_inv[q1s]: + swapped = order[zone] + order[zone] = order[zone + 1] + order[zone + 1] = swapped + # place the sq ops for op in sq_ops: q1 = op[0] diff --git a/tests/e2e_test.py b/tests/e2e_test.py index 4f43d33..b90b36a 100644 --- a/tests/e2e_test.py +++ b/tests/e2e_test.py @@ -30,6 +30,7 @@ assert shard.ID in {0, 1} # type: ignore [misc] for shard in shards_1: # type: ignore [misc] assert shard.ID in {2, 3} # type: ignore [misc] - # cost_0 is wrong because we are getting an unnecessary swap, add swap reduction option? # noqa: E501 + cost_0 = output[0][2] # type: ignore [misc] cost_1 = output[1][2] # type: ignore [misc] + assert cost_0 == 2.0 # type: ignore [misc] assert cost_1 == 0.0 # type: ignore [misc]