我有一个如下所示的pd.dataframe:
key_value a b c d e
value_01 1 10 x NaN NaN
value_01 NaN 12 NaN NaN NaN
value_01 NaN 7 NaN NaN NaN
value_02 7 4 y NaN NaN
value_02 NaN 5 NaN NaN NaN
value_02 NaN 6 NaN NaN NaN
value_03 19 15 z NaN NaN
所以现在基于key_value,
对于列“ a”和“ c”,我想根据key_value从同一列“ a”和“ c”中复制最后一个单元格的值。
对于另一列“ d”,我想将行“ i-1”的单元格值从列“ b”复制到第d列“ d”。
最后,对于列'e',我想将'i-1'单元格的总和从列'b'复制到列'e'第i个单元格。
对于每个key_value ,列“ a”,“ b”和“ c”在第一行中都有一些值,基于这些值,下一个值将被复制到该值上或针对不同的列复制该值正在为其生成。
key_value a b c d e
value_01 1 10 x NaN NaN
value_01 1 12 x 10 10
value_01 1 7 x 12 22
value_02 7 4 y NaN NaN
value_02 7 5 y 4 4
value_02 7 6 y 5 9
value_03 8 15 z NaN NaN
我目前的做法:
size = df.key_value.size
for i in range(size):
if pd.isna(df.a[i]) and df.key_value[i] == output.key_value[i - 1]:
df.a[i] = df.a[i - 1]
df.c[i] = df.c[i - 1]
df.d[i] = df.b[i - 1]
df.e[i] = df.e[i] + df.b[i - 1]
对于像“ a”和“ b”这样的列, NaN 值都在同一行索引中。
我的方法可行,但是由于我的daframe具有超过50000条记录,所以花费了很长时间,我想知道是否还有其他方法可以这样做,因为我有多个列,例如'a'和'b',需要复制值基于'key_value'和一些使用诸如'b'之类的列来计算值的列
答案 0 :(得分:3)
pd.concat
与groupby
和assign
pd.concat([
g.ffill().assign(d=lambda d: d.b.shift(), e=lambda d: d.d.cumsum())
for _, g in df.groupby('key_value')
])
key_value a b c d e
0 value_01 1.0 1 x NaN NaN
1 value_01 1.0 2 x 1.0 1.0
2 value_01 1.0 3 x 2.0 3.0
3 value_02 7.0 4 y NaN NaN
4 value_02 7.0 5 y 4.0 4.0
5 value_02 7.0 6 y 5.0 9.0
6 value_03 19.0 7 z NaN NaN
groupby
和apply
def h(g):
return g.ffill().assign(
d=lambda d: d.b.shift(), e=lambda d: d.d.cumsum())
df.groupby('key_value', as_index=False, group_keys=False).apply(h)
答案 1 :(得分:2)
您可以使用groupby
+ ffill
进行分组填充。其他操作需要shift
和cumsum
。
通常,请注意,在熊猫中已有效实施了许多常见操作。
g = df.groupby('key_value')
df['a'] = g['a'].ffill()
df['c'] = g['c'].ffill()
df['d'] = df['b'].shift()
df['e'] = df['d'].cumsum()
print(df)
key_value a b c d e
0 value_01 1.0 1 x NaN NaN
1 value_01 1.0 2 x 1.0 1.0
2 value_01 1.0 3 x 2.0 3.0
3 value_02 7.0 4 y 3.0 6.0
4 value_02 7.0 5 y 4.0 10.0
5 value_02 7.0 6 y 5.0 15.0
6 value_03 19.0 7 z 6.0 21.0