在Gephi中打开之前,在Networkx write_graphml中添加属性

2024-05-15 23:30:49 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个由可能的网络连接组成的数据帧,格式为df = pd.DataFrame(["A", "B", "Count", "some_attribute"])。此数据帧表示如下连接:

  • A和B有联系
  • 此连接发生了“Count”次
  • 此连接具有特定属性(即特定类型的联系人)

我想将这个数据帧导出为graphml格式。使用以下代码可以正常工作:

import networkx as nx
G = nx.Graph()
G.add_weighted_edges_from(df[["A", "B", "Count"]].values)
nx.write_graphml(G, "my_graph.graphml")

这段代码生成一个带有正确图形的graphml文件,我可以将其用于Gephi。现在我要添加一个属性:

^{pr2}$

每当我试图在这段代码中添加属性时,就不可能将其写入graphml文件。使用此代码,我得到以下错误消息:

NetworkXError: GraphML writer does not support <class 'numpy.ndarray'> as data values.

我找到了相关的文章(比如thisone),但是它没有提供任何解决这个问题的方法。有没有人有一个使用networkx向graphml文件添加属性的解决方案,以便我可以在Gephi中使用它们?在


Tags: 文件数据代码networkxdf属性as格式
1条回答
网友
1楼 · 发布于 2024-05-15 23:30:49

假设随机数据帧:

import pandas as pd
df = pd.DataFrame({'A': [0,1,2,0,0],
                   'B': [1,2,3,2,3],
                   'Count': [1,2,5,1,1],
                   'some_attribute': ['red','blue','red','blue','red']})

    A   B   Count  some_attribute
0   0   1   1   red
1   1   2   2   blue
2   2   3   5   red
3   0   2   1   blue
4   0   3   1   red

按照上面的代码实例化Graph

^{pr2}$

检查一条边时,numpy数组df['some_attribute'].values被指定为每个边的一个属性:

print (G.edge[0][1])
print (G.edge[2][3])
{'attr': array(['red', 'blue', 'red', 'blue', 'red'], dtype=object), 'weight': 1}
{'attr': array(['red', 'blue', 'red', 'blue', 'red'], dtype=object), 'weight': 5}

如果我正确理解您的意图,我假设您希望每个边的属性对应于df['some_attribute']列。在

您可能会发现使用^{}创建Graph更加容易,尤其是因为您已经在DataFrame对象中格式化了数据。在

G = nx.from_pandas_dataframe(df, 'A', 'B', ['Count', 'some_attribute'])

print (G.edge[0][1])
print (G.edge[2][3])
{'Count': 1, 'some_attribute': 'red'}
{'Count': 5, 'some_attribute': 'red'}

写入文件没有问题:

nx.write_graphml(G,"my_graph.graphml")

但是,我不是一个普通的Gephi用户,所以可能有另一种方法来解决以下问题。当我用'Count'作为边属性加载文件时,Gephi图默认情况下不识别边权重。因此,我将列名从'Count'更改为'weight',并在加载到Gephi时看到以下内容:

df.columns=['A', 'B', 'weight', 'some_attribute']
G = nx.from_pandas_dataframe(df, 'A', 'B', ['weight', 'some_attribute'])
nx.write_graphml(G,"my_graph.graphml")

enter image description here

希望这有帮助,我能正确理解你的问题。在

编辑

根据Corley上面的评论,如果您选择使用add_edges_from,那么可以使用以下内容。在

G.add_edges_from([(u,v,{'weight': w, 'attr': a}) for u,v,w,a in df[['A', 'B', 'Count', 'some_attribute']].values ])

虽然没有显著的性能提升,但是我发现from_pandas_dataframe更具可读性。在

import numpy as np

df = pd.DataFrame({'A': np.arange(0,1000000),
                   'B': np.arange(1,1000001),
                   'Count': np.random.choice(range(10), 1000000, replace=True),
                   'some_attribute': np.random.choice(['red','blue'], 1000000, replace=True,)})

%%timeit
G = nx.Graph()
G.add_edges_from([(u,v,{'weight': w, 'attr': a}) for u,v,w,a in df[['A', 'B', 'Count', 'some_attribute']].values ])

1 loop, best of 3: 4.23 s per loop

%%timeit
G = nx.Graph()
G = nx.from_pandas_dataframe(df, 'A', 'B', ['Count', 'some_attribute'])

1 loop, best of 3: 3.93 s per loop

相关问题 更多 >