Skip to content

Commit

Permalink
Fix dag visualization with Var wires (#12848)
Browse files Browse the repository at this point in the history
* Fix dag visualization with Var wires

This commit fixes the dag visualization for DAGs with classical
variables. The Var type was not handled in the attribute callback
functions for nodes and edges. This was causing the visualizer to fail
if the dag contained these types. This fixes this by adding explict
handling for the Var types and using the name attribute of the Var
object.

* Add release note and test
  • Loading branch information
mtreinish authored Aug 8, 2024
1 parent fa5510c commit adbe887
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 4 deletions.
13 changes: 10 additions & 3 deletions qiskit/visualization/dag_visualization.py
Original file line number Diff line number Diff line change
Expand Up @@ -174,10 +174,13 @@ def node_attr_func(node):
label = register_bit_labels.get(
node.wire, f"q_{dag.find_bit(node.wire).index}"
)
else:
elif isinstance(node.wire, Clbit):
label = register_bit_labels.get(
node.wire, f"c_{dag.find_bit(node.wire).index}"
)
else:
label = str(node.wire.name)

n["label"] = label
n["color"] = "black"
n["style"] = "filled"
Expand All @@ -187,10 +190,12 @@ def node_attr_func(node):
label = register_bit_labels.get(
node.wire, f"q[{dag.find_bit(node.wire).index}]"
)
else:
elif isinstance(node.wire, Clbit):
label = register_bit_labels.get(
node.wire, f"c[{dag.find_bit(node.wire).index}]"
)
else:
label = str(node.wire.name)
n["label"] = label
n["color"] = "black"
n["style"] = "filled"
Expand All @@ -203,8 +208,10 @@ def edge_attr_func(edge):
e = {}
if isinstance(edge, Qubit):
label = register_bit_labels.get(edge, f"q_{dag.find_bit(edge).index}")
else:
elif isinstance(edge, Clbit):
label = register_bit_labels.get(edge, f"c_{dag.find_bit(edge).index}")
else:
label = str(edge.name)
e["label"] = label
return e

Expand Down
8 changes: 8 additions & 0 deletions releasenotes/notes/fix-var-wires-4ebc40e0b19df253.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
---
fixes:
- |
Fixed an issue with :func:`.dag_drawer` and :meth:`.DAGCircuit.draw`
when attempting to visualize a :class:`.DAGCircuit` instance that contained
:class:`.Var` wires. The visualizer would raise an exception trying to
do this which has been fixed so the expected visualization will be
generated.
15 changes: 14 additions & 1 deletion test/python/visualization/test_dag_drawer.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,14 @@
import tempfile
import unittest

from qiskit.circuit import QuantumRegister, ClassicalRegister, QuantumCircuit, Qubit, Clbit
from qiskit.circuit import QuantumRegister, ClassicalRegister, QuantumCircuit, Qubit, Clbit, Store
from qiskit.visualization import dag_drawer
from qiskit.exceptions import InvalidFileError
from qiskit.visualization import VisualizationError
from qiskit.converters import circuit_to_dag, circuit_to_dagdependency
from qiskit.utils import optionals as _optionals
from qiskit.dagcircuit import DAGCircuit
from qiskit.circuit.classical import expr, types
from .visualization import path_to_diagram_reference, QiskitVisualizationTestCase


Expand Down Expand Up @@ -108,6 +110,17 @@ def test_dag_drawer_with_dag_dep(self):
image = Image.open(tmp_path)
self.assertImagesAreEqual(image, image_ref, 0.1)

@unittest.skipUnless(_optionals.HAS_GRAPHVIZ, "Graphviz not installed")
@unittest.skipUnless(_optionals.HAS_PIL, "PIL not installed")
def test_dag_drawer_with_var_wires(self):
"""Test visualization works with var nodes."""
a = expr.Var.new("a", types.Bool())
dag = DAGCircuit()
dag.add_input_var(a)
dag.apply_operation_back(Store(a, a), (), ())
image = dag_drawer(dag)
self.assertIsNotNone(image)


if __name__ == "__main__":
unittest.main(verbosity=2)

0 comments on commit adbe887

Please sign in to comment.