Chapter 10 数据分组和数据透视表
一、数据分组groupby
数据分组就是根据一个或多个键将数据分成若干组,对分组后的数据进行汇总计算。被用作汇总计算的函数称为聚合函数。Python中用groupby()方法进行分组。
源数据如下:
1. 分组键是列名
ic(df.groupby("分类"),df.groupby("分类").count())
输出如下:
直接运行groupby()方法返回的是DataframeGroupby对象而不是Dataframe,这个对象里面包含着分组以后的若干组数据,但是没有直接显示出来,需要对这些分组数据进行汇总计算以后才会展示出来。
以上代码对分组后的数据进行计数运算,因此每一列都会有结果;但是如果对分组后的结果做一些数值运算,这个时候就只有数据类型是数值(int、float)的列才会参与运算,比如下面的求和运算:
ic(df.groupby("分类").sum())
非数值的列直接输出,如下‘商品’列:
2.根据多列分组
依然使用Groupby方法,将多列名称以列表的形式传给Groupby
# 根据多列分组
ic(df.groupby(['分类','商品']).count())
输出如下:
分组后默认对所有数据进行聚合运算,若只需要对某些列进行运算,可通过索引的方式取出来,然后对取出来的数据上进行聚合运算
ic(df.groupby(['分类','商品'])['数值'].sum())
以上代码根据’分类’和’商品’列分组,对’数值’列进行求和运算,输出如下:
2. 分组键是Series
Dataframe中取出一列就是Series数据。与列名的区别就在于传入的参数形式不同,其他操作和根据列名分组相同。需要注意的是,通过多个Series分组也要以列表的形式传入,否则会报错(TypeError: unhashable type: ‘Series’)
# 根据Series分组
ic(df.groupby([df['分类'],df['商品']]).sum())
# 错误代码
ic(df.groupby(df['分类'],df['商品']).sum())
3.aggregate方法
前面使用的聚合函数都是直接在DateFrameGroupby上调用,对所有可计算数据进行同一种聚合运算。aggregate方法可以一次使用多种聚合运算,还可以对不同列进行不同运算。
# 对分类后的所有数据进行'count','sum'两种运算
ic(df.groupby(['分类']).aggregate(['count','sum']))
# 分类后对'分类'列进行计数运算,对'数值'列进行求和运算
ic(df.groupby(['分类']).aggregate({'分类':'count','数值':'sum'}))
输出如下:
4.对分组后的结果重置索引
DataFrameGroupBy 对象经过汇总运算以后的形式并不是标准的DataFrame形式。为了接下来对分组结果进行进一步处理与分析,我们需要把非标准形式转化为标准的 DataFrame 形式,利用的方法就是重置索引reset_index()方法
# 对分组后的结果进行重置索引
ic(df.groupby(['分类']).sum().reset_index())
输出如下:
二、数据透视表pivot_table
数据分组是在一维(行)方向上不断拆分,而数据透视表是在行、列方向上同时拆分。
Excel中插入数据透视表如下图所示,将字段拖拽到相应透视表区域即可完成透视表的制作。
Python中通过pivot_table制作数据透视表。pivot_table的主要参数如下:
- data:做透视表的数据
- values:对应Excel右下角中‘值’的部分,即要计算的列
- index:对应Excel中‘行’部分
- columns:对应Excel中‘列’部分
- aggfunc:对values的计算类型。当只传入一种类型时,表示对所有的值字段都进行同样的计算;如果需要对不同的值进行不同的计算类型,则需要传入一个字典,其中键为列名,值为计算方式
- margins:是否显示合计列
# 数据透视表,df即data做透视表的数据
ic(pd.pivot_table(df,values='数值',columns='商品',index='分类',aggfunc='sum',margins=True))
# 对不同列进行不同运算
df_pivot = pd.pivot_table(df,values=['数值','金额'],columns='商品',index='分类',aggfunc={'金额':'sum','数值':'count'},margins=True).reset_index()
ic(df_pivot)
输出如下: