数据分析day05
数据分析回顾
numpy
- 基于一维或者多维的数组
- 如何创建numpy数组
- np.array()
- plt.imread()
- random
- linspace
- range
- 数组的索引和切片
- 索引:
- arr[0]:取出第一行数据
- 切片:
- arr[行,列]
- 翻转:
- arr[::-1,::-1]
- 索引:
- 级联
- 条件:
- 必须保证维度一致形状相符
- 条件:
- 变形:
- reshape():修改数组的形状
- 基于聚合、统计的函数
- std(标准差),val(方差)
- 矩阵:
- 矩阵乘法
pandas
- Series:类似于一维数组的数据结构
- 创建方式
- 索引和切片
- 运算法则:
- 索引与之一致的元素可以进行算术运算否则补空
- isnull,notnull,unique,nunique
- DataFrame
- df是由Series组成
- df中如果单独取出一行或者一列返回的一定是一个Series
- df的创建方式
- 索引和切片
- 索引:
- df['列索引']
- df.iloc['行索引']
- df.loc[行,列]
- 切片
- df[row1:row4]
- df.loc[:,col1:col4]
- 索引:
- 股票案例:
- read_xxx():将外部文件中的数据读取到df
- to_xxx():将df中的数据写入到文件中
- tushare:财经数据接口包
- Series中有一个方法:shift(x),将Series中的元素上下移动x个位置
- 数据的重新取样:
- df.resameple('A/M').first()/.last()
- 设置时间序列类型
- pd.to_datetime(df['col'])
- 设置指定的列作为源数据的行索引:
- set_index(df['col'])
- df运算的过程中如果返回了一组boolean,则该boolean马上需要作为源数据的行索引,取出True所对应的行数据
- Series中有一个函数:rolling(n),将Series中的前n个数汇总为一组值,通常rolling后面需要进行聚合操作
- 数据清洗
- 缺失值
- isnull-》any,notnull-》all
- dropna()
- 重复值
- drop_duplicates(kee=='first)
- 异常值
- 判定异常值的条件
- None和NAN的区别:
- NAN是float可以参与运算
- 缺失值
- replace():df元素的替换
- map映射
- map运算工具:map==apply
- map只可以基于Series进行运算或者映射
- 随机抽样
- take():打乱df的中行列索引
- random.permutation(n):返回0到n-1的一个随机乱序的序列
- 级联&合并
- 级联:将多个df进行横向或者纵向的拼接
- 合并:根据一个或者多个合并条件进行数据的汇总
- 内,外(推荐),左,右
- 人口分析:
- query:df进行条件查询
- value_counts:统计Series中每一个元素出现的次数
- info()
- 分组聚合
- groupby()
- 高级聚合:作为分组后的运算工具
- apply
- transform
- 透视表:
- index
- value
- aggfunc
- columns
- apply
- df.apply()对df中的行列进行某种形式的运算
- applymap:
- 对df中的元素进行某种形式的运算
- df是由Series组成
项目需求
第一部分:数据类型处理
- 数据加载
- 字段含义:
- user_id:用户ID
- order_dt:购买日期
- order_product:购买产品的数量
- order_amount:购买金额
- 字段含义:
- 观察数据
- 查看数据的数据类型
- 数据中是否存储在缺失值
- 将order_dt转换成时间类型
- 查看数据的统计描述
- 计算所有用户购买商品的平均数量
- 计算所有用户购买商品的平均花费
- 在源数据中添加一列表示月份:astype('datetime64[M]')
In [2]:
import pandas as pd import numpy as np from pandas import DataFrame import matplotlib.pyplot as plt %matplotlib inline
In [17]:
df = pd.read_csv('./CDNOW_master.txt',header=None,sep='\s+',names=['user_id','order_dt','order_product','order_amount']) df.head()
Out[17]:
user_id | order_dt | order_product | order_amount | |
---|---|---|---|---|
0 | 1 | 19970101 | 1 | 11.77 |
1 | 2 | 19970112 | 1 | 12.00 |
2 | 2 | 19970112 | 5 | 77.00 |
3 | 3 | 19970102 | 2 | 20.76 |
4 | 3 | 19970330 | 2 | 20.76 |
In [5]:
df.info() <class 'pandas.core.frame.DataFrame'> RangeIndex: 69659 entries, 0 to 69658 Data columns (total 4 columns): user_id 69659 non-null int64 order_dt 69659 non-null int64 order_product 69659 non-null int64 order_amount 69659 non-null float64 dtypes: float64(1), int64(3) memory usage: 2.1 MB
In [55]:
df.describe()
Out[55]:
user_id | order_product | order_amount | |
---|---|---|---|
count | 69659.000000 | 69659.000000 | 69659.000000 |
mean | 11470.854592 | 2.410040 | 35.893648 |
std | 6819.904848 | 2.333924 | 36.281942 |
min | 1.000000 | 1.000000 | 0.000000 |
25% | 5506.000000 | 1.000000 | 14.490000 |
50% | 11410.000000 | 2.000000 | 25.980000 |
75% | 17273.000000 | 3.000000 | 43.700000 |
max | 23570.000000 | 99.000000 | 1286.010000 |
In [18]:
#order_dt转换成时间序列 df['order_dt'] = pd.to_datetime(df['order_dt'],format='%Y%m%d') df.head()
Out[18]:
user_id | order_dt | order_product | order_amount | |
---|---|---|---|---|
0 | 1 | 1997-01-01 | 1 | 11.77 |
1 | 2 | 1997-01-12 | 1 | 12.00 |
2 | 2 | 1997-01-12 | 5 | 77.00 |
3 | 3 | 1997-01-02 | 2 | 20.76 |
4 | 3 | 1997-03-30 | 2 | 20.76 |
In [10]:
df.info() <class 'pandas.core.frame.DataFrame'> RangeIndex: 69659 entries, 0 to 69658 Data columns (total 4 columns): user_id 69659 non-null int64 order_dt 69659 non-null datetime64[ns] order_product 69659 non-null int64 order_amount 69659 non-null float64 dtypes: datetime64[ns](1), float64(1), int64(2) memory usage: 2.1 MB
In [19]:
#添加新的一列表示月份 #使用Series调用astype('数据类型'):将Serise的元素转换成指定的数据类型 df['month'] = df['order_dt'].values.astype('datetime64[M]') df.head()
Out[19]:
user_id | order_dt | order_product | order_amount | month | |
---|---|---|---|---|---|
0 | 1 | 1997-01-01 | 1 | 11.77 | 1997-01-01 |
1 | 2 | 1997-01-12 | 1 | 12.00 | 1997-01-01 |
2 | 2 | 1997-01-12 | 5 | 77.00 | 1997-01-01 |
3 | 3 | 1997-01-02 | 2 | 20.76 | 1997-01-01 |
4 | 3 | 1997-03-30 | 2 | 20.76 | 1997-03-01 |
第二部分:按月数据分析
- 用户每月花费的总金额
- 绘制曲线图展示
- 所有用户每月的产品购买量
- 所有用户每月的消费总次数
- 统计每月的消费人数
In [23]:
#用户每月花费的总金额 month_amount_series = df.groupby(by='month')['order_amount'].sum() month_amount_series
In [24]:
month_amount_series.plot()
Out[24]:
<matplotlib.axes._subplots.AxesSubplot at 0x232e5a75dd8>
In [26]:
#所有用户每月的产品购买量 df.groupby(by='month')['order_product'].sum().plot()
Out[26]:
<matplotlib.axes._subplots.AxesSubplot at 0x232e572cd30>
In [29]:
#所有用户每月的消费总次数 df.groupby(by='month')['user_id'].count().plot()
Out[29]:
<matplotlib.axes._subplots.AxesSubplot at 0x232e5a6c550>
In [30]:
#统计每月的消费人数(去重) df.groupby(by='month')['user_id'].nunique()
In [36]:
#高级聚合操作 df.groupby(by='month')['user_id'].apply(lambda x:len(x.drop_duplicates()))
Out[36]:
month 1997-01-01 7846 1997-02-01 9633 1997-03-01 9524 1997-04-01 2822 1997-05-01 2214 1997-06-01 2339 1997-07-01 2180 1997-08-01 1772 1997-09-01 1739 1997-10-01 1839 1997-11-01 2028 1997-12-01 1864 1998-01-01 1537 1998-02-01 1551 1998-03-01 2060 1998-04-01 1437 1998-05-01 1488 1998-06-01 1506 Name: user_id, dtype: int64
第三部分:用户个体消费数据分析
- 用户消费总金额和消费总次数的统计描述
- 用户消费金额和消费次数的散点图
- 各个用户消费总金额的直方分布图(消费金额在1000之内的分布)
- 各个用户消费的总数量的直方分布图(消费商品的数量在100次之内的分布)
In [37]:
#用户消费总金额和消费总次数的统计描述 df.describe()
Out[37]:
user_id | order_product | order_amount | |
---|---|---|---|
count | 69659.000000 | 69659.000000 | 69659.000000 |
mean | 11470.854592 | 2.410040 | 35.893648 |
std | 6819.904848 | 2.333924 | 36.281942 |
min | 1.000000 | 1.000000 | 0.000000 |
25% | 5506.000000 | 1.000000 | 14.490000 |
50% | 11410.000000 | 2.000000 | 25.980000 |
75% | 17273.000000 | 3.000000 | 43.700000 |
max | 23570.000000 | 99.000000 | 1286.010000 |
In [39]:
#用户消费金额和消费次数的散点图 user_amount = df.groupby(by='user_id')['order_amount'].sum() user_oder_count = df.groupby(by='user_id')['order_product'].count()
In [41]:
#绘制散点图 plt.scatter(user_oder_count,user_amount) plt.xlabel('count') plt.ylabel('amount')
Out[41]:
Text(0,0.5,'amount')
In [47]:
#各个用户消费总金额的直方分布图(消费金额在1000之内的分布) user_amount_1000 = df.groupby(by='user_id').sum().query('order_amount <= 1000')['order_amount'] plt.hist(user_amount_1000)
In [51]:
#各个用户消费的总数量的直方分布图(消费商品的数量在100之内的分布) user_product_count = df.groupby(by='user_id').sum().query('order_product <= 100')['order_product'] plt.hist(user_product_count)
Out[51]:
(array([19543., 2330., 830., 328., 185., 116., 57., 42., 39., 21.]), array([ 1. , 10.7, 20.4, 30.1, 39.8, 49.5, 59.2, 68.9, 78.6, 88.3, 98. ]), <a list of 10 Patch objects>)
第四部分:用户消费行为分析
- 用户第一次消费的月份分布,和人数统计
- 绘制线形图
- 用户最后一次消费的时间分布,和人数统计
- 绘制线形图
- 新老客户的占比
- 消费一次为新用户
- 消费多次为老用户
- 分析出每一个用户的第一个消费和最后一次消费的时间
- agg(['func1','func2']):对分组后的结果进行指定聚合
- 分析出新老客户的消费比例
- 分析出每一个用户的第一个消费和最后一次消费的时间
- 用户分层
- 分析得出每个用户的总购买量和总消费金额and最近一次消费的时间的表格rfm
- RFM模型设计
- R表示客户最近一次交易时间的间隔。
- /np.timedelta64(1,'D'):去除days
- F表示客户购买商品的总数量,F值越大,表示客户交易越频繁,反之则表示客户交易不够活跃。
- M表示客户交易的金额。M值越大,表示客户价值越高,反之则表示客户价值越低。
- 将R,F,M作用到rfm表中
- R表示客户最近一次交易时间的间隔。
- 根据价值分层,将用户分为:
- 重要价值客户
- 重要保持客户
- 重要挽留客户
- 重要发展客户
- 一般价值客户
- 一般保持客户
- 一般挽留客户
- 一般发展客户
- 使用已有的分层模型即可rfm_func
In [60]:
#用户第一次消费的月份分布,和人数统计 #思路:找出用户购买月份的最小值,进行数量统计 df.groupby(by='user_id')['month'].min().value_counts()
Out[60]:
1997-02-01 8476 1997-01-01 7846 1997-03-01 7248 Name: month, dtype: int64
In [62]:
df.groupby(by='user_id')['month'].min().value_counts().plot()
Out[62]:
<matplotlib.axes._subplots.AxesSubplot at 0x232e7770e48>
In [65]:
#用户最后一次消费的月份分布,和人数统计 df.groupby(by='user_id')['month'].max().value_counts()
In [66]:
df.groupby(by='user_id')['month'].max().value_counts().plot()
Out[66]:
<matplotlib.axes._subplots.AxesSubplot at 0x232e7a78320>
In [ ]:
#分析出新老客户的消费比例
In [69]:
#新用户:用户的首次购买时间和最后一次购买时间,两个时间一样,则表示该用户只购买了一次为新用户 #老用户:不同上为老用户 df_dt_min_max = df.groupby(by='user_id')['order_dt'].agg(['min','max',])#agg(['func1','func2']):对分组后的结果进行指定多种形式聚合 df_dt_min_max.head()
Out[69]:
min | max | |
---|---|---|
user_id | ||
1 | 1997-01-01 | 1997-01-01 |
2 | 1997-01-12 | 1997-01-12 |
3 | 1997-01-02 | 1998-05-28 |
4 | 1997-01-01 | 1997-12-12 |
5 | 1997-01-01 | 1998-01-03 |
In [71]:
(df_dt_min_max['min'] == df_dt_min_max['max']).value_counts()
Out[71]:
True 12054 False 11516 dtype: int64
In [83]:
#分析得出每个用户的总购买量和总消费金额and最近(最后)一次消费的时间的表格rfm rfm = df.pivot_table(index='user_id',aggfunc={'order_product':'sum','order_amount':'sum','order_dt':'max'}) rfm.head()
Out[83]:
order_amount | order_dt | order_product | |
---|---|---|---|
user_id | |||
1 | 11.77 | 1997-01-01 | 1 |
2 | 89.00 | 1997-01-12 | 6 |
3 | 156.46 | 1998-05-28 | 16 |
4 | 100.50 | 1997-12-12 | 7 |
5 | 385.61 | 1998-01-03 | 29 |
In [84]:
#R列表示客户最近一次交易时间的间隔。/np.timedelta64(1,'D'):去除days rfm['R'] = -(rfm['order_dt'] - rfm['order_dt'].max())/np.timedelta64(1,'D') rfm.head()
Out[84]:
order_amount | order_dt | order_product | R | |
---|---|---|---|---|
user_id | ||||
1 | 11.77 | 1997-01-01 | 1 | 545.0 |
2 | 89.00 | 1997-01-12 | 6 | 534.0 |
3 | 156.46 | 1998-05-28 | 16 | 33.0 |
4 | 100.50 | 1997-12-12 | 7 | 200.0 |
5 | 385.61 | 1998-01-03 | 29 | 178.0 |
In [85]:
#将rfm模型对应的数据整合出来 #r:购买的时间间隔 #f:购买商品的总量 #m:购买商品花费的总金额 rfm = rfm[['order_amount','order_product','R']] rfm.rename(columns={'order_amount':'M','order_product':'F'},inplace=True) rfm.head()
Out[85]:
M | F | R | |
---|---|---|---|
user_id | |||
1 | 11.77 | 1 | 545.0 |
2 | 89.00 | 6 | 534.0 |
3 | 156.46 | 16 | 33.0 |
4 | 100.50 | 7 | 200.0 |
5 | 385.61 | 29 | 178.0 |
In [86]:
def rfm_func(x):# -94.310426 -6.122656 177.778362 #存储存储的是三个字符串形式的0或者1 level = x.map(lambda x :'1' if x >= 0 else '0') label = level['R']+ level['F'] + level.M #==>level['M'] d = { '111':'重要价值客户', '011':'重要保持客户', '101':'重要挽留客户', '001':'重要发展客户', '110':'一般价值客户', '010':'一般保持客户', '100':'一般挽留客户', '000':'一般发展客户' } result = d[label] return result #df.apply(func):可以对df中的行或者列进行某种(func)形式的运算 rfm['label'] = rfm.apply(lambda x : x - x.mean()).apply(rfm_func,axis = 1) rfm.head()
Out[86]:
M | F | R | label | |
---|---|---|---|---|
user_id | ||||
1 | 11.77 | 1 | 545.0 | 一般挽留客户 |
2 | 89.00 | 6 | 534.0 | 一般挽留客户 |
3 | 156.46 | 16 | 33.0 | 重要保持客户 |
4 | 100.50 | 7 | 200.0 | 一般发展客户 |
5 | 385.61 | 29 | 178.0 | 重要保持客户 |
用户的生命周期
- 将用户划分为活跃用户和其他用户
- 统计每个用户每个月的消费次数
- 统计每个用户每个月是否消费,消费记录为1否则记录为0
- 知识点:DataFrame的apply和applymap的区别
- applymap:返回df
- 将函数做用于DataFrame中的所有元素(elements)
- apply:返回Series
- apply()将一个函数作用于DataFrame中的每个行或者列
- 知识点:DataFrame的apply和applymap的区别
- 将用户按照每一个月份分成:
- unreg:观望用户(前两月没买,第三个月才第一次买,则用户前两个月为观望用户)
- unactive:首月购买后,后序月份没有购买则在没有购买的月份中该用户的为非活跃用户
- new:当前月就进行首次购买的用户在当前月为新用户
- active:连续月份购买的用户在这些月中为活跃用户
- return:购买之后间隔n月再次购买的第一个月份为该月份的回头客
In [94]:
#统计每个用户每个月的消费次数 df_purchase = df.pivot_table(index='user_id',aggfunc='count',values='order_dt',columns='month').fillna(0) df_purchase.head(5)
Out[94]:
month | 1997-01-01 00:00:00 | 1997-02-01 00:00:00 | 1997-03-01 00:00:00 | 1997-04-01 00:00:00 | 1997-05-01 00:00:00 | 1997-06-01 00:00:00 | 1997-07-01 00:00:00 | 1997-08-01 00:00:00 | 1997-09-01 00:00:00 | 1997-10-01 00:00:00 | 1997-11-01 00:00:00 | 1997-12-01 00:00:00 | 1998-01-01 00:00:00 | 1998-02-01 00:00:00 | 1998-03-01 00:00:00 | 1998-04-01 00:00:00 | 1998-05-01 00:00:00 | 1998-06-01 00:00:00 |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
user_id | ||||||||||||||||||
1 | 1.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 |
2 | 2.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 |
3 | 1.0 | 0.0 | 1.0 | 1.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 2.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 1.0 | 0.0 |
4 | 2.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 1.0 | 0.0 | 0.0 | 0.0 | 1.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 |
5 | 2.0 | 1.0 | 0.0 | 1.0 | 1.0 | 1.0 | 1.0 | 0.0 | 1.0 | 0.0 | 0.0 | 2.0 | 1.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 |
In [96]:
#统计每个用户每个月是否消费,消费记录为1否则记录为0 df_purchase = df_purchase.applymap(lambda x:1 if x > 0 else 0) #df.applymap(func):df的一个运算工具,运算对应的是df中的每一个元素 df_purchase.head(7)
Out[96]:
month | 1997-01-01 00:00:00 | 1997-02-01 00:00:00 | 1997-03-01 00:00:00 | 1997-04-01 00:00:00 | 1997-05-01 00:00:00 | 1997-06-01 00:00:00 | 1997-07-01 00:00:00 | 1997-08-01 00:00:00 | 1997-09-01 00:00:00 | 1997-10-01 00:00:00 | 1997-11-01 00:00:00 | 1997-12-01 00:00:00 | 1998-01-01 00:00:00 | 1998-02-01 00:00:00 | 1998-03-01 00:00:00 | 1998-04-01 00:00:00 | 1998-05-01 00:00:00 | 1998-06-01 00:00:00 |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
user_id | ||||||||||||||||||
1 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
2 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
3 | 1 | 0 | 1 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 1 | 0 | 0 | 0 | 0 | 0 | 1 | 0 |
4 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 1 | 0 | 0 | 0 | 1 | 0 | 0 | 0 | 0 | 0 | 0 |
5 | 1 | 1 | 0 | 1 | 1 | 1 | 1 | 0 | 1 | 0 | 0 | 1 | 1 | 0 | 0 | 0 | 0 | 0 |
6 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 |
7 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 1 | 0 | 0 | 0 | 0 | 1 | 0 | 0 | 0 |
In [ ]:
将用户按照每一个月份分成: unreg:观望用户(前两月没买,第三个月才第一次买,则用户前两个月为观望用户) unactive:首月购买后,后序月份没有购买则在没有购买的月份中该用户的为非活跃用户 new:当前月就进行首次购买的用户在当前月为新用户 active:连续月份购买的用户在这些月中为活跃用户 return:购买之后间隔n月再次购买的第一个月份为该月份的回头客
In [97]:
#将df_purchase中的原始数据0和1修改为new,unactive......,返回新的df叫做df_purchase_new #固定算法 def active_status(data): #data就是df_purchase中的某一行数据(0,1不同分布组成) status = []#某个用户每一个月的活跃度 for i in range(18): #若本月没有消费 if data[i] == 0: if len(status) > 0: if status[i-1] == 'unreg': status.append('unreg') else: status.append('unactive') else: status.append('unreg') #若本月消费 else: if len(status) == 0: status.append('new') else: if status[i-1] == 'unactive': status.append('return') elif status[i-1] == 'unreg': status.append('new') else: status.append('active') return status pivoted_status = df_purchase.apply(active_status,axis = 1) pivoted_status.head()
Out[97]:
month | 1997-01-01 00:00:00 | 1997-02-01 00:00:00 | 1997-03-01 00:00:00 | 1997-04-01 00:00:00 | 1997-05-01 00:00:00 | 1997-06-01 00:00:00 | 1997-07-01 00:00:00 | 1997-08-01 00:00:00 | 1997-09-01 00:00:00 | 1997-10-01 00:00:00 | 1997-11-01 00:00:00 | 1997-12-01 00:00:00 | 1998-01-01 00:00:00 | 1998-02-01 00:00:00 | 1998-03-01 00:00:00 | 1998-04-01 00:00:00 | 1998-05-01 00:00:00 | 1998-06-01 00:00:00 |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
user_id | ||||||||||||||||||
1 | new | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive |
2 | new | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive | unactive |
3 | new | unactive | return | active | unactive | unactive | unactive | unactive | unactive | unactive | return | unactive | unactive | unactive | unactive | unactive | return | unactive |
4 | new | unactive | unactive | unactive | unactive | unactive | unactive | return | unactive | unactive | unactive | return | unactive | unactive | unactive | unactive | unactive | unactive |
5 | new | active | unactive | return | active | active | active | unactive | return | unactive | unactive | return | active | unactive | unactive | unactive | unactive | unactive |
- 每月【不同活跃】用户的计数
- purchase_status_ct = df_purchase_new.apply(lambda x : pd.value_counts(x)).fillna(0)
- 转置进行最终结果的查看
In [99]:
pivoted_status.apply(lambda x:pd.value_counts(x)).fillna(0)
Out[99]:
month | 1997-01-01 00:00:00 | 1997-02-01 00:00:00 | 1997-03-01 00:00:00 | 1997-04-01 00:00:00 | 1997-05-01 00:00:00 | 1997-06-01 00:00:00 | 1997-07-01 00:00:00 | 1997-08-01 00:00:00 | 1997-09-01 00:00:00 | 1997-10-01 00:00:00 | 1997-11-01 00:00:00 | 1997-12-01 00:00:00 | 1998-01-01 00:00:00 | 1998-02-01 00:00:00 | 1998-03-01 00:00:00 | 1998-04-01 00:00:00 | 1998-05-01 00:00:00 | 1998-06-01 00:00:00 |
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
active | 0.0 | 1157.0 | 1681.0 | 1773.0 | 852.0 | 747.0 | 746.0 | 604.0 | 528.0 | 532.0 | 624.0 | 632.0 | 512.0 | 472.0 | 571.0 | 518.0 | 459.0 | 446.0 |
new | 7846.0 | 8476.0 | 7248.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 |
return | 0.0 | 0.0 | 595.0 | 1049.0 | 1362.0 | 1592.0 | 1434.0 | 1168.0 | 1211.0 | 1307.0 | 1404.0 | 1232.0 | 1025.0 | 1079.0 | 1489.0 | 919.0 | 1029.0 | 1060.0 |
unactive | 0.0 | 6689.0 | 14046.0 | 20748.0 | 21356.0 | 21231.0 | 21390.0 | 21798.0 | 21831.0 | 21731.0 | 21542.0 | 21706.0 | 22033.0 | 22019.0 | 21510.0 | 22133.0 | 22082.0 | 22064.0 |
unreg | 15724.0 | 7248.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 | 0.0 |
In [100]:
#进行转置在进行查看 pivoted_status.apply(lambda x:pd.value_counts(x)).fillna(0).T
Out[100]:
active | new | return | unactive | unreg | |
---|---|---|---|---|---|
month | |||||
1997-01-01 | 0.0 | 7846.0 | 0.0 | 0.0 | 15724.0 |
1997-02-01 | 1157.0 | 8476.0 | 0.0 | 6689.0 | 7248.0 |
1997-03-01 | 1681.0 | 7248.0 | 595.0 | 14046.0 | 0.0 |
1997-04-01 | 1773.0 | 0.0 | 1049.0 | 20748.0 | 0.0 |
1997-05-01 | 852.0 | 0.0 | 1362.0 | 21356.0 | 0.0 |
1997-06-01 | 747.0 | 0.0 | 1592.0 | 21231.0 | 0.0 |
1997-07-01 | 746.0 | 0.0 | 1434.0 | 21390.0 | 0.0 |
1997-08-01 | 604.0 | 0.0 | 1168.0 | 21798.0 | 0.0 |
1997-09-01 | 528.0 | 0.0 | 1211.0 | 21831.0 | 0.0 |
1997-10-01 | 532.0 | 0.0 | 1307.0 | 21731.0 | 0.0 |
1997-11-01 | 624.0 | 0.0 | 1404.0 | 21542.0 | 0.0 |
1997-12-01 | 632.0 | 0.0 | 1232.0 | 21706.0 | 0.0 |
1998-01-01 | 512.0 | 0.0 | 1025.0 | 22033.0 | 0.0 |
1998-02-01 | 472.0 | 0.0 | 1079.0 | 22019.0 | 0.0 |
1998-03-01 | 571.0 | 0.0 | 1489.0 | 21510.0 | 0.0 |
1998-04-01 | 518.0 | 0.0 | 919.0 | 22133.0 | 0.0 |
1998-05-01 | 459.0 | 0.0 | 1029.0 | 22082.0 | 0.0 |
1998-06-01 | 446.0 | 0.0 | 1060.0 | 22064.0 | 0.0 |
来源:https://www.cnblogs.com/bky20061005/p/12233254.html