【问题标题】:summing all amounts by date in respect with individuals按日期合计与个人有关的所有金额
【发布时间】:2019-03-11 18:45:49
【问题描述】:

我有这个数据框

df:
     payout  person1 person2      date    
1    300.0     LA       NaN     2012-02-01  
2    500.0     DO       NaN     2012-02-01  
3    600.0     DO       NaN     2012-02-01  
4    300.0     DO       NaN     2012-01-01  
5    500.0     DO       NaN     2012-01-01  
6    1000.0    DO       AL      2012-01-01  
7    800.0     DO       AL      2012-01-01 

在一个单独的 Dataframe 中,我需要分别对每个 person1 的每个唯一月份和年份的所有支出求和。然后,如果 person2 存在,我需要在 person1 和 person2 之间分配支出(在每个月的总和之后)。
输出应该是这样的:

df:
         person     date         sum 
    1    LA         2012-02-01    300.0 
    2    DO         2012-02-01    1100.0        
    3    DO         2012-01-01    1700.0
    4    AL         2012-01-01    900.0 

【问题讨论】:

    标签: python pandas bigdata pandas-groupby pandasql


    【解决方案1】:

    可能不那么优雅,但适用于这种情况:

    m1=(df[df.person2.isna()].groupby([df.date.dt.date,'person1'])
       .payout.sum().reset_index().rename(columns={'person1':'person'}))
    
    m2=df.dropna().groupby([df.date.dt.date,'person1','person2']).payout.mean().reset_index()
    
    df_new=(m1.merge(m2.melt(['date','payout'],value_name='person').
              drop('variable',1),how='outer').groupby(['date','person'],as_index=False).sum())
    
    print(df_new)
    
             date person  payout
    0  2012-01-01     AL   900.0
    1  2012-01-01     DA  1700.0
    2  2012-02-01     DA  1100.0
    3  2012-02-01     LA   300.0
    

    【讨论】:

      【解决方案2】:

      如果 person2 列中有np.where 的人,您可以创建一个包含大量总和的列

      df['payout_sum'] = np.where(df.person2.notnull(), df.payout/2., df.payout)
      

      然后使用concat、groupby和pd.Grouper,可以得到结果:

      df_tot = (pd.concat([df[['date','person1','payout_sum']].rename(columns={'person1':'person'}),
                           df[['date','person2','payout_sum']].rename(columns={'person2':'person'})
                                                                .dropna()])\
                  .groupby([pd.Grouper(key='date', freq='MS'),'person'])['payout_sum']
                  .sum().reset_index())
      print (df_tot)
              date person  payout_sum
      0 2012-01-01     AL       900.0
      1 2012-01-01     DA      1700.0
      2 2012-02-01     DA      1100.0
      3 2012-02-01     LA       300.0
      

      pd.Grouper 与“MS”的兴趣在于它将在月初重新采样,以防您在一个月中的几天内付款。

      【讨论】:

        猜你喜欢
        • 2016-03-27
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2021-01-23
        相关资源
        最近更新 更多