淘宝用户行为数据分析
一.项目背景
本数据报告以淘宝app平台为数据集,通过行业的指标对淘宝用户行为进行分析,从而探索淘宝用户的行为模式,具体指标包括:日PV和日UV分析,付费率分析,复购行为分析,漏斗流失分析和用户价值RFM分析。
二.数据来源
https://tianchi.aliyun.com/dataset/dataDetail?dataId=46&userId=1
三.提出问题
-
1.日PV有多少
-
2.日UV有多少
-
3.付费率情况如何
-
4.复购率是多少
-
5.漏斗流失情况如何
-
6.用户价值情况
四.理解数据
-
本数据集共有104万条左右数据,数据为淘宝APP2014年11月18日至2014年12月18日的用户行为数据,共计6列字段,列字段分别是:
-
user_id:用户身份,脱敏
-
item_id:商品ID,脱敏
-
behavior_type:用户行为类型(包含点击、收藏、加购物车、支付四种行为,分别用数字1、2、3、4表示)
-
user_geohash:地理位置
-
item_category:品类ID(商品所属的品类)
-
time:用户行为发生的时间
五.数据清洗
#导入库
import pandas as pd
import numpy as np
import seaborn as sns
%matplotlib inline
import matplotlib.pyplot as plt
#导入数据
path = 'D:/办公/数据分析/taobao1920/taobao2014.csv'
data_user = pd.read_csv(path,encoding='utf-8',engine='python')
data_user.head()
输出:
image.png
#缺失值处理
missingTotal = data_user.isnull().sum()
missingExist = missingTotal[missingTotal>0]
missingExist = missingExist.sort_values(ascending = False)
print(missingTotal)
输出:
user_id 0
item_id 0
behavior_type 0
user_geohash 8334824
item_category 0
time 0
dtype: int64
print(missingExist)
输出
user_geohash 8334824
dtype: int64
- 存在缺失值的是user_geohash,有717785条,不能删除缺失值,因为地理信息在数据集收集过程中做过加密转换,因此对数据集不做处理。
#一致化处理
import re
#拆分time数据为date日期和hour小时两个数据
data_user['date'] = data_user.time.map(lambda s: re.compile(' ').split(s)[0])
data_user['hour'] = data_user.time.map(lambda s: re.compile(' ').split(s)[1])
data_user.head()
输出:
image.png
#查看data_user数据集的数据类型
data_user.dtypes
输出:
user_id int64
item_id int64
behavior_type int64
user_geohash object
item_category int64
time object
date object
hour object
dtype: object
发现time列和date列应该转化为日期类数据类型,hour列应该是字符串数据类型。
#数据类型转化
data_user['time'] = pd.to_datetime(data_user['time'])
data_user['date'] = pd.to_datetime(data_user['date'])
data_user['hour'] = data_user['hour'].astype('int64')
data_user.dtypes
#查看数据集统计描述检查异常值是否存在
data_user = data_user.sort_values(by = 'time',ascending=True)
data_user = data_user.reset_index(drop=True)
data_user.describe()
输出:
image.png
- 通过观察数据集的四分位数,总数,平均值,方差等,发现数据集并无异常值存在。
六、用户行为分析
(1)pv和uv分析
-
PV(访问量):即Page View, 具体是指网站的是页面浏览量或者点击量,页面被刷新一次就计算一次。
-
UV(独立访客):即Unique Visitor,访问您网站的一台电脑客户端为一个访客。
1)日访问量分析
#pv_daily记录每天用户操作次数,uv_daily记录每天不同的上线用户数量
pv_daily = data_user.groupby('date')['user_id'].count().reset_index().rename(columns={'user_id':'pv'})
uv_daily = data_user.groupby('date')['user_id'].apply(lambda x: x.drop_duplicates().count()).reset_index().rename(columns={'user_id':'uv'})
fig,axes=plt.subplots(2,1,sharex=True)
pv_daily.plot(x='date',y='pv',ax=axes[0])
uv_daily.plot(x='date',y='uv',ax=axes[1])
axes[0].set_title('pv_daily')
axes[1].set_title('uv_daily')
plt.savefig('日访问pv-uv对比图.png')
输出:
image.png
- 结果显示如上图所示,在双十二期间,pv和uv访问量达到峰值,并且可以发现,uv和pv两个访问量数值差距比较大,同时,因为数据集总人数大约是10000人左右,因此,通过uv值可以分析出双十二期间淘宝用户的日活跃大概是45%浮动。
2)小时访问量分析
#pv_hour记录每小时用户操作次数,uv_hour记录每小时不同的上线用户数量
pv_hour = data_user.groupby('hour')['user_id'].count().reset_index().rename(columns={'user_id':'pv'})
uv_hour = data_user.groupby('hour')['user_id'].apply(lambda x: x.drop_duplicates().count()).reset_index().rename(columns={'user_id':'uv'})
fig,axes=plt.subplots(2,1,sharex=True)
pv_hour.plot(x='hour',y='pv',ax=axes[0])
uv_hour.plot(x='hour',y='uv',ax=axes[1])
axes[0].set_title('pv_hour')
axes[1].set_title('uv_hour')
plt.savefig('小时访问pv-uv对比图.png')
输出:
image.png
- 可以看出pv和uv都在0点开始下降,一直到凌晨5点到达最低点然后随着时间开始上升。同时在晚上18:00左右,pv波动情况比较剧烈,相比来看uv不太明显,因此晚上18:00以后是淘宝用户访问app的活跃时间段。
3)不同行为类型用户pv分析
#不同行为类型用户pv分析
pv_detail = data_user.groupby(['behavior_type','hour'])['user_id'].count().reset_index().rename(columns={'user_id':'total_pv'})
fig,axes = plt.subplots(2,1,sharex=True)#建立2*1的图共享x轴
sns.pointplot(x='hour',y='total_pv',hue='behavior_type',data=pv_detail,ax=axes[0])
sns.pointplot(x='hour',y='total_pv',hue='behavior_type',data=pv_detail[pv_detail.behavior_type!=1],ax=axes[1])
axes[0].set_title('pv_different_behavior_type')
axes[1].set_title('pv_different_behavior_type_except1')
plt.tight_layout()#控制两个图之间的距离,更美观
plt.savefig('不同行为类型用户pv图.png')
输出:
image.png
- 由图表显示:点击这一用户行为相比较于其他三类用户行为,pv访问量较高,同时四种用户行为的波动情况基本一致,因此晚上这一时间段不管哪一种用户行为,pv访问量都是最高的。从图2可以看出,加入购物车这一用户行为的pv总量高于收藏的总量,因此在后续漏斗流失分析中,用户行为类型3应该在2之前分析。
七.用户消费行为分析
(1)用户购买次数情况分析
data_user_buy = data_user[data_user.behavior_type==4].groupby('user_id')['behavior_type'].count()
sns.distplot(data_user_buy,kde=False)
plt.title('daily_user_buy')
plt.savefig('用户购买次数柱状图.png')
输出:
image.png
- 图表显示:淘宝用户消费次数普遍在10次以内,因此需要重点关注购买次数在10次以上的消费者用户群体。
(2)日ARPPU
-
ARPPU(average revenue per paying user)是指从每位付费用户身上获得的收入,它反映的是每个付费用户的平均付费额度。
-
ARPPU=总收入/活跃用户付费数量
-
因为本数据集中没有消费金额,因此在计算过程中用消费次数代替消费金额
-
人均消费次数=消费总次数/消费人数
data_user_buy1 = data_user[data_user.behavior_type==4].groupby(['date','user_id'])['behavior_type'].count().reset_index().rename(columns={'behavior_type':'total'})
data_user_buy1.groupby('date').apply(lambda x: x.total.sum()/x.total.count()).plot()
plt.title('daily_ARPPU')
plt.savefig('日ARPPU.png')
输出:
image.png
- 图表显示:平均每天消费次数在1-2次之间波动,双十二期间消费次数达到最高值。
(3)日ARPU
- ARPU(Average Revenue Per User) :平均每用户收入,可通过 总收入/AU 计算得出。它可以衡量产品的盈利能力和发展活力。
#活跃用户数平均消费次数=消费总次数/活跃用户人数(每天有操作行为的为活跃)
data_user['operation'] = 1
data_user_buy2 = data_user.groupby(['date','user_id','behavior_type'])['operation'].count().reset_index().rename(columns={'operation':'total'})
data_user_buy2.groupby('date').apply(lambda x: x[x.behavior_type==4].total.sum()/len(x.user_id.unique())).plot()
plt.title('daily_ARPU')
plt.savefig('日ARPU.png')
输出:
image.png
- 由图表显示,日ARPU最高点接近2.0,在每个月的11-13号。其他时间ARPU在0.4-0.6之间平缓波动。
(4)付费率
付费率=消费人数/活跃用户人数
data_user_buy2.groupby('date').apply(lambda x: x[x.behavior_type==4].total.count()/len(x.user_id.unique())).plot()
plt.title('daily_afford_rate')
plt.savefig('付费率图.png')
输出:
image.png
- 可以看到付费率的曲线与ARPU曲线基本一致,最高点也是在11-13号之间达到0.5,其他时间则在0.20-0.25之间波动。
(5)同一时间段用户消费次数分布
data_user_buy3 = data_user[data_user.behavior_type==4].groupby(['user_id','date','hour'])['operation'].sum().rename('buy_count')
sns.distplot(data_user_buy3)
plt.savefig('同一时间段用户消费次数分布图.png')
print('大多数用户消费:{}次'.format(data_user_buy3.mode()[0]))
输出:大多数用户消费:1次
image.png
八.复购情况分析
复购情况,即两天以上有购买行为,一天多次购买算一次
复购率=有复购行为的用户数/有购买行为的用户总数
data_rebuy = data_user[data_user.behavior_type==4].groupby('user_id')['date'].apply(lambda x: len(x.unique())).rename('rebuy_count')
print('复购率:',round(data_rebuy[data_rebuy>=2].count()/data_rebuy.count(),4))
输出:
复购率: 0.8717
从复购率0.8717来看,用户的复购率还是很高的。
#所有复购时间间隔消费次数分布
data_day_buy = data_user[data_user.behavior_type==4].groupby(['user_id','date']).operation.count().reset_index()
输出:
image.png
data_user_buy4 = data_day_buy.groupby('user_id').date.apply(lambda x:x.sort_values().diff(1).dropna())
data_user_buy4.astype('timedelta64[D]')
data_user_buy4 = data_user_buy4.map(lambda x:x.days)
data_user_buy4.value_counts().plot(kind='bar')
plt.title('time_gap')
plt.xlabel('gap_day')
plt.ylabel('gap_count')
plt.savefig('复购时间间隔消费次数分布图.png')
输出:
image.png
多数用户消费次数随着消费时间间隔的增加而不断下降,在1-10天之内复购次数比较多,10天之后复购次数淘宝用户很少在进行复购,因此需要重视10天之内的淘宝用户复购行为,增加用户复购。不同用户平均复购时间呈正态分布,但是总体来看,呈现逐渐下降趋势。多数淘宝用户平均复购时间集中在1-5天时间间隔内。
#不同用户平均复购时间分析
sns.distplot(data_user_buy4.reset_index().groupby('user_id').date.mean())
plt.savefig('不同用户平均复购时间分析图.png')
输出:
image.png
不同用户平均复购时间呈正态分布,但是总体来看,呈现逐渐下降趋势。多数淘宝用户平均复购时间集中在1-5天时间间隔内。
九.漏斗流失分析
漏斗分析是一套流程式数据分析,它能够科学反映用户行为状态以及从起点到终点各阶段用户转化率情况的重要分析模型。
data_user_count=data_user.groupby(['behavior_type']).count()
data_user_count.head()
输出:
image.png
pv_all=data_user['user_id'].count()
liushi_dianji = round((pv_all-data_user_count.iloc[0,0])/pv_all,4)
liushi_gouwuche = round((data_user_count.iloc[0,0]-data_user_count.iloc[2,0])/data_user_count.iloc[0,0],4)
liushi_shoucang = round((data_user_count.iloc[2,0]-data_user_count.iloc[1,0])/data_user_count.iloc[2,0],4)
liushi_buy = round((data_user_count.iloc[1,0]-data_user_count.iloc[3,0])/data_user_count.iloc[1,0],4)
print('浏览-点击流失率:',liushi_dianji,'\n点击-加入购物车流失率:',liushi_gouwuche,'\n购物车-收藏流失率:',liushi_shoucang,'\n收藏-购买流失率',liushi_buy)
输出:
浏览-点击流失率: 0.0576
点击-加入购物车流失率: 0.9703
购物车-收藏流失率: 0.294
收藏-购买流失率 0.5044
十.用户行为与商品种类关系分析
#不同用户行为类别的转化率
data_category=data_user[data_user.behavior_type!=2].groupby(['item_category','behavior_type']).operation.count().unstack(1).rename(columns={1:'点击量',3:'加入购物车量',4:'购买量'}).fillna(0)
data_category.head()
输出:
image.png
#转化率计算
data_category['转化率']=data_category['购买量']/data_category['点击量']
data_category.head()
输出:
image.png
data_category = data_category.fillna(0)
data_category = data_category[data_category['转化率']<=1]#小于1的转化率才是正常值
sns.distplot(data_category['转化率'])
plt.savefig('用户行为转化率图.png')
输出:
image.png
sns.distplot(data_category[data_category['转化率']>0]['转化率'],kde=False)
输出:
image.png
图表显示:基本上各种用户行为类型转换率都在0.1以内,同时绝大多数用户都没有购买情况,需要重点关注出现该现象的原因进行分析改进。
data_category['感兴趣比率'] = data_category['加入购物车量']/data_category['点击量']
data_category.head()
输出:
image.png
#异常值处理,感兴趣比率绘图
data_category = data_category[data_category['感兴趣比率']<=1]
sns.distplot(data_category['感兴趣比率'])
sns.distplot(data_category[data_category['感兴趣比率']>0]['感兴趣比率'],kde=False)
输出:
image.png
image.png
图表显示:感兴趣比率和转化率类似,基本也是0.1以内,说明用户点击的绝大多数商品并非感兴趣,需要重视推荐系统的调整。
#将转化率分三类查看各类占比例
data_convert_rate = pd.cut(data_category['转化率'],[-1,0,0.1,1]).value_counts()
data_convert_rate = data_convert_rate/data_convert_rate.sum()
data_convert_rate
输出:
(0.0, 0.1] 0.502693
(-1.0, 0.0] 0.476885
(0.1, 1.0] 0.020422
Name: 转化率, dtype: float64
#将感兴趣比率分三类查看各类占比例
data_interest_rate = pd.cut(data_category['感兴趣比率'],[-1,0,0.1,1]).value_counts()
data_interest_rate = data_interest_rate/data_interest_rate.sum()
data_interest_rate
输出:
(0.0, 0.1] 0.538487
(-1.0, 0.0] 0.390373
(0.1, 1.0] 0.071140
Name: 感兴趣比率, dtype: float64
根据以上输出显示:转化率达到0.1以上仅仅只有2%的用户,有47%的用户几乎不会发生购买行为。同时从感兴趣比率来看:有40%的用户对商品不感兴趣。
十一.二八理论分析
二八定律:在任何一组东西中,最重要的只占其中一小部分,约20%,其余80%尽管是多数,却是次要的,因此又称二八定律。
#二八理论和长尾理论
data_category = data_category[data_category['购买量']>0]
value_8 = data_category['购买量'].sum()*0.8
value_10 = data_category['购买量'].sum()
data_category = data_category.sort_values(by='购买量',ascending=False)
data_category['累计购买量'] = data_category['购买量'].cumsum()
data_category['分类'] = data_category['累计购买量'].map(lambda x:'前80%' if x<=value_8 else '后20%')
data_category.head()
输出:
image.png
data_category.groupby('分类')['分类'].count()/data_category['分类'].count()
输出:
分类
前80% 0.155727
后20% 0.844273
Name: 分类, dtype: float64
图表显示:前80%销量有15%左右的商品品类承包,接近二八原则。但我们也看出有15%的销量由85%的商品品类提供。
对于传统零售行业,因为成本高,因此只能局限于这前15%的商品提供利润;
对于电子商务,空间成本吉减少乃至为0,使后85%的商品也可以销售出去,因此将长尾部分的商品优化推荐好,能够给企业带来更大的收益。
十二.用户价值度RFM模型分析
RFM的含义:
- R(Recency):客户最近一次交易时间的间隔。R值越大,表示客户交易发生的日期越久,反之则表示客户交易发生的日期越近。
- F(Frequency):客户在最近一段时间内交易的次数。F值越大,表示客户交易越频繁,反之则表示客户交易不够活跃。
- M(Monetary):客户在最近一段时间内交易的金额。M值越大,表示客户价值越高,反之则表示客户价值越低。
RFM分析就是根据客户活跃程度和交易金额的贡献,进行客户价值细分的一种方法。
from datetime import datetime
datenow=datetime(2014,12,20)
#每位用户最近购买时间
recent_buy_time = data_user[data_user.behavior_type==4].groupby('user_id').date.apply(lambda x: datetime(2014,12,20)-x.sort_values().iloc[-1]).reset_index().rename(columns={'date':'recent'})
recent_buy_time.recent = recent_buy_time.recent.map(lambda x:x.days)
#每个用户消费频率
buy_freq=data_user[data_user.behavior_type==4].groupby('user_id').date.count().reset_index().rename(columns={'date':'freq'})
rfm=pd.merge(recent_buy_time,buy_freq,left_on='user_id',right_on='user_id',how='outer')
#将各维度分成两个程度,分数越高越好
rfm['recent_value']=pd.qcut(rfm.recent,2,labels=['2','1'])
rfm['freq_value']=pd.qcut(rfm.freq,2,labels=['1','2'])
rfm['rfm']=rfm['recent_value'].str.cat(rfm['freq_value'])
rfm.head()
输出:
image.png
表格显示:因为本数据集没有提供消费金额,因此只能R和F进行用户价值分析,通过RF用户价值分析,对于22用户,为重点用户需要关注;对于21这类忠诚度高而购买能力不足的,可以可以适当给点折扣或捆绑销售来增加用户的购买频率。对于12这类忠诚度不高而购买能力强的,需要关注他们的购物习性做精准化营销。