首页 > 解决方案 > python graphviz中的子图方法?

问题描述

所以我试图在 python 上使用 graphviz 包,它有一个名为的方法subgraph(),但我认为它与网络理论中广泛使用的定义不同。

据我所知,子图是指一个图,其节点和边是另一个图的子集。

在graphviz用户指南上它说:
将给定的唯一图形参数的当前内容添加为子图或返回一个上下文管理器,返回一个使用给定(名称,评论等)参数创建的新图形实例,其内容在离开时作为子图添加上下文管理器的 with 块。

这是用户指南中的示例

import graphviz
p = Graph(name='parent')
p.edge('spam', 'eggs')
c = Graph(name='child', node_attr={'shape': 'box'})
c.edge('foo', 'bar')

p.subgraph(c)

例子

根据网络理论,图 p 应该具有所有节点 'spam'、'eggs'、'foo'、'bar',并且子图 c 应该由图 p 中使用的节点和边组成。

但事实并非如此。似乎 subgraph() 方法只是将两个图合二为一。我对吗?

什么是特殊的簇子图?(如果子图的名称以“cluster”开头,布局引擎会将其视为特殊的集群子图)。我在谷歌上找不到任何结果。

谢谢

标签: pythonnetwork-programmingnetworkxgraphvizpygraphviz

解决方案


您可以将subgraph其视为对节点和边进行逻辑分组的工具。

考虑以下示例(如果您不介意,我将使用本机 Graphviz 语法,而不是 Python Graphviz 包装器):

digraph {
    a -> b
    c
    d -> e
    f
    g -> h
    c -> a
}

原来的

现在让我们在节点周围添加一个子图cde更改全局节点属性,例如,给它们矩形形状和红色:

digraph {
    a -> b
    subgraph mysubgraph {
        node [shape=rect color=red]
        c
        d -> e
    }
    f
    g -> h
    c -> a
}

分段

如您所见,节点放置没有任何变化,但是子图中的那些节点改变了形状和颜色。另外,请注意您是对的:我们影响了c定义为节点的节点和d;e隐式定义为边的节点。

我们还可以使用带有rank属性的子图来控制节点放置(这就是大多数时候使用的子图) 。要强制子图中的节点出现在同一行,请在子图中添加一个rank=same属性:

digraph {
    a -> b
    subgraph mysubgraph {
        node [shape=rect color=red]
        rank=same
        c
        d -> e
    }
    f
    g -> h
    c -> a
}

等级相同

集群是一个完全不同的故事。当您在子图名称的开头添加单词“cluster”时,在此集群内定义的节点将物理地聚集在一起。您还将获得一个矩形(默认情况下)将这些节点包裹在您的图表上:

digraph {
    a -> b
    subgraph cluster_mysubgraph {
        node [shape=rect color=red]
        c
        d -> e
    }
    f
    g -> h
    c -> a
}

簇

注意这张图和第二张图的区别。我建议您谨慎使用集群。一旦您在集群内外的节点之间建立了连接,就布局而言,事情可能会变得很奇怪。

顺便说一句,通过官方文档学习 garphviz 真的很难,因为它们更多的是参考而不是指导。但他们也有一个很好的指南,用普通人(对不起,数学家)的好语言编写,但它被埋在 Graphviz 网站中:https ://graphviz.gitlab.io/_pages/pdf/dotguide.pdf


推荐阅读