igraph在Ncol()格式导入边列表后如何填充节点属性?
我不太确定这是合并操作,还是两个独立的导入,或者我应该完全重新考虑这个问题。我最开始使用igraph是因为在gephi里玩的时候,我总是采用两步导入,先导入边,然后再导入节点数据。这样的方法在igraph里合适吗?
所以,多亏了最近的一些帮助,我刚刚导入了一个边列表,内容大概是这样的:
123123 321321 1
222222 333333 2
123123 333333 3
222222 321321 4
...使用的导入命令是
import igraph
g = igraph.Graph.Read_Ncol('edgelist.txt')
我想给这个边列表生成的节点添加一些属性。这些属性大概是这样的...
123123 "color:red" "community:1"
222222 "color:blue" "community:2"
321321 "color:red" "community:1"
333333 "color:red" "community:2"
我该如何把这些数据添加到我当前的图里呢?我看到有很多复杂的边列表导入格式,但没有节点列表的格式。我是不是漏掉了什么?难道没有自动把节点数据添加到相应节点的功能吗?
如果没有,能不能推荐一种更简单的方法,把节点数据填充到现有的图里?
我本能地想到了类似这样的方式...
[g.vs["color"] = x for x in node_list.color if g.vs["name"] == node_list.name]
[g.vs["community"] = x for x in node_list.community if g.vs["name"] == node_list.name]
但这看起来实在是太麻烦了。
1 个回答
你走在正确的道路上,不过这确实会有点麻烦。之所以麻烦,是因为igraph的底层是用C语言写的,而在C语言中,处理数字(比如顶点和边的ID)要比处理名字(比如顶点和边的名称)简单得多。所以,igraph用从零开始的整数来表示顶点和边,而不是用它们的名字。这就是为什么你需要多做一步,才能从名字找到对应的顶点。
我可能会这样做:
- 使用
Graph.Read_Ncol
来读取边列表。(你已经做过了)。 建立一个字典,把顶点名字和它们的ID对应起来:
>>> id_mapping = dict((v, k) for k, v in g.vs["name"])
把你的属性文件读入
node_list
。我假设node_list.name
会给我一个顶点名字的列表,而node_list.color
会给我一个对应颜色的列表。然后你可以这样做:>>> for name, color in izip(node_list.name, node_list.color): ... g.vs[id_mapping[name]]["color"] = color
在第三步中,还有一种替代的方法是使用 g.vs.find(name)
,这会给你一个 Vertex
对象,指向具有给定名字的顶点。然后你可以把属性分配给这个顶点;例如:
>>> for name, color in izip(node_list.name, node_list.color):
... g.vs.find(name)["color"] = color
在这种情况下,你就不需要 id_mapping
了。实际上,igraph在后台维护了一个名字到ID的映射,专门用于 name
这个顶点属性,而 g.vs.find
就是利用了这个映射。如果你想用其他顶点属性作为唯一标识,而不是 name
,那么基于 id_mapping
的方法会更有用。