Для удобства пользования решение, описанное в ответе HighPerformanceMark применительно к исходному вопросу, выглядит следующим образом:
digraph G {
graph [fontsize=10 fontname="Verdana" compound=true];
node [shape=record fontsize=10 fontname="Verdana"];
subgraph cluster_0 {
node [style=filled];
"Item 1" "Item 2";
label = "Container A";
color=blue;
}
subgraph cluster_1 {
node [style=filled];
"Item 3" "Item 4";
label = "Container B";
color=blue;
}
subgraph cluster_2 {
node [style=filled];
"Item 5" "Item 6";
label = "Container C";
color=blue;
}
// Edges between nodes render fine
"Item 1" -> "Item 2";
"Item 2" -> "Item 3";
// Edges that directly connect one cluster to another
"Item 1" -> "Item 3" [ltail=cluster_0 lhead=cluster_1];
"Item 1" -> "Item 5" [ltail=cluster_0 lhead=cluster_2];
}
compound=true
в декларации graph
имеет жизненно важное значение. Это производит вывод:
![graph with connected clusters](https://i.stack.imgur.com/pEEsK.png)
Обратите внимание, что я изменил ребра на ссылочные узлы в кластере, добавил атрибуты ltail и lhead для каждого ребра, указав имя кластера, и добавил атрибут уровня графа 'component = true'.
Что касается беспокойства о том, что кто-то может захотеть подключить кластер без узлов внутри него, мое решение было всегда добавить узел в каждый кластер, визуализированный с помощью style = plaintext. Используйте этот узел для маркировки кластера (вместо встроенного в кластер атрибута «label», который должен быть установлен в пустую строку (в Python, label='""'
). Это означает, что я больше не добавляю ребра, которые соединяют кластеры напрямую , но это работает в моей конкретной ситуации.