前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >盘一盘 Python 特别篇 15 - Pivot Table

盘一盘 Python 特别篇 15 - Pivot Table

作者头像
用户5753894
发布2020-06-16 10:20:22
1.4K0
发布2020-06-16 10:20:22
举报
文章被收录于专栏:王的机器

本文含 3796 字,22 图表截屏

建议阅读 20 分钟

本文是 Python 系列的特别篇的第十五篇

从功能上讲,Pandas 中用透视表 (pivot table) 和 Excel 里面的透视表是一样的。透视表是一种做多维数据分析的工具,还记得 Pandas 的 split-apply-combine 三部曲吗?首先用 groupby 分组,再平行将某个函数应用到各组上,最后自动连接成一个总表。今天介绍的 pivot_table() 函数可以将上面“拆分-应用-结合”三个步骤用一行来完成。

先看一张图:

Pivot 字面意思是支点,即上图中的 index 和 columns 指定的行和列标签,支点可想理解成数据 (values) 在哪个维度上做整合 (aggfunc),再吧 NaN 值用 fill_value 替代,按行按列加总 (margin=True)。

理解还有些难度?没问题,看完本帖就懂了。

数据

首先从 csv 读数据。

代码语言:javascript
复制
df = pd.read_csv('PB Sales.csv')
df

设置“单行”为 Pivot

创建透视表的 pivot_table() 函数里面的参数设置很多,学习它最有效的方式是每一步设置一个参数,检查结果是否符合预期。

先从最简单的语法开始,只设置 index='Account',通用语法如下:

pd.pivot_table(df, index=label_str)

代码语言:javascript
复制
pd.pivot_table( df, index="Account" )

从上表结果看,Price 和 Quantity 两列按照 Account 以某种方式合并了。看原 df 最后两行,账户 MM729833 合并成一行,对应的 Price 和 Quantity 是 42500 和 200,看来某种方式是求平均。现在大概可以猜出 pivot_table() 函数中有个参数用来设置整合方式,而默认值为平均。

设置“多行”为 Pivot

上例设置单个 index,接下来看看设置多个 index 的结果是什么样的。这时用列表来存储多个 index。通用语法如下:

代码语言:javascript
复制
pd.pivot_table(df, index=label_list)
代码语言:javascript
复制
pd.pivot_table( df, index=["Account","Trader","Counterparty"] )

上表显示着每个 Account 对应的交易员和交易对手的信息,但有点乱。

一个交易员管理一个或多个账户,多个交易员可以和一个交易对手交易,改变 index 里面的标签顺序,先按 Counterparty 合并,再按 Trader 合并。

代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader"] )

到目前为止,我们只设置了 index,那为什么只在 Price 和 Quantity 两列上做整合呢?因为这两列的值是数值型 (int, float),而其他例的值是非数值型 (object),用 df.dtypes 就可看出。

代码语言:javascript
复制
df.dtypes
代码语言:javascript
复制
Account object
Trader object
Counterparty object
Ticker object
Quantity int64
Value int64
Category object
dtype: object

设定被整合的数据

如果只看 Price 列下的整合结果,只需设置 values='Price' 或者 values=['Price'],通用语法如下:

pd.pivot_table(df, index=label_list, values=label_list)

代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader"], 
values="Value" )

设置整合函数

默认整合函数是求平均,如果要用求和的函数需要设置 aggfunc=np.sum,通用语法为

代码语言:javascript
复制
pd.pivot_table(df, index=label_list, values=label_list, aggfunc=func)
代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader"], 
                    values=["Value"], 
                    aggfunc=np.sum )

aggfunc 参数可以被设置为多个函数,用列表储存,通用语法为

代码语言:javascript
复制
pd.pivot_table(df, index=label_list, values=label_list, aggfunc=func_list)
代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader"], 
                    values=["Value"],
                    aggfunc=[len, np.sum] )

设定“列” 为 Pivot

如果进一步想看按产品类别划分后的整合结果,可以设置 columns=['Category],通用语法为,

代码语言:javascript
复制
pd.pivot_table(df, index=label_list, values=label_list, columns=label_list, aggfunc=func_list)
代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader"], 
                    values=["Value"],
                    columns=["Category"],
                    aggfunc=[len, np.sum] )

上表结果中的 NaN 不好看,可设置 fill_value=0 用零替代。

代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader"], 
                    values=["Value"],
                    columns=["Category"],
                    aggfunc=[len, np.sum],
                    fill_value=0 )

除此之外还可以把产品类别放在 index 中,改变结果的展示方式而已 (那些结果为零都没显示了,看起来更舒服点)。

代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader","Category"], 
                    values=["Value"],
                    aggfunc=[len, np.sum],
                    fill_value=0 )

设置“显示”总和

要看总计怎么办?设置 margins=True 就可以了。

代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader","Category"], 
                    values=["Value","Quantity"],
                    aggfunc=[len, np.sum],
                    fill_value=0,
                    margins=True )

整合函数的不同设置方式

aggfunc 参数还可以传进一个字典来实现不同列下应用不同的整合函数,语法如下:

代码语言:javascript
复制
aggfunc = {col_1:func_1, col_2:func_2, ... col_n:func_n}
代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader","Category"], 
                    values=["Value","Quantity"],
                    aggfunc={"Value":np.sum, "Quantity":len},
                    fill_value=0,
                    margins=True )

再进一步,不同列还可以应用多个函数,只需把函数名称变成函数列表就可以了。语法如下:

代码语言:javascript
复制
aggfunc = {col_1:func_1, col_2:func_list, ... col_n:func_n}

假设第二列传入一个函数列表。

代码语言:javascript
复制
pd.pivot_table( df, index=["Counterparty","Trader","Category"], 
                    values=["Value","Quantity"],
                    aggfunc={"Value":[np.sum, min, max], 
                             "Quantity":len},
                    fill_value=0 )

查询终表

一次性做出这样的表不容易,但按步摸索 (一次设置一次参数) 的方式却很简单。

一旦得到最终结果,它本质还是个数据帧,因此可以使用所有标配函数。下例用 query() 函数来查询名叫 Steven Wang 和 Sherry Zhang 的交易员。

代码语言:javascript
复制
table = pd.pivot_table( df, index=["Counterparty","Trader","Category"], 
                            values=["Value","Quantity"],
                            aggfunc={"Value":np.sum, "Quantity":len},
                            fill_value=0 )
table.query('Trader == ["Steven Wang", "Sherry Zhang"]')

查询所有期权和基金产品相关的信息。

代码语言:javascript
复制
table.query('Category == ["Fund", "Option"]')

总结,一图胜千言!现在再看下图可视化 pivot_table() 函数的用法,是不是都能理解了?

Stay Tuned!

本文参与 腾讯云自媒体同步曝光计划,分享自微信公众号。
原始发表:2020-06-12,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 王的机器 微信公众号,前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
灰盒安全测试
腾讯知识图谱(Tencent Knowledge Graph,TKG)是一个集成图数据库、图计算引擎和图可视化分析的一站式平台。支持抽取和融合异构数据,支持千亿级节点关系的存储和计算,支持规则匹配、机器学习、图嵌入等图数据挖掘算法,拥有丰富的图数据渲染和展现的可视化方案。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档