3

I want to create a graph using NetworkX, layout the graph using Graphviz(via pygraphviz). I have successfully ran all the examples in the NetworkX pygraphviz examples documentation

The question I have is - how do I get the coordinates (x, y) and dimensions (width, height) of the vertices back into the NetworkX graph. That is the goal. I want only Graphviz' layout capabilities, not drawing capabilities. Is that possible using this stack (NetworkX, pygraphviz, graphviz)? Any other way?

The background motivation is this. Graphviz outputs png, or ps, or svg and many other formats. But I don't want to be constrained by the formats Graphviz handles. And I want to be able to post-process the layout results, even if I end up outputting the popular formats like Graphviz does support.

Update: I have rewritten the question for clarity. The advice on Graphviz output formats miss the point. It is the layout data that I need

Update2: One suggestion was to make Graphviz ouptput in some format that I can then parse the layout data back from. The suggestion was for SVG. I had had considered that possibility. Graphviz outputs json (according to Graphviz output formats documentation page). I failed to make it work on my windows installation - for some reason not all the output formats were present). However it is the approach that makes me uneasy. Parsing formatted output for data that was used to create that output seems backwards. The data itself should have been made available, I think.

Update 3 - There is a similar question - How to get the coordinates from layout from graphviz?. One of the answers suggests using NetworkX. However the answer uses layout made by NetworkX and not Graphviz. The author of the answer did not know how to get the Graphviz layout data. So my question remains relevant, and yet to be answered

Update 4 - it is 07-2019 and I still did not find a way to solve this. I marked one answer as accepted - but with a caveat - I still am in the dark despite the good advice found in that answer

4

4 回答 4

1

迈克尔,我重新阅读了你的问题和评论,并使用我知道的工具(而且我知道如何使用),这就是我在你的鞋子里所做的。我会在 DOT/GraphViz 中绘制您的图表,然后选择一种人类可读且易于解析的格式,例如 SVG、“plain”甚至 x-dot。为什么?不是要获取图形本身——其中一些甚至不实现图形——而是因为这些格式是人类可读的并且包含不同绘图组件的 XY 坐标。您可以根据自己的目的使用这些坐标和大小。我刚刚做的一个简单图表中的一些片段应该可以说明。SVG优先

<svg width="89pt" height="188pt"

<g id="node1" class="node"><title>A</title>
<ellipse fill="none" stroke="black" cx="54" cy="-162" rx="27" ry="18"/>
<text text-anchor="middle" x="54" y="-158.3" font-family="Times New Roman,serif" font-size="14.00">A</text>

或者以“普通”格式,也许是最简单的解析:

graph 1 0.75 1.5
node A 0.375 1.25 0.75 0.5 A solid ellipse black lightgrey
node B 0.375 0.25 0.75 0.5 B solid ellipse black lightgrey
edge A B 4 0.375 0.99579 0.375 0.88865 0.375 0.7599 0.375 0.64045 solid black
stop

或类似 html 的 VML:

<v:oval style="position:absolute; left: 0.00; top: 0.00; width: 54.00; height: 36.00" filled="false"  >

等等... 不难想象解析出各种元素的所有 X-Y 轴,并按照您认为合适的方式重新调整它们的用途。

于 2017-07-18T20:11:11.530 回答
1

关于更新 4

现在仍然是 2019 年,但这非常适合我的需求

import networkx as nx
G = nx.complete_graph(10)
pos = nx.drawing.nx_agraph.graphviz_layout(G, prog='dot')
print(pos)

给我吗

{0: (327.0, 666.0), 1: (504.0, 594.0), 2: (327.0, 522.0), 3: (449.0, 450.0), 4: (283.0, 378.0), 5: (283.0, 306.0), 6: (473.0, 234.0), 7: (287.0, 162.0), 8: (418.0, 90.0), 9: (287.0, 18.0)}

节点和位置的字典!

迎接dom

于 2019-09-11T17:19:26.567 回答
1

这是另一个解决方案。它与 Dominik Ku​​mmer 的不同之处在于它公开了pygraphviz.AGraph对象,从而可以指定任意 gaphviz 属性来自定义布局。

import networkx as nx
import pygraphviz as pgv

g = nx.complete_graph(10)
ag = nx.drawing.nx_agraph.to_agraph(g)
ag.layout(prog='dot')
layout = [ag.get_node(n).attr['pos'] for n in ag.nodes()]
layout = [[int(ss) for ss in s.split(",")] for s in layout]
print(layout)

给我吗:

[[327, 666], [504, 594], [327, 522], [449, 450], [283, 378], [283, 306], [473, 234], [287, 162], [418, 90], [287, 18]]

于 2020-05-27T14:18:30.013 回答
0

PyGraphviz 没有用于检索和设置布局信息(例如节点形状、边缘路由等)的 API。我不知道 Graphviz C 库的这些部分有任何 Python 接口。Graphviz 本身确实提供了一个 Python 接口,包括渲染器,但我认为它也不完全符合您的要求 - 请参阅http://www.graphviz.org/pdf/gv.3python.pdf

正如@JHL 建议的那样,最简单的方法可能确实是通过生成 SVG。

于 2017-07-19T13:44:32.577 回答