本文整理了客户终身价值(CLV或者CLTV)的相关概念,并对一家英国线上零售公司的一年交易数据进行分析,计算该公司所有客户的CLV并且建立回归预测模型。
用户生命周期价值Customer Lifetime value(缩写是CLV 或者CLTV), 也有称为Lifetime Value(LTV),值得是在客户整个生命周期中企业能获得的总价值。
多数情况下二者没有区别,比较模糊的情况下是:LTV不包括成本,而CLV是扣掉成本后的利润。
比如在互联网行业、APP、移动广告等业务中,使用的公式是:
LTV=LT(活跃天数)*ARPU(用户每次活跃产生的价值)
同时LTV还会结合CAC(获客成本Customer acquisition cost)一起分析,CAC公式如下:
CAC=总市场花费/对应花费带来的总新用户数
可见在这个场景中LTV是计算用户支出的总金额(不包括成本)。
比如这篇文章认为LTV是总收入,而CLV是利润(去掉成本), 并且使用具体的例子解释。
另外一篇文章中的CLV计算则是用的总收入。
比如一个客户每年都在会在一家商店里买东西,每个月花200元,一共有10年时间在这家店消费。那么对于这家商店而言,这个客户的终身价值就是他在店里一共消费的金额,即200*12*10=24000元
。
在实际商业分析中,仅仅分析一个客户是没有意义的,一般是要去计算整个企业、或者不同产品、地区的CLV。由上面单个用户的计算过成,可以推导出:
客户终身价值(CLV)=客户价值(Customer Value) * 平均客户生命周期(Average Customer Lifespan)
其中,
客户价值(Customer Value)=平均支付金额(Average purchase value)*平均支付次数(Average purchase frequency)
客户的生命周期比较难预估,尤其是新的企业,可能没有足够的时间去观察平均的客户生命周期。
**客户生命周期(Customer Lifetime)**=1/Churn Rate
其中,
就是前面提到过的公式,常用于游戏、APP等互联网业务数据分析中:
CLV=LT(活跃天数)*ARPU(用户每次活跃产生的价值)
这种方法根据企业过去的毛利润来计算客户的生命周期价值,很简单直接。
因为业务增长是波动变化的,客户的支付总金额不可能一成不变,客户数量也在不断变化,还要考虑到通货膨胀的影响,传统的CLV计算公式为:
更多的计算方法可以参考这篇文章
这里简单介绍两种方法。
客户每年支付总金额*客户关系时长-总获客/服务成本
直接根据经验或者历史数据去预估各项数据,比如:
CLV=500*5-50-10*5=2500-100=2400(元)
现存客户CLV预测模型,根据历史数据对未来的一个时间进行预测,可以使用近6个月或者过去三年的数据进行数据建模,求出下面这个拟合公式的各项参数:
数据集包含一家在英国注册的在线零售公司于 01/12/2010 和 09/12/2011 之间发生的所有交易。该公司主要销售各种场合的礼品,公司的许多客户都是批发商。
数据集一共包含8列:
#导入包
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
import datetime as dt
import numpy as np
#数据读取
data=pd.read_excel('Online Retail.xlsx', parse_dates=['InvoiceDate'])
#查看数据
data.head()
# 查看数据分布
data.describe()
数据集中的数量Quantity和价格中包含异常的负数,应是属于取消订单,但这里先当作异常值直接删除。
#filter
data = data[(data['Quantity']>0)&(data['UnitPrice']>0)]
data.describe()
# 查看缺失情况
data.isnull().sum()
#删除缺失值
data=data.dropna()
#检查结果
data.isnull().sum()
#Calulate total purchase
data['TotalPurchase'] = data['Quantity'] * data['UnitPrice']
#删除重复数据
filtered_data=data[['Country','CustomerID']].drop_duplicates()
#查看前十个最多客户的国家
filtered_data.Country.value_counts()[:10].plot(kind='bar')
uk_data=data[data.Country=='United Kingdom']
uk_data.info()
#选取需要的数据列
uk_data=uk_data[['CustomerID','InvoiceDate','InvoiceNo','Quantity','UnitPrice','TotalPurchase']]
# 根据客户ID分组,分别计算出最近消费时间、总消费单数和总消费金额
uk_data_group=uk_data.groupby('CustomerID').agg({'InvoiceDate': lambda date: (date.max() - date.min()).days,
'InvoiceNo': lambda num: len(num),
'Quantity': lambda quant: quant.sum(),
'TotalPurchase': lambda price: price.sum()})
#重命名
uk_data_group.columns=['num_days','num_transactions','num_units','spent_money']
#查看结果
uk_data_group.head()
这里用到的计算公式是:
# Average Order Value
uk_data_group['avg_order_value']=uk_data_group['spent_money']/uk_data_group['num_transactions']
#purchase_frequency
purchase_frequency=sum(uk_data_group['num_transactions'])/uk_data_group.shape[0]
# Repeat Rate
repeat_rate=uk_data_group[uk_data_group.num_transactions > 1].shape[0]/uk_data_group.shape[0]
#Churn Rate
churn_rate=1-repeat_rate
利润率是常用的盈利比率。它代表总销售额的多少百分比作为收益获得。假设我们的业务在总销售额中有大约 5% 的利润。
uk_data_group['profit_margin']=uk_data_group['spent_money']*0.05
#查看结果
uk_data_group.head()
# Customer Value
uk_data_group['CLV']=(uk_data_group['avg_order_value']*purchase_frequency)/churn_rate
# Customer Lifetime Value
uk_data_group['cust_lifetime_value']=uk_data_group['CLV']*uk_data_group['profit_margin']
#提取年月
uk_data['month_yr'] = uk_data['InvoiceDate'].apply(lambda x: x.strftime('%b-%Y'))
#将数据转置
sale=uk_data.pivot_table(index=['CustomerID'],columns=['month_yr'],values='TotalPurchase',aggfunc='sum',fill_value=0).reset_index()
#计算每个客户的CLV
sale['CLV']=sale.iloc[:,2:].sum(axis=1)
#查看结果
sale.head()
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LinearRegression
#取最近6个月的数据作为特征X,CLV是Y
X=sale[['Dec-2011','Nov-2011', 'Oct-2011','Sep-2011','Aug-2011','Jul-2011']]
y=sale[['CLV']]
#数据集切分
X_train, X_test, y_train, y_test = train_test_split(X, y,random_state=0)
#模型训练
linreg = LinearRegression()
linreg.fit(X_train, y_train)
#结果预测
y_pred = linreg.predict(X_test)
# 打印截距和系数
print(linreg.intercept_)
print(linreg.coef_)
#模型评估
from sklearn import metrics
print("R-Square:",metrics.r2_score(y_test, y_pred))
print("MAE:",metrics.mean_absolute_error(y_test,y_pred))
print("MSE",metrics.mean_squared_error(y_test, y_pred))
print("RMSE:",np.sqrt(metrics.mean_squared_error(y_test, y_pred)))
R平方介于 0-1 之间,越接近 1,回归拟合效果越好,一般认为 超过 0.8 的模型拟合优度比较高。
该模型的R平方为0.85,因此该模型的拟合效果比较高。