脚本如何最佳地布局纯分层图可视化/点图?

发布于 2025-01-05 02:46:10 字数 2713 浏览 5 评论 0原文

我即将编写一个脚本,生成具有以下两个特征的 graphviz/dot 图:

  1. 除了一个节点之外的所有节点都只有一个父节点(因此,它是一棵树)。
  2. 如果两个或多个节点共享相同的父节点,则它们本身是 按特定顺序。

有了这些特征,我希望我的结果(即点生成的图形)看起来像这样:

  1. 没有边应该交叉
  2. 具有相同父级的节点应该与图形顶部边框具有相同的距离。
  3. 具有相同父节点的节点应按照从左到右的顺序绘制 。

但是,我无法让 dot 按照我想要的方式运行 这是一个点文件来演示我的问题:

digraph G {

  node [shape=plaintext fontname="Arial"];

  0  [label="zero"      ];
  1  [label="one"       ];
  2  [label="two"       ];
  3  [label="three"     ];
  4  [label="four"      ];
  5  [label="five"      ];
  6  [label="six"       ];
  7  [label="seven"     ];
  8  [label="eight"     ];
  9  [label="nine"      ];
  10 [label="ten"       ];
  11 [label="eleven"    ];
  12 [label="twelve"    ];
  13 [label="thirteen"  ];
  14 [label="fourteen"  ];
  15 [label="fivteen"   ];
  16 [label="sixteen"   ];
  17 [label="seventeen" ];
  18 [label="eighteen"  ];
  19 [label="nineteen"  ];
  20 [label="twenty"    ];
  21 [label="twenty-one"];
  22 [label="twenty-two"];

  0  -> 1  [arrowhead=none];
  1  -> 2  [arrowhead=none];
  2  -> 7  [arrowhead=none];
  7  -> 8  [arrowhead=none];
  8  -> 9  [arrowhead=none];
  8  -> 10 [arrowhead=none];
  9  -> 10 [color="#aaaaaa" constraint=false];
  10 -> 11 [arrowhead=none];
  10 -> 12 [arrowhead=none];
  11 -> 12 [color="#aaaaaa" constraint=false];
  7  -> 13 [arrowhead=none];
  8  -> 13 [color="#aaaaaa" constraint=false];
  13 -> 14 [arrowhead=none];
  7  -> 15 [arrowhead=none];
  13 -> 15 [color="#aaaaaa" constraint=false];
  15 -> 16 [arrowhead=none];
  15 -> 17 [arrowhead=none];
  16 -> 17 [color="#aaaaaa" constraint=false];
  2  -> 3  [arrowhead=none];
  7  -> 3  [color="#aaaaaa" constraint=false];
  3  -> 4  [arrowhead=none];
  2  -> 5  [arrowhead=none];
  3  -> 5  [color="#aaaaaa" constraint=false];
  5  -> 6  [arrowhead=none];
  2  -> 18 [arrowhead=none];
  5  -> 18 [color="#aaaaaa" constraint=false];
  18 -> 19 [arrowhead=none];
  19 -> 20 [arrowhead=none];
  19 -> 21 [arrowhead=none];
  20 -> 21 [color="#aaaaaa" constraint=false];
  18 -> 22 [arrowhead=none];
  19 -> 22 [color="#aaaaaa" constraint=false];
}

结果

Resulting graph

注意,兄弟姐妹之间的顺序由灰色边缘表示(箭头)。

例如,我对七 -> 感到满意。三->五->十八个兄弟姐妹,因为它们是按照正确的顺序从左到右绘制的(如箭头所示)。

但我对兄弟姐妹八 -> 不满意。十三->十五 因为它们的边与其他边交叉,并且因为它们的顺序不是像我希望的那样从左到右。

另外,九 ->十二十 ->二十一十九 ->二十二方向错误。

我知道如果我使用额外的(不可见的)边缘和权重属性以及可能更多的功能,我可能可以得到我想要的图片。但由于图表(其中有很多)是由脚本生成的,我无法手动执行此操作。

那么,有没有办法实现我想要的呢?

I am about to write a script that generates graphviz/dot graphs with the following two characteristics:

  1. All except one node have excactly one parent node (so, it's a tree).
  2. If two or more node share the sampe parent node, they themselves are
    in a specific order.

With these characteristics, I'd like my resulting (that is dot-generated graph) to look like so:

  1. No edges should cross
  2. Nodes with the same parent should have the same distance from the graphs top border.
  3. Nodes with the same parent should be drawn from left to right according
    to their ordering

However, I can't make dot behave the way I'd like. Here's a dot file to demonstrate my problem:

digraph G {

  node [shape=plaintext fontname="Arial"];

  0  [label="zero"      ];
  1  [label="one"       ];
  2  [label="two"       ];
  3  [label="three"     ];
  4  [label="four"      ];
  5  [label="five"      ];
  6  [label="six"       ];
  7  [label="seven"     ];
  8  [label="eight"     ];
  9  [label="nine"      ];
  10 [label="ten"       ];
  11 [label="eleven"    ];
  12 [label="twelve"    ];
  13 [label="thirteen"  ];
  14 [label="fourteen"  ];
  15 [label="fivteen"   ];
  16 [label="sixteen"   ];
  17 [label="seventeen" ];
  18 [label="eighteen"  ];
  19 [label="nineteen"  ];
  20 [label="twenty"    ];
  21 [label="twenty-one"];
  22 [label="twenty-two"];

  0  -> 1  [arrowhead=none];
  1  -> 2  [arrowhead=none];
  2  -> 7  [arrowhead=none];
  7  -> 8  [arrowhead=none];
  8  -> 9  [arrowhead=none];
  8  -> 10 [arrowhead=none];
  9  -> 10 [color="#aaaaaa" constraint=false];
  10 -> 11 [arrowhead=none];
  10 -> 12 [arrowhead=none];
  11 -> 12 [color="#aaaaaa" constraint=false];
  7  -> 13 [arrowhead=none];
  8  -> 13 [color="#aaaaaa" constraint=false];
  13 -> 14 [arrowhead=none];
  7  -> 15 [arrowhead=none];
  13 -> 15 [color="#aaaaaa" constraint=false];
  15 -> 16 [arrowhead=none];
  15 -> 17 [arrowhead=none];
  16 -> 17 [color="#aaaaaa" constraint=false];
  2  -> 3  [arrowhead=none];
  7  -> 3  [color="#aaaaaa" constraint=false];
  3  -> 4  [arrowhead=none];
  2  -> 5  [arrowhead=none];
  3  -> 5  [color="#aaaaaa" constraint=false];
  5  -> 6  [arrowhead=none];
  2  -> 18 [arrowhead=none];
  5  -> 18 [color="#aaaaaa" constraint=false];
  18 -> 19 [arrowhead=none];
  19 -> 20 [arrowhead=none];
  19 -> 21 [arrowhead=none];
  20 -> 21 [color="#aaaaaa" constraint=false];
  18 -> 22 [arrowhead=none];
  19 -> 22 [color="#aaaaaa" constraint=false];
}

results in

Resulting graph

Note, the ordering between siblings is indicated by the grey edges (arrows).

So, for example, I am happy with the seven -> three -> five -> eighteen siblings, since they are drawn from left to right in their correct order (as indicated by the arrows).

But I am unhappy with the siblings eight -> thirteen -> fivteen because their edges cross other edges and because their ordering is not from left to right, as I'd like.

Also, nine -> ten, twenty -> twenty-one and nineteen -> twenty-two are in the wrong direction.

I am aware that I could probably get to a picture as I want if I used additional (invisible) edges and the weight attribute and possibly even more features. But as the graphs (and there are many of those) are generated by a script, I can't do that manually.

So, is there a way to achieve what I want?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

凹づ凸ル 2025-01-12 02:46:10

在这种情况下,它实际上非常简单:脚本中节点的出现顺序确实很重要。在您的脚本中,它们出现在从节点 0 到节点 22 的位置,并且布局尽可能尊重这一点。但是,它们应该按照您添加边的顺序出现(0,1,2,7,3,5,18,...)。因此,最简单的解决方案是将定义标签的块移到定义边缘的块之后,您将得到:

ordered graph

没有权重,没有不可见的边,也没有不可见的节点。

In this case it's actually very simple: The order of appearance of the nodes in the script does matter. In your script they appear from node 0 to node 22 and are layed out to respect this as much as possible. However, they should appear in the order you added the edges (0,1,2,7,3,5,18, ...). Therefore the simplest solution is to move the block which defines the labels after the block which defines the edges, and you'll get:

ordered graph

No weights, no invisible edges and no invisible nodes.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文