在熊猫数据框中按具有半冒号分隔值的列分组

时间:2018-09-11 11:24:09

标签: python pandas pandas-groupby

想象一个由{p>给定的pandas数据帧

import pandas as pd

df = pd.DataFrame({
    'id': range(5),
    'vmns': ('nan', 'a', 'a;b', 'c', 'b')
})

给出下表

   id vmns
0   0  nan
1   1    a
2   2  a;b
3   3    c
4   4    b

现在,我希望按vmns列进行分组,但请注意vmns的{​​{1}}的半冒号分隔值。应该将其解释为id = 2a,以便在这些值之间创建链接。因此,结果表应该看起来像这样

b

有什么建议吗?

1 个答案:

答案 0 :(得分:0)

我继续使用networkx创建了一个解决方案。如下(扩展示例)

import networkx as nx
import pandas as pd

df = pd.DataFrame({
    'id': range(7),
    'vmns': ('nan', 'a', 'a;b;c', 'c', 'b', 'd;e', 'e')
})

产生

   id   vmns
0   0    nan
1   1      a
2   2  a;b;c
3   3      c
4   4      b
5   5    d;e
6   6      e

然后,我从没有分号的行中创建节点,并从带有分号的行中创建边缘。带有nan的行将被忽略。

# determine which rows contains nodes and which contains edges
edges_mask = df['vmns'].str.contains(';')
nodes_mask = ~df['vmns'].str.contains(';') & (df['vmns'] != 'nan')

def create_pairwise_edges(lst):
    return [(lst[0], value) for value in lst[1:]]

# create the graph with nodes and edges
G = nx.Graph()
G.add_nodes_from(df.loc[nodes_mask, 'vmns'])
G.add_edges_from([st for row in df.loc[edges_mask, 'vmns'].str.split(';').map(create_pairwise_edges) for st in row])

# determine the connected components and write to df
Gcc = nx.connected_components(G)
new_map = dict()
for g, ids in enumerate(Gcc):
    for id in ids:
        new_map[id] = g
new_map['nan'] = 'nan'
df['combined_group'] = df['vmns'].str.split(';').map(lambda x: new_map[x[0]])

结果是

   id   vmns combined_group
0   0    nan            nan
1   1      a              0
2   2  a;b;c              0
3   3      c              0
4   4      b              0
5   5    d;e              1
6   6      e              1
相关问题