我有一个名为egypt的软件生成的点文件。点文件包含许多节点和边。如果我用这个点文件画图,由于节点太多,很难看清图片。而我需要的只是从一个节点开始的子图,不需要全图。
有没有办法使用这个点文件从指定节点(例如start_node)绘制子图?
(由于@varetchen和@shijunzhao的评论和链接)
gvpr
程序提取子图GraphViz包支持称为gvpr的图形模式匹配和处理语言。它有点像 AWK,因为程序以成对的模式、指令块为中心,具有 BEGIN 和 END 模式 - 区别在于 gvpr 匹配图形节点和边,而不是文本行。
一个昵称“blabber”的好家伙已经实现了一个 gvpr 程序来匹配、打印、归零并将其发布到网上 - 这就是我们将使用的:
gvpr
;否则,使用 gvpr
设置适当的 Graphviz 分布。reduce.g
.gvpr -f reduce.g -a '"foo" NNN' full_graph.dot > rooted_at_foo.dot
其中 "foo"
是您感兴趣的根节点的名称(不是标签),NNN
是从 foo
开始的子树的最大深度。reduce.g
:
BEGIN{
if (ARGC != 2) {
print("This script takes exactly two parameter. 1: name of node, 2: number of hops");
exit(1);
}
void reduce_in(graph_t _g, node_t _n, edge_t _e, int _d){
_e = fstin(_n);
while (_e != NULL) {
clone(_g, _e);
if (_d < atoi(ARGV[1])) {
reduce_in(_g, _e.tail, NULL, _d + 1);
}
_e = nxtin(_e);
}
}
void reduce_out(graph_t _g, node_t _n, edge_t _e, int _d){
_e = fstout(_n);
while (_e != NULL) {
clone(_g, _e);
if (_d < atoi(ARGV[1])) {
reduce_out(_g, _e.head, NULL, _d + 1);
}
_e = nxtout(_e);
}
}
}
BEG_G {
graph_t g = graph("G", "S");
g.rankdir = "RL";
}
N [name==ARGV[0]] {
node_t n = clone(g, $);
n.color="red";
reduce_in(g, $, NULL, 1);
reduce_out(g, $, NULL, 1);
}
END_G {
$O = g;
}