Skip to content

Commit

Permalink
Add from_heavy_hex() and from_heavy_square() generator methods to…
Browse files Browse the repository at this point in the history
… CouplingMap (#6959)

* add class methods for heavy hex and heavy square graphs

* added tests for heavy_hex and heavy_square

* fix black formatting

* changed variable name to 'distance'

* fixed variable name

* added bidirectional tests

* fixed linting

* added release note template

* Fix release note

* Expand docstring

* Fix copy paste errors in docstrings

Co-authored-by: Jake Lishman <jake@binhbar.com>

Co-authored-by: Matthew Treinish <mtreinish@kortar.org>
Co-authored-by: Jake Lishman <jake@binhbar.com>
  • Loading branch information
3 people authored Sep 21, 2021
1 parent 6efe3c5 commit 123a0a7
Show file tree
Hide file tree
Showing 3 changed files with 237 additions and 0 deletions.
50 changes: 50 additions & 0 deletions qiskit/transpiler/coupling.py
Original file line number Diff line number Diff line change
Expand Up @@ -320,6 +320,56 @@ def from_grid(cls, num_rows, num_columns, bidirectional=True):
)
return cmap

@classmethod
def from_heavy_hex(cls, distance, bidirectional=True):
"""Return a heavy hexagon graph coupling map
A heavy hexagon graph is described in:
https://journals.aps.org/prx/abstract/10.1103/PhysRevX.10.011022
Args:
distance (int): The code distance for the generated heavy hex
graph. The value for distance can be any odd positive integer.
The distance relates to the number of qubits by:
:math:`n = \\frac{5d^2 - 2d - 1}{2}` where :math:`n` is the
number of qubits and :math:`d` is the ``distance`` parameter.
bidirectional (bool): Whether the edges in the output coupling
graph are bidirectional or not. By default this is set to
``True``
Returns:
CouplingMap: A heavy hex coupling graph
"""
cmap = cls(description="heavy-hex")
cmap.graph = rx.generators.directed_heavy_hex_graph(distance, bidirectional=bidirectional)
return cmap

@classmethod
def from_heavy_square(cls, distance, bidirectional=True):
"""Return a heavy square graph coupling map.
A heavy square graph is described in:
https://journals.aps.org/prx/abstract/10.1103/PhysRevX.10.011022
Args:
distance (int): The code distance for the generated heavy square
graph. The value for distance can be any odd positive integer.
The distance relates to the number of qubits by:
:math:`n = 3d^2 - 2d` where :math:`n` is the
number of qubits and :math:`d` is the ``distance`` parameter.
bidirectional (bool): Whether the edges in the output coupling
graph are bidirectional or not. By default this is set to
``True``
Returns:
CouplingMap: A heavy square coupling graph
"""
cmap = cls(description="heavy-square")
cmap.graph = rx.generators.directed_heavy_square_graph(
distance, bidirectional=bidirectional
)
return cmap

def largest_connected_component(self):
"""Return a set of qubits in the largest connected component."""
return max(rx.weakly_connected_components(self.graph), key=len)
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
---
features:
- |
Added two new constructor methods,
:meth:`~qiskit.transpiler.CouplingMap.from_heavy_hex` and
:meth:`~qiskit.transpiler.CouplingMap.from_heavy_square`, to the
:class:`~qiskit.transpiler.CouplingMap` class. These constructor methods
are used to create a :class:`~qiskit.transpiler.CouplingMap` that are
a heavy hex or heavy square graph as described in:
https://journals.aps.org/prx/abstract/10.1103/PhysRevX.10.011022
For example:
.. jupyter-execute::
from qiskit.transpiler import CouplingMap
cmap = CouplingMap.from_heavy_hex(5)
cmap.draw()
.. jupyter-execute::
from qiskit.transpiler import CouplingMap
cmap = CouplingMap.from_heavy_square(5)
cmap.draw()
160 changes: 160 additions & 0 deletions test/python/transpiler/test_coupling.py
Original file line number Diff line number Diff line change
Expand Up @@ -196,6 +196,166 @@ def test_grid_factory_unidirectional(self):
expected = [(0, 3), (0, 1), (3, 4), (1, 4), (1, 2), (4, 5), (2, 5)]
self.assertEqual(set(edges), set(expected))

def test_heavy_hex_factory(self):
coupling = CouplingMap.from_heavy_hex(3, bidirectional=False)
edges = coupling.get_edges()
expected = [
(0, 9),
(0, 13),
(1, 13),
(1, 14),
(2, 14),
(3, 9),
(3, 15),
(4, 15),
(4, 16),
(5, 12),
(5, 16),
(6, 17),
(7, 17),
(7, 18),
(8, 12),
(8, 18),
(10, 14),
(10, 16),
(11, 15),
(11, 17),
]
self.assertEqual(set(edges), set(expected))

def test_heavy_hex_factory_bidirectional(self):
coupling = CouplingMap.from_heavy_hex(3, bidirectional=True)
edges = coupling.get_edges()
expected = [
(0, 9),
(0, 13),
(1, 13),
(1, 14),
(2, 14),
(3, 9),
(3, 15),
(4, 15),
(4, 16),
(5, 12),
(5, 16),
(6, 17),
(7, 17),
(7, 18),
(8, 12),
(8, 18),
(9, 0),
(9, 3),
(10, 14),
(10, 16),
(11, 15),
(11, 17),
(12, 5),
(12, 8),
(13, 0),
(13, 1),
(14, 1),
(14, 2),
(14, 10),
(15, 3),
(15, 4),
(15, 11),
(16, 4),
(16, 5),
(16, 10),
(17, 6),
(17, 7),
(17, 11),
(18, 7),
(18, 8),
]
self.assertEqual(set(edges), set(expected))

def test_heavy_square_factory(self):
coupling = CouplingMap.from_heavy_square(3, bidirectional=False)
edges = coupling.get_edges()
expected = [
(0, 15),
(1, 16),
(2, 11),
(3, 12),
(3, 17),
(4, 18),
(5, 11),
(6, 12),
(6, 19),
(7, 20),
(9, 15),
(9, 17),
(10, 16),
(10, 18),
(13, 17),
(13, 19),
(14, 18),
(14, 20),
(15, 1),
(16, 2),
(17, 4),
(18, 5),
(19, 7),
(20, 8),
]
self.assertEqual(set(edges), set(expected))

def test_heavy_square_factory_bidirectional(self):
coupling = CouplingMap.from_heavy_square(3, bidirectional=True)
edges = coupling.get_edges()
expected = [
(0, 15),
(1, 15),
(1, 16),
(2, 11),
(2, 16),
(3, 12),
(3, 17),
(4, 17),
(4, 18),
(5, 11),
(5, 18),
(6, 12),
(6, 19),
(7, 19),
(7, 20),
(8, 20),
(9, 15),
(9, 17),
(10, 16),
(10, 18),
(11, 2),
(11, 5),
(12, 3),
(12, 6),
(13, 17),
(13, 19),
(14, 18),
(14, 20),
(15, 0),
(15, 1),
(15, 9),
(16, 1),
(16, 2),
(16, 10),
(17, 3),
(17, 4),
(17, 9),
(17, 13),
(18, 4),
(18, 5),
(18, 10),
(18, 14),
(19, 6),
(19, 7),
(19, 13),
(20, 7),
(20, 8),
(20, 14),
]
self.assertEqual(set(edges), set(expected))

def test_subgraph(self):
coupling = CouplingMap.from_line(6, bidirectional=False)
with self.assertWarns(DeprecationWarning):
Expand Down

0 comments on commit 123a0a7

Please sign in to comment.