我有什么:在gx文件加载的networkx whit节点和egdes中导入的图表G.
问题:如何将新属性添加到选定边缘。
我想做什么:我想为图表的特定边E添加新属性'type'。注意:此边E不存在属性“type”。
我在互联网和这里阅读了很多解决方案,但这些解决方案中没有一个解决了我的问题。 实际上我的代码是:
G.edge[id_source][id_target]['type']= value
但是如果我打印G的所有边缘,现在我有n + 1条边,G的所有旧边和新边p =(id_source,id_target,{'type'= value})。此外,旧边E(我想要修改的边)没有新属性'type'。
所以我的代码添加了一个新的边缘(我不想要) 我想要更新旧版本添加不存在的新属性。
感谢您的帮助!
编辑:已解决 感谢Aric和一些技巧,我解决了我的问题:
def add_attribute_to_edge(H,id_node_source,id_node_target,new_attr,value_attr):
keydict =H[id_node_source][id_node_target]
key=len(keydict)
for k in keydict:
if 'type' not in H.edge[id_source][id_target][k]:
H.add_edge(id_node_source,id_node_target,key=k, new_attr= value_attr)
答案 0 :(得分:10)
你可能有一个networkx MultiGraph而不是图形,在这种情况下,边缘的属性设置有点小问题。 (您可以通过加载节点之间具有多个边缘的图形来获取多图形)。您可能通过分配属性来破坏数据结构
您需要时G.edge[id_source][id_target]['type']= value
G.edge[id_source][id_target][key]['type']= value
。
以下是Graphs和MultiGraphs的不同工作方式示例。
对于Graph案例属性,可以这样工作:
In [1]: import networkx as nx
In [2]: G = nx.Graph()
In [3]: G.add_edge(1,2,color='red')
In [4]: G.edges(data=True)
Out[4]: [(1, 2, {'color': 'red'})]
In [5]: G.add_edge(1,2,color='blue')
In [6]: G.edges(data=True)
Out[6]: [(1, 2, {'color': 'blue'})]
In [7]: G[1][2]
Out[7]: {'color': 'blue'}
In [8]: G[1][2]['color']='green'
In [9]: G.edges(data=True)
Out[9]: [(1, 2, {'color': 'green'})]
使用MultiGraphs,还有一个额外级别的键可以跟踪平行边缘,因此它的工作方式略有不同。如果您没有明确设置密钥,MultiGraph.add_edge()将添加一个带有内部选择键的新边(顺序整数)。
In [1]: import networkx as nx
In [2]: G = nx.MultiGraph()
In [3]: G.add_edge(1,2,color='red')
In [4]: G.edges(data=True)
Out[4]: [(1, 2, {'color': 'red'})]
In [5]: G.add_edge(1,2,color='blue')
In [6]: G.edges(data=True)
Out[6]: [(1, 2, {'color': 'red'}), (1, 2, {'color': 'blue'})]
In [7]: G.edges(data=True,keys=True)
Out[7]: [(1, 2, 0, {'color': 'red'}), (1, 2, 1, {'color': 'blue'})]
In [8]: G.add_edge(1,2,key=0,color='blue')
In [9]: G.edges(data=True,keys=True)
Out[9]: [(1, 2, 0, {'color': 'blue'}), (1, 2, 1, {'color': 'blue'})]
In [10]: G[1][2]
Out[10]: {0: {'color': 'blue'}, 1: {'color': 'blue'}}
In [11]: G[1][2][0]['color']='green'
In [12]: G.edges(data=True,keys=True)
Out[12]: [(1, 2, 0, {'color': 'green'}), (1, 2, 1, {'color': 'blue'})]
答案 1 :(得分:1)
我不太清楚你为什么只想在一条边上添加一个属性,而是可以在所有边上添加一个属性,然后将the wanted value
赋予你的特定边缘。
Networkx有一个名为set_edge_attributes
的方法可以为所有边添加边属性,例如
G = nx.path_graph(3)
bb = nx.edge_betweenness_centrality(G, normalized=False)
nx.set_edge_attributes(G, 'betweenness', bb)
G[1][2]['betweenness']
输出:2.0
答案 2 :(得分:0)
实际上,有一种更好的简短方法可以将新属性添加到图表中的现有边缘:
>>> for itr in G.edges_iter(None, True, True):
itr
(0, 1, {})
(0, 2, {'edge': (0, 2)})
(0, 3, {})
(0, 4, {})
(1, 2, {})
(1, 3, {})
(2, 3, {})
(2, 4, {})
(3, 4, {})
>>> G[0][1].update(edge=(0,1)) #This will add 'edge'=(0,1) dict item to edge(0,1)
>>> for itr in G.edges_iter(None, True, True):
itr
(0, 1, {'edge': (0, 1)})
(0, 2, {'edge': (0, 2)})
(0, 3, {})
(0, 4, {})
(1, 2, {})
(1, 3, {})
(2, 3, {})
(2, 4, {})
(3, 4, {})
答案 3 :(得分:0)
下面李新峰的答案起作用了,只是注意values
和name
的参数在Networkx v1.x(最初编写答案时)和Networkx v2.x之间切换。对于v2.x,代码为:
G = nx.path_graph(3)
bb = nx.edge_betweenness_centrality(G, normalized=False)
nx.set_edge_attributes(G, bb, 'betweenness')
G[1][2]['betweenness']
答案 4 :(得分:0)
从OP的问题中添加的解决方案:
感谢Aric和一些技巧,我解决了我的问题:
def add_attribute_to_edge(H,id_node_source,id_node_target,new_attr,value_attr): keydict =H[id_node_source][id_node_target] key=len(keydict) for k in keydict: if 'type' not in H.edge[id_source][id_target][k]: H.add_edge(id_node_source,id_node_target,key=k, new_attr= value_attr)