Pandas数据帧合并和元素级乘法

1 投票
2 回答
3188 浏览
提问于 2025-04-18 15:32

我有一个数据表,长这样:

df1 = pd.DataFrame({'name':['al', 'ben', 'cary'], 'bin':[1.0, 1.0, 3.0], 'score':[40, 75, 15]})

    bin     name    score
0   1   al  40
1   1   ben     75
2   3   cary    15

还有一个数据表,长这样:

df2 = pd.DataFrame({'bin':[1.0, 2.0, 3.0, 4.0, 5.0], 'x':[1, 1, 0, 0, 0], 
                    'y':[0, 0, 1, 1, 0], 'z':[0, 0, 0, 1, 0]})

    bin     x   y   z
0   1   1   0   0
1   2   1   0   0
2   3   0   1   0
3   4   0   1   1
4   5   0   0   0

我想做的是把第一个数据表(df1)扩展,增加‘x’,‘y’,和‘z’这几列,并且只在‘bin’匹配的情况下,当对应的‘x’,‘y’,‘z’的值是1而不是0时,填入分数。

我已经做到这一步:

df3 = pd.merge(df1, df2, how='left', on=['bin'])
    bin     name    score   x   y   z
0   1   al  40  1   0   0
1   1   ben     75  1   0   0
2   3   cary    15  0   1   0

但是我找不到一个简单的方法把分数填到正确的‘x’,‘y’等列里(我实际的问题有一百多列这样的,所以用 df3['x'] = df3['score'] * df3['x'] 可能会比较慢)。

2 个回答

1

这可能没有比逐个遍历快多少,但这是一个想法。

先导入numpy,然后定义在操作中涉及的列。

import numpy as np
columns = ['x','y','z']
score_col = 'score'

构建一个numpy数组,内容是分数列,并调整形状以匹配操作中列的数量。

score_matrix = np.repeat(df3[score_col].values, len(columns))
score_matrix = score_matrix.reshape(len(df3), len(columns))

然后用这些列进行相乘,并把结果重新赋值回数据框中。

df3[columns] = score_matrix * df3[columns]
2

你只需要先列出你想要用来乘分数的那些列,然后就可以使用 apply 这个函数了:

cols = [each for each in df2.columns if each not in ('name', 'bin')]
df3 = pd.merge(df1, df2, how='left', on=['bin'])
df3[cols] = df3.apply(lambda x: x['score'] * x[cols], axis=1)

撰写回答