熊猫-自上次交易以来算

时间:2018-09-25 09:37:32

标签: python pandas dataframe

我有一个包含货币交易记录的数据框(称为txn_df),这是此问题中的重要列:

txn_year    txn_month   custid  withdraw    deposit
2011        4           123     0.0         100.0
2011        5           123     0.0         0.0
2011        6           123     0.0         0.0
2011        7           123     50.1        0.0
2011        8           123     0.0         0.0

还假设我们在这里有多个客户。 withdrawdeposit的0.0值都表示未发生任何事务。我要做的是产生一个新列,该列指示自交易以来已发生了多少个月。与此类似:

txn_year    txn_month   custid  withdraw    deposit     num_months_since_last_txn
2011        4           123     0.0         100.0       0
2011        5           123     0.0         0.0         1
2011        6           123     0.0         0.0         2           
2011        7           123     50.1        0.0         3
2011        8           123     0.0         0.0         1

到目前为止,我能想到的唯一解决方案是在has_txn和{{1}中的任何一个时产生一个新列withdraw(1/0或True / False) }的值> 0.0,但我无法从那里继续。

1 个答案:

答案 0 :(得分:4)

解决此问题的一种方法,

df['series'] =  df[['withdraw','deposit']].ne(0).sum(axis=1)
m = df['series']>=1

@Chris A评论,

m = df[['withdraw','deposit']].gt(0).any(axis=1) #replacement for above snippet,

df['num_months_since_last_txn'] = df.groupby(m.cumsum()).cumcount()
df.loc[df['num_months_since_last_txn']==0,'num_months_since_last_txn']=(df['num_months_since_last_txn']+1).shift(1).fillna(0)
print df

输出:

   txn_year  txn_month  custid  withdraw  deposit
0      2011          4     123       0.0    100.0
1      2011          5     123       0.0      0.0
2      2011          6     123       0.0      0.0
3      2011          7     123      50.1      0.0
4      2011          8     123       0.0      0.0
   txn_year  txn_month  custid  withdraw  deposit  num_months_since_last_txn
0      2011          4     123       0.0    100.0                        0.0
1      2011          5     123       0.0      0.0                        1.0
2      2011          6     123       0.0      0.0                        2.0
3      2011          7     123      50.1      0.0                        3.0
4      2011          8     123       0.0      0.0                        1.0

说明:

  1. 要获取交易发生与否,请使用ne并求和以获取二进制值。
  2. 当交易为1时,使用groupbycumsumcumcount从0,1,2 ... n创建序列。
  3. 使用0重新排列.loc的值

注意:可能是我添加了更复杂的方法来解决此问题。但这会为您提供解决此问题的想法和方法。

考虑客户ID的解决方案

df=df.sort_values(by=['custid','txn_month'])
mask=~df.duplicated(subset=['custid'],keep='first')
m = df[['withdraw','deposit']].gt(0).any(axis=1)
df['num_months_since_last_txn'] = df.groupby(m.cumsum()).cumcount()
df.loc[df['num_months_since_last_txn']==0,'num_months_since_last_txn']=(df['num_months_since_last_txn']+1).shift(1)
df.loc[mask,'num_months_since_last_txn']=0

样本输入:

   txn_year  txn_month  custid  withdraw  deposit
0      2011          4     123       0.0    100.0
1      2011          5     123       0.0      0.0
2      2011          4    1245       0.0    100.0
3      2011          5    1245       0.0      0.0
4      2011          6     123       0.0      0.0
5      2011          7    1245      50.1      0.0
6      2011          7     123      50.1      0.0
7      2011          8     123       0.0      0.0
8      2011          6    1245       0.0      0.0
9      2011          8    1245       0.0      0.0

样本输出:

   txn_year  txn_month  custid  withdraw  deposit  num_months_since_last_txn
0      2011          4     123       0.0    100.0                        0.0
1      2011          5     123       0.0      0.0                        1.0
4      2011          6     123       0.0      0.0                        2.0
6      2011          7     123      50.1      0.0                        3.0
7      2011          8     123       0.0      0.0                        1.0
2      2011          4    1245       0.0    100.0                        0.0
3      2011          5    1245       0.0      0.0                        1.0
8      2011          6    1245       0.0      0.0                        2.0
5      2011          7    1245      50.1      0.0                        3.0
9      2011          8    1245       0.0      0.0                        1.0

考虑客户ID的说明

  1. 以上代码基于[1,1]之间的间隔工作。因此,要使格式相同,请按cust_id和txn_month对df进行排序,将来可以添加txn_year。
  2. fillna(0),在这里不起作用,因为shift不会为下一个客户创建NaN。要将其重置为0,请查找客户ID的重复项,然后将第一个值替换为0。