淘宝用户行为分析
import pandas as pd
data=pd.read_csv("train_user.csv")
data
user_id | item_id | behavior_type | user_geohash | item_category | time | |
---|---|---|---|---|---|---|
0 | 98047837 | 232431562.0 | 1.0 | NaN | 4245.0 | 2014-12-06 02 |
1 | 97726136 | 383583590.0 | 1.0 | NaN | 5894.0 | 2014-12-09 20 |
2 | 98607707 | 64749712.0 | 1.0 | NaN | 2883.0 | 2014-12-18 11 |
3 | 98662432 | 320593836.0 | 1.0 | 96nn52n | 6562.0 | 2014-12-06 10 |
4 | 98145908 | 290208520.0 | 1.0 | NaN | 13926.0 | 2014-12-16 21 |
... | ... | ... | ... | ... | ... | ... |
1159667 rows × 6 columns
item_id:商品id
item_geohash:地理位置
item_category:品类ID
time:用户行为发生的时间
user_id:用户身份
behavior_type:用户行为类型(包含点击=1,收藏=2,加购物车=3,支付=4)
data.info()
<class 'pandas.core.frame.DataFrame'>
RangeIndex: 1159667 entries, 0 to 1159666
Data columns (total 6 columns):
# Column Non-Null Count Dtype
--- ------ -------------- -----
0 user_id 1159667 non-null int64
1 item_id 1159666 non-null float64
2 behavior_type 1159666 non-null float64
3 user_geohash 370241 non-null object
4 item_category 1159666 non-null float64
5 time 1159666 non-null object
dtypes: float64(3), int64(1), object(2)
memory usage: 53.1+ MB
data= data.drop(data[data.user_id==1].index)
数据预处理
缺失值处理
missing=data.isnull().sum()
data['user_geohash']
0 NaN
1 NaN
2 NaN
3 96nn52n
4 NaN
...
1159661 95amccn
1159662 NaN
1159663 NaN
1159664 NaN
1159665 969uc9r
Name: user_geohash, Length: 1159666, dtype: object
从上面的数据可以看出地理位置虽然有很多缺失值但是已经超过一半了不能进行数据的删除,同时,地理数据本身就已经加密,没有探究的意义,同时,针对淘宝数据,重复值也是不需要给予处理的,接下来进行数据的一致化处理
数据一致化处理
数据的一致化处理主要针对日期数据,主要是对日期和时间分开的进行分析,比如说哪个日期的销量特多啊,或者哪个时间段的用户量也特多啊
import re
data['date']=data.time.map(lambda x : re.compile(" ").split(x)[0])
data['hour']=data.time.map(lambda x : re.compile(" ").split(x)[1])
data
user_id | item_id | behavior_type | user_geohash | item_category | time | date | hour | |
---|---|---|---|---|---|---|---|---|
0 | 98047837 | 232431562.0 | 1.0 | NaN | 4245.0 | 2014-12-06 02 | 2014-12-06 | 02 |
1 | 97726136 | 383583590.0 | 1.0 | NaN | 5894.0 | 2014-12-09 20 | 2014-12-09 | 20 |
2 | 98607707 | 64749712.0 | 1.0 | NaN | 2883.0 | 2014-12-18 11 | 2014-12-18 | 11 |
3 | 98662432 | 320593836.0 | 1.0 | 96nn52n | 6562.0 | 2014-12-06 10 | 2014-12-06 | 10 |
4 | 98145908 | 290208520.0 | 1.0 | NaN | 13926.0 | 2014-12-16 21 | 2014-12-16 | 21 |
... | ... | ... | ... | ... | ... | ... | ... | ... |
1159666 rows × 8 columns
如果对日期进行分析需要查看是否是我们想要的datetime类型和int类型
data.dtypes
user_id int64
item_id float64
behavior_type float64
user_geohash object
item_category float64
time datetime64[ns]
date datetime64[ns]
hour object
dtype: object
可以看出并不是我们想要的datetime的类型,因此这里需要做一个转换,将日期函数转换成datetime
data['date']=pd.to_datetime(data['date'])
data['time']=pd.to_datetime(data['time'])
data['hour']=data['hour'].astype('int64')
data.dtypes
user_id int64
item_id float64
behavior_type float64
user_geohash object
item_category float64
time datetime64[ns]
date datetime64[ns]
hour int64
dtype: object
对缺失值和数据进行处理之后,需要对异常值也进行处理,从数据可以看出其实并不会说哪些数据是异常的,最后可能出现异常的可能是日期函数的hour不是24个小时,或者date是目前之后的数据。一般在查看异常值最常使用的函数就是describe(),但是由于本数据主要针对的就是日期函数所以可以先进行一个排序然后再看。
sort=data.sort_values(by='time',ascending=True)
从排序可以看出日期数据也并无异常,为了更好的进行分析,需要重新索引
data=sort.reset_index(drop=True)
data
user_id | item_id | behavior_type | user_geohash | item_category | time | date | hour | |
---|---|---|---|---|---|---|---|---|
0 | 115621707 | 356483847.0 | 1.0 | NaN | 3892.0 | 2014-11-18 00:00:00 | 2014-11-18 | 0 |
1 | 20643274 | 37304772.0 | 1.0 | NaN | 13230.0 | 2014-11-18 00:00:00 | 2014-11-18 | 0 |
2 | 120594609 | 401627479.0 | 1.0 | NaN | 13326.0 | 2014-11-18 00:00:00 | 2014-11-18 | 0 |
3 | 131534140 | 60463018.0 | 1.0 | NaN | 10392.0 | 2014-11-18 00:00:00 | 2014-11-18 | 0 |
4 | 71146691 | 195202339.0 | 1.0 | NaN | 3156.0 | 2014-11-18 00:00:00 | 2014-11-18 | 0 |
... | ... | ... | ... | ... | ... | ... | ... | ... |
1159666 rows × 8 columns
用户行为分析
日访问量分析
page_view:网站的是页面浏览量或者点击量,页面被刷新一次就计算一次
unique_visitor:访问您网站的一台电脑客户端为一个访客
page_view=data.groupby("date")['user_id'].count().reset_index().rename(columns={"user_id":"page_view"})
unique_visitor=data.groupby('date')['user_id'].apply(lambda x:x.drop_duplicates().count()).reset_index().rename(columns={'user_id':'unique_visitor'})
import matplotlib.pyplot as plt
fig,axes=plt.subplots(2,1,sharex=True)
page_view.plot(x='date',y="page_view",ax=axes[0])
unique_visitor.plot(x='date',y='unique_visitor',ax=axes[1])
plt.show()
我们的数据只从2014.11.18-2014.12.18 所以可以很明显的看到双十二的日访问量明显达到峰值,让我们来看看双十二这一天一共有多少用户参加和活跃度。
用户活跃度
total_people=len(data.user_id.unique())
xi=data[data['date']=='2014-12-12']
double_people=len(xi.user_id.unique())
activate=double_people/total_people
print(activate)
0.6722814498933902
通过本数据可以初步判断在双12这一天用户的活跃度为67.23%左右,接下来争对时间来看看小时的访问量分析
小时的访问量分析
pv_hour=data.groupby("hour")['user_id'].count().reset_index().rename(columns={"user_id":"pv_hour"})
uv_hour=data.groupby('hour')['user_id'].apply(lambda x:x.drop_duplicates().count()).reset_index().rename(columns={'user_id':'uv_hour'})
fig,axes=plt.subplots(2,1)
pv_hour.plot(x='hour',y='pv_hour',ax=axes[0])
axes[0].set_title("pv_hour")
uv_hour.plot(x='hour',y='uv_hour',ax=axes[1])
axes[1].set_title("uv_hour")
Text(0.5, 1.0, 'uv_hour')
从图中可以看出晚上六点开始一直到晚上21是淘宝用户点击的高峰期。分析完时间序列,接下来对用户的行为进行分析
用户行为分析
一般来说用户行为分析就是包含点击=1,收藏=2,加购物车=3,支付=4,一般来说对我们最后价值的就是最后支付了的用户
import seaborn as sns
data_user_buy=data[data.behavior_type==4].groupby('user_id')['behavior_type'].count()
sns.distplot(data_user_buy,kde=False)
plt.title('daily_user_buy')
Text(0.5, 1.0, 'daily_user_buy')
从图中可以看出,一般来说用户都是的购买量都是在1~10之间,接下来使用ARPPU这个指标来衡量一下用户的平均付费额度
data_use_buy1=data[data.behavior_type==4].groupby(['date','user_id'])['behavior_type'].count().reset_index().rename(columns={'behavior_type':'total'})
data_use_buy1.groupby('date').apply(lambda x:x.total.sum()/x.total.count()).plot()
plt.title('daily_ARPPU')
Text(0.5, 1.0, 'daily_ARPPU')
图表显示:平均每天消费都是在1-2次之间波动
data['operation']=1
data_use_buy2=data.groupby(['date','user_id','behavior_type'])['operation'].count().reset_index().rename(columns={'operation':'total'})
data_use_buy2.groupby('date').apply(lambda x:x[x.behavior_type==4].total.sum()/len(x.user_id.unique())).plot()
plt.title('daily_ARPU')
Text(0.5, 1.0, 'daily_ARPU')
data_use_buy2.groupby('date').apply(lambda x:x[x.behavior_type==4].total.count()/len(x.user_id.unique())).plot()
plt.title('daily_afford_rate')
Text(0.5, 1.0, 'daily_afford_rate')
data_user_buy3=data[data.behavior_type==4].groupby(['user_id','date','hour'])['operation'].sum().rename('buy_count')
sns.distplot(data_user_buy3)
print('大多数用户消费:{}次'.format(data_user_buy3.mode()[0]))
大多数用户消费:1次
复购情况分析
date_rebuy=data[data.behavior_type==4].groupby('user_id')['date'].apply(lambda x:len(x.unique())).rename('rebuy_count')
print('复购率:',round(date_rebuy[date_rebuy>=2].count()/date_rebuy.count(),4))
复购率: 0.4734
#所有复购时间间隔消费次数分布
data_day_buy=data[data.behavior_type==4].groupby(['user_id','date']).operation.count().reset_index()
data_user_buy4=data_day_buy.groupby('user_id').date.apply(lambda x:x.sort_values().diff(1).dropna())
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')
Text(0, 0.5, 'gap_count')
多数用户复购率为0.4693,消费次数随着消费时间间隔的增加而不断下降,在1-10天之内复购次数比较多,10天之后复购次数淘宝用户很少在进行复购,因此需要重视10天之内的淘宝用户复购行为,增加用户复购。不同用户平均复购时间呈正态分布,但是总体来看,呈现逐渐下降趋势。多数淘宝用户平均复购时间集中在1-5天时间间隔内。
漏斗流式分析
data_user_count=data.groupby(['behavior_type']).count()
data_user_count.head()
pv_all=data['user_id'].count()
print(pv_all)
1159666
#用户行为与商品种类关系分析
#不同用户行为类别的转化率
data_category=data[data.behavior_type!=2].groupby(['item_category','behavior_type']).operation.count().unstack(1).rename(columns={1:'点击量',3:'加入购物车量',4:'购买量'}).fillna(0)
data_category.head()
behavior_type | 点击量 | 加入购物车量 | 购买量 |
---|---|---|---|
item_category | |||
8.0 | 103.0 | 1.0 | 0.0 |
10.0 | 20.0 | 1.0 | 1.0 |
11.0 | 793.0 | 7.0 | 0.0 |
12.0 | 16.0 | 0.0 | 0.0 |
13.0 | 9.0 | 0.0 | 0.0 |
我们团队旨在建设并发布高质量的技术文章和技术社区去储备人才,输送人才,有对大数据人工智能感兴趣的朋友可以加我们的QQ群呀~(我们平时会推送一些免费的课程,每周都有技术分享会欢迎大家参与)
我们的技术社区的网址:https://discourse.qingxzd.com/