[英]How to transform directed graph to undirected graph while recording information about attributes using NetworkX?
我是NetworkX的新手,我认为有一个问题可能很笼统:如何获取定向网络,如何将其转换为非定向网络,并在此过程中记录有关原始定向网络中边缘的一些信息?
具体来说,我在NetworkX中有一个DiGraph,它记录了从id_from到id_to的链接。 每个边的属性是链接的月份和权重。
我想将此有向图转换为我记录为属性的无向图:
这是我开始的熊猫数据框示例:
In [12]: df
Out[12]:
id_from id_to total month
0 a b 100.0 2014-01-01
1 b a 10.0 2014-02-01
2 a c 15.0 2014-01-01
3 c d 7.0 2015-06-01
4 d c 500.0 2016-03-01
我将其作为DiGraph阅读:
In [13]: G = nx.from_pandas_dataframe(df, 'id_from', 'id_to', edge_attr = True, create_using = nx.DiGraph())
In [14]: print(G.edges(data = True))
Out[14]: [(a, b, {'id_from': a, 'id_to': b, 'amount': 100.0, 'month': Timestamp('2014-01-01 00:00:00')}), (b, a, {'id_from': b, 'id_to': a, 'amount': 10.0, 'month': Timestamp('2014-02-01 00:00:00')}), (a, c, {'id_from': a, 'id_to': c, 'amount': 15.0, 'month': Timestamp('2014-01-01 00:00:00')}), (c, d, {'id_from': c, 'id_to': d, 'amount': 7.0, 'month': Timestamp('2015-06-01 00:00:00')}), (d, c, {'id_from': d, 'id_to': c, 'amount': 500.0, 'month': Timestamp('2016-03-01 00:00:00')})]
然后,我最终希望获得一个图形,然后可以将其转换为熊猫数据框,如下所示:
id_one id_two total first_month last_month nr_months bidirect
0 a b 110.0 2014-01-01 2014-02-01 2.0 Yes
1 a c 15.0 2014-02-01 2014-02-01 1.0 No
2 c d 507.0 2015-06-01 2016-03-01 2.0 Yes
谁能帮我这个?
我似乎找不到类似的问题,但是如果我错了,请纠正我。 任何帮助深表感谢。
一种可能的方法是使用G.to_undirected()
将有向图转换为无向图。 然后遍历边缘以更新每个边缘的所需属性,最后将图形转换为数据框:
import pandas as pd
import networkx as nx
import datetime
data = {
'id_from': ['a', 'b', 'a', 'c', 'd'],
'id_to': ['b', 'a', 'c', 'd', 'c'],
'total': [100.0, 10.0, 15.0, 7.0, 500.0],
'month': [datetime.datetime(2014, 1, 1), datetime.datetime(2014, 2, 1), datetime.datetime(2014, 1, 1), datetime.datetime(2015, 6, 1), datetime.datetime(2016, 3, 1)],
}
df = pd.DataFrame(data)
G = nx.from_pandas_edgelist(df, 'id_from', 'id_to', edge_attr=True, create_using=nx.DiGraph())
undirected = G.to_undirected()
for edge in undirected.edges(data=True):
direction_1 = df.ix[(df['id_from'] == edge[0]) & (df['id_to'] == edge[1])]
direction_2 = df.ix[(df['id_from'] == edge[1]) & (df['id_to'] == edge[0])]
edges = pd.concat([direction_1, direction_2])
edge[2]['bidirect'] = 'Yes' if (not direction_1.empty) & (not direction_2.empty) else 'No'
edge[2]['total'] = edges['total'].sum()
edge[2]['first_month'] = edges['month'].min()
edge[2]['last_month'] = edges['month'].max()
edge[2]['nr_months'] = edges['month'].nunique()
del edge[2]['month']
print(nx.to_pandas_edgelist(undirected))
结果是:
bidirect first_month last_month nr_months source target total
0 No 2014-01-01 2014-01-01 1 a c 15.0
1 Yes 2014-01-01 2014-02-01 2 a b 110.0
2 Yes 2015-06-01 2016-03-01 2 c d 507.0
networkx图中的每个边缘本质上都是一个元组,其中前2个元素是边缘的节点,最后一个元素(edge [2])是具有边缘属性的字典。 因此,我们可以根据所需逻辑简单地更新此字典。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.