按条件添加小计列

2 投票
4 回答
75 浏览
提问于 2025-04-14 15:20

请问你能告诉我怎么添加一个季度列吗?这个列里要包含每个月的值的总和。

部分 2024年3月1日 00:00:00 2024年4月1日 00:00:00 2024年5月1日 00:00:00 2024年6月1日 00:00:00 2024年7月1日 00:00:00 2024年8月1日 00:00:00 2024年9月1日 00:00:00
部分1 6 8 2 3 0 5 5
部分2 7 1 3 8 9 4 10
部分3 10 7 4 5 6 10 0
部分4 6 9 3 0 10 9 10
部分5 2 1 10 8 7 3 3
部分6 1 0 4 1 1 7 8

我想要的输出是这样的:

部分 2024年3月1日 00:00:00 Q1'24 2024年4月1日 00:00:00 2024年5月1日 00:00:00 2024年6月1日 00:00:00 Q2'24 2024年7月1日 00:00:00 2024年8月1日 00:00:00 2024年9月1日 00:00:00 Q3'24
部分1 6 6 8 2 3 13 0 5 5 10
部分2 7 7 1 3 8 12 9 4 10 23
部分3 10 10 7 4 5 16 6 10 0 16
部分4 6 6 9 3 0 12 10 9 10 29
部分5 2 2 1 10 8 19 7 3 3 13
部分6 1 1 0 4 1 5 1 7 8 16

原始数据

4 个回答

0

这里你可以看到代码。

import pandas as pd
from io import StringIO

data='''
part,"2024-03-01 00:00:00","2024-04-01 00:00:00","2024-05-01 00:00:00","2024-06-01 00:00:00","2024-07-01 00:00:00","2024-08-01 00:00:00","2024-09-01 00:00:00"
part1,6,8,2,3,0,5,5
part2,7,1,3,8,9,4,10
part3,10,7,4,5,6,10,0
part4,6,9,3,0,10,9,10
part5,2,1,10,8,7,3,3
part6,1,0,4,1,1,7,8
'''
data_str=StringIO(data)

df=pd.read_csv(data_str)
print(df)
#Unpivot the DF
un_pivot = pd.melt(df, 
   id_vars = 'part',var_name='date', value_name='count'

)
print(un_pivot.dtypes)
un_pivot['date']=pd.to_datetime(un_pivot['date'])

un_pivot_g=un_pivot.groupby(['part', pd.Grouper(key='date', freq='Q')]).sum().reset_index()

un_pivot_g['date'] = un_pivot_g['date'].dt.to_period('Q').astype(str)


pivot_result = un_pivot_g.pivot_table(index='part', columns='date', values='count')

final_df = pd.merge(df, pivot_result, on='part')
print(final_df,'output')

输出的图片

在这里输入图片描述

2

一种方法是先把数据进行转置,然后使用一个叫做 Grouper 的工具来把季度数据分组;接着,你可以把结果数据的索引转换成 Period 类型,再把它拼接回原来的数据中,最后再转置一次,就能得到想要的结果:

tmp = df.T
tmp.index = pd.to_datetime(tmp.index)
res = tmp.groupby(pd.Grouper(freq='Q')).sum()
res.index = res.index.to_period('Q')
out = pd.concat([tmp, res]).sort_index(key=lambda x:pd.PeriodIndex(x, 'Q')).T

输出结果:

        2024-03-01 00:00:00  2024Q1  2024-04-01 00:00:00  2024-05-01 00:00:00  \
part
part1                     6       6                    8                    2
part2                     7       7                    1                    3
part3                    10      10                    7                    4
part4                     6       6                    9                    3
part5                     2       2                    1                   10
part6                     1       1                    0                    4

        2024-06-01 00:00:00  2024Q2  2024-07-01 00:00:00  2024-08-01 00:00:00  \
part
part1                     3      13                    0                    5
part2                     8      12                    9                    4
part3                     5      16                    6                   10
part4                     0      12                   10                    9
part5                     8      19                    7                    3
part6                     1       5                    1                    7

        2024-09-01 00:00:00  2024Q3
part
part1                     5      10
part2                    10      23
part3                     0      16
part4                    10      29
part5                     3      13
part6                     8      16
3

你可以通过使用 DatetimeIndex.to_period 来把列转换为季度时间段,这样可以方便计算小计。然后,可以用 concat 把这些小计和原始数据合并在一起。为了确保数据的顺序正确,可以使用 DataFrame.sort_index 来排序:

df.columns = pd.to_datetime(df.columns)
out = (pd.concat([df,
                 df.groupby(df.columns.to_period('Q'), axis=1).sum()],
                 axis=1)
         .sort_index(axis=1, key=lambda x: pd.PeriodIndex(x, 'Q')))


out.columns = [x.strftime("Q%q'%y") if isinstance(x, pd.Period) 
               else x for x in out.columns]

print (out)
       2024-03-01 00:00:00  Q1'24  2024-04-01 00:00:00  2024-05-01 00:00:00  \
part                                                                          
part1                    6      6                    8                    2   
part2                    7      7                    1                    3   
part3                   10     10                    7                    4   
part4                    6      6                    9                    3   
part5                    2      2                    1                   10   
part6                    1      1                    0                    4   

       2024-06-01 00:00:00  Q2'24  2024-07-01 00:00:00  2024-08-01 00:00:00  \
part                                                                          
part1                    3     13                    0                    5   
part2                    8     12                    9                    4   
part3                    5     16                    6                   10   
part4                    0     12                   10                    9   
part5                    8     19                    7                    3   
part6                    1      5                    1                    7   

       2024-09-01 00:00:00  Q3'24  
part                               
part1                    5     10  
part2                   10     23  
part3                    0     16  
part4                   10     29  
part5                    3     13  
part6                    8     16  

说得好 - 在最新版本的 pandas (2.1.4+) 中需要进行转置,谢谢 @nick:

df.columns = pd.to_datetime(df.columns)
df = df.T

out = (pd.concat([df,
                 df.groupby(df.index.to_period('Q')).sum()]).T
          .sort_index(axis=1, key=lambda x: pd.PeriodIndex(x, 'Q'))
         )


out.columns = [x.strftime("Q%q'%y") 
               if isinstance(x, pd.Period) 
               else x for x in out.columns]

print (out)

       2024-03-01 00:00:00  Q1'24  2024-04-01 00:00:00  2024-05-01 00:00:00  \
part                                                                          
part1                    6      6                    8                    2   
part2                    7      7                    1                    3   
part3                   10     10                    7                    4   
part4                    6      6                    9                    3   
part5                    2      2                    1                   10   
part6                    1      1                    0                    4   

       2024-06-01 00:00:00  Q2'24  2024-07-01 00:00:00  2024-08-01 00:00:00  \
part                                                                          
part1                    3     13                    0                    5   
part2                    8     12                    9                    4   
part3                    5     16                    6                   10   
part4                    0     12                   10                    9   
part5                    8     19                    7                    3   
part6                    1      5                    1                    7   

       2024-09-01 00:00:00  Q3'24  
part                               
part1                    5     10  
part2                   10     23  
part3                    0     16  
part4                   10     29  
part5                    3     13  
part6                    8     16 

撰写回答