如何向networkx中的边添加新属性?

问题描述 投票:0回答:6

我有:在networkx中导入的图G,其节点和边由gml文件加载。

问题:如何向选定的边E添加新属性。

我想要做什么:我想为图表的特定边 E 添加一个新属性“类型”。注意:该边 E 不存在属性“type”。

我的代码是:

  G.edge[id_source][id_target]['type']= value

但是如果我打印G的所有边,现在我有n+1条边; G 的所有旧边和新边 p= (id_source, id_target, {'type'= value})。此外,旧边 E(我要修改的边)没有新属性“类型”。

所以我的代码添加了一个新的边缘(我不想要)。

我想更新旧属性,添加一个不存在的新属性。

python graph attributes networkx
6个回答
31
投票

您可能有一个networkx MultiGraph而不是图,在这种情况下,边的属性设置有点棘手。 (您可以通过加载节点之间具有多个边的图来获得多重图)。您可能会通过分配属性来破坏数据结构

G.edge[id_source][id_target]['type']= value
当你需要的时候
G.edge[id_source][id_target][key]['type']= value

以下示例说明了它对于图和多重图的工作方式有何不同。

对于图形案例属性的工作方式如下:

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'})]

3
投票

我不太明白为什么你只想向一条边添加属性,相反,你可以向所有边添加属性,然后将

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


1
投票

李新峰的以下答案有效,只需注意

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']

1
投票

从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)

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, {})

0
投票

nx.set_edge_attributes( G, { (id_源,id_目标):{ '类型1':值1, '类型2':值2, '类型3':值3, } }, )

© www.soinside.com 2019 - 2024. All rights reserved.