【问题标题】:pandas dataframe to adjacency matrix熊猫数据框到邻接矩阵
【发布时间】:2018-03-22 13:10:29
【问题描述】:

我有一个如下形式的 pandas 数据框:

index | id    | group
0     | abc   | A
1     | abc   | B
2     | abc   | B
3     | abc   | C
4     | def   | A
5     | def   | B
6     | ghi   | B
7     | ghi   | C

我想将其转换为加权图/邻接矩阵,其中节点是“组”,权重是每个组对的共享 ID 的总和:

权重是每个 id 的组对组合的计数,所以:

AB = 'abc' indexes (0,1),(0,2) + 'def' indexes (4,5) = 3

AC = 'abc' (0,3) = 1

BC = 'abc' (2,3), (1,3) + 'ghi' (6,7) = 3

得到的矩阵是:

    A  |B  |C
A| 0   |3  |1
B| 3   |0  |3
C| 1   |3  |0

目前我这样做的效率很低:

f = df.groupby(['id']).agg({'group':pd.Series.nunique}) # to count groups per id
f.loc[f['group']>1] # to get a list of the ids with >1 group

# i then for loop through the id's getting the count of values per pair (takes a long time). 

这是第一次通过粗略的黑客方法,我确信必须有使用 groupby 或 crosstab 的替代方法,但我无法弄清楚。

【问题讨论】:

  • 正确:已编辑

标签: python pandas dataframe matrix data-structures


【解决方案1】:

您可以使用以下内容:

df_merge = df.merge(df, on='id')
results = pd.crosstab(df_merge.group_x, df_merge.group_y)
np.fill_diagonal(results.values, 0)
results

输出:

group_y  A  B  C
group_x         
A        0  3  1
B        3  0  3
C        1  3  0

注意:您的结果与我的结果 C-B 和 B-C 三个而不是两个的差异是由于 B-abc 索引第 1 行和第 2 行的重复记录。

【讨论】:

  • 不错!我知道交叉表是要走的路,但无法弄清楚。
【解决方案2】:

不妨试试dot

s=pd.crosstab(df.id,df.group)
s=s.T.dot(s)
s.values[[np.arange(len(s))]*2] = 0
s
Out[15]: 
group  A  B  C
group         
A      0  3  1
B      3  0  3
C      1  3  0

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-05-10
    • 1970-01-01
    • 2017-04-11
    • 2021-10-02
    • 1970-01-01
    • 2020-12-15
    相关资源
    最近更新 更多