python数据分析与数据运营---第五章RFM实战案例

5.7案例:基于RFM的精细化用户管理

案例背景:在用户2015-2018年订单数据的基础上,对用户进行分群,总结每个组用户特征,以便于精细化运营,制定定制化和差异性的营销和关怀;

分析思路:基于RFM对用户进行分群,将三个维度分别作三个区间的离散化

import time
import numpy as np
import pandas as pd
from sklearn.ensemble import RandomForestClassifier
from pyecharts.charts import Bar3D
import pyecharts.options as opts

sheet_names = ["2015","2016","2017","2018","会员等级"]
sheet_datas = [pd.read_excel(r"D:\data_analysis_and_data_operation_with_python\python_book_v2\chapter5\sales.xlsx",sheet_name=i) for i in sheet_names]

#查看各个表是否存在缺失值
#for i in sheet_datas:
#    print(i.info())
for each_name,each_data in zip(sheet_names,sheet_datas):
    print("[data summary for {0:=^50}]".format(each_name))
    print("Overview:","\n",each_data.head())
    print("DESC:","\n",each_data.describe())
    print("NA records",each_data.isnull().any(axis=1).sum())
    
#数据均可以读取,无格式错误。缺失值总共只有一个,可以直接删除,其次订单金额分布极不均衡,根据业务背景,极大值产生是合理的(有贵重商品),其次金额小于1的订单,没有实际意义;
#处理缺失值和删除订单金额小于1的数据
for ind,each_data in enumerate(sheet_datas[:-1]):
    sheet_datas[ind] = each_data.dropna()
    sheet_datas[ind] = each_data[each_data["订单金额"]>1]
    #便于计算,最近一购买时间间隔
    sheet_datas[ind]["max_years_date"] = each_data["提交日期"].max()
    
#将年份数据进行纵向合并
data_merge = pd.concat(sheet_datas[:-1],axis=0)
#获取购买时间与年末的差值(最近一次购买),获取购买年份
data_merge["date_interval"] = data_merge["max_years_date"] - data_merge["提交日期"]
data_merge["year"] = data_merge["提交日期"].dt.year
#date_interval时间戳转化为数字
data_merge["date_interval"] = data_merge["date_interval"].apply(lambda x:x.days)
#提取“购买金额”,“购买次数”,“最近一次购买”时间字段,有两种方法,数据透视表以及groupby
#rfm_gb = pd.pivot_table(data_merge,index=["year","会员ID"],values=["订单号","订单金额","date_interval"],aggfunc=
#                     {"订单号":"count","订单金额":"sum","date_interval":"min"}).reset_index()
rfm_gb = data_merge.groupby(["year","会员ID"],as_index=False).agg({
        "date_interval":"min",
        "提交日期":"count",
        "订单金额":"sum"})
rfm_gb.columns=["year","会员ID","r","f","m"]
#查看属性分布
rfm_gb[["r","f","m"]].describe()
  r f m
count 148591 148591 148591
mean 165.524043 1.365002 1323.741329
std 101.988472 2.626953 3753.906883
min 0 1 1.5
25% 79 1 69
50% 156 1 189
75% 255 1 1199
max 365 130 206251.8

数据解读,最近一次购买时间分布较为均匀,购买频率大部分用户为一次,主要是因为行业属性(大家电)原因,用户一年购买一次较为普遍,那么最近一次购买时间分布均为也是此原因,可以认为家电购买时间随机分布;(个人感觉将最近一次购买时间作为重要指标不合适)

#临界点划分,r和m以四分位点划分即可,f则以[0,2,5,130]进行划分;
#定义区间边界,注意最小值,python进行区间分割时,是左开右闭区间
r_bins = [-1,79,255,365]
f_bins = [0,2,5,130]
m_bins = [-1,69,1199,206252]
#确定rfm因子权重,基于会员等级给予权重
rfm_merge = pd.merge(rfm_gb,sheet_datas[-1],on="会员ID",how="inner")
clf = RandomForestClassifier()
clf = clf.fit(rfm_merge[["r","f","m"]],rfm_merge["会员等级"])
weights = clf.feature_importances_
#rfm分箱,并将分类属性转化为数值属性
rfm_gb["r_score"] = pd.cut(rfm_gb["r"],r_bins,labels = [i for i in range(len(r_bins)-1,0,-1)])
rfm_gb["f_score"] = pd.cut(rfm_gb["f"],f_bins,labels = [i+1 for i in range(len(f_bins)-1)])
rfm_gb["m_score"] = pd.cut(rfm_gb["m"],m_bins,labels = [i+1 for i in range(len(m_bins)-1)])
#计算RFM加权得分
rfm_gb = rfm_gb.apply(np.int32)
rfm_gb["rfm_score"] = rfm_gb["r_score"]*weights[0] + rfm_gb["f_score"]*weights[1]+rfm_gb["m_score"]*weights[2]
#计算RFM组合分群,
rfm_gb["r_score"] = rfm_gb["r_score"].astype(np.str)
rfm_gb["f_score"] = rfm_gb["f_score"].astype(np.str)
rfm_gb["m_score"] = rfm_gb["m_score"].astype(np.str)
rfm_gb["rfm_group"] = rfm_gb["r_score"].str.cat(rfm_gb["f_score"]).str.cat(rfm_gb["m_score"])
#保存数据文件
rfm_gb.to_excel(r"D:\data_analysis_and_data_operation_with_python\sales_rfm_score.xlsx")
#RFM图形展示,只展示年份,rfm分组,用户数量
display_data = rfm_gb.group_by(["rfm_group","year"],as_index=False)["会员ID"].count()
display_data.columns = ["rfm_group","year","number"]
display_data["rfm_group"] = display_data["rfm_group"].astype(np.int32)
#画图
bar3d = Bar3D(init_opts=opts.InitOpts(width="900px", height="600px"))
range_color = ["#313695","#4575b4","#74add1","#abd9e9","#e0f3f8","#ffffbf",
              "#fee090","#fdae61","#f46d43","#d73027","#a50026"]

bar3d.add(
        series_name="rfm分组结果",
        data = [d.tolist() for d in display_data.values]
        ).set_global_opts(
        visualmap_opts=opts.VisualMapOpts(
            max_=display_data["number"].max(),
            range_color=range_color,
        ))
bar3d.render(r"D:\data_analysis_and_data_operation_with_python\sales_rfm_score.html")


结果分析:

用户标签 用户数量占比 用户消费金额占比 运营思路
212 24.79% 5.58% 可发展的一般性群体,通过运营手段维持并提升其消费状态
211 12.80% 0.32% 可发展的低价值群体,通过运营手段提升其购买金额
312 12.55% 2.86% 有潜力的一般性群体,购买新近度高,单忠诚度一般,通过其最近购买的商品,推荐相关商品
112 11.34% 2.53% 可挽回的一般性群体,通过多种方式触达客户并挽回
213 11.02% 31.48% 可发展的高价值群体,发展重点是提高其购物频率
311 6.24% 0.16% 有潜力的低价值群体,可以通过分析其渠道,加大相应渠道的投入,引导客户复购
111 6.14% 0.16% 各个维度都比较差的群体,主要通过多种策略挽回客户(资源足够的情况下)
313 5.61% 16.57% 有潜力的高价值群体,发展重点是提高其购物频率
113 5.07% 14.19% 可挽回的高价值群体,可适当的进行人工介入
123 1.30% 4.80%
333 0.33% 4.53% 绝对忠诚的高价值各户,应为其提供相应的VIP服务
233 0.70% 9.21% 一般性的高价值客户,重点在于提升新近购买度
133 0.32% 4.66%
223 0.25% 1.33%
322 0.28% 0.09% 有潜力的普通群体,需要提升购买频次,和额度
323 0.25% 1.14%
332 0.02% 0.01%

总结:1,个人认为该案例数据不太实用RFM模型,因为数据北京是大家电行业,大型的家用电器一般属于耐用品,属于绝对的低频消费,因此在购买频次这个指标很难看出客户的价值,其次也很难通过运营提高购买频次;最近的购买时间也是如此,如果你购买的时间越短,反而不会再进行购买;是否可以根据产品的生命周期,提醒客户更新换代,并推出相应的以旧换新服务;

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章