客户价值分析的产出不是数,是一张「分堆名单」加每堆的处置办法。 数据只有一张订单流水,9308 行 4 个字段,覆盖 1200 个客户——没有客户表,画像得自己算。 四个项目走到最后一个:这一章的重点是把模型输出翻译成业务动作。
第 9 章连库、第 10 章读 Excel、第 11 章带图表模块,这一章做客户分群。 前面三章的产出都是数或图,这一章的产出一张名单——它要直接指导花钱。
一、老板要的三个答案
一家公司有一堆客户,不可能一样对待。老板要三个答案:谁最值钱、谁快走了、钱该花在谁身上。 这三个问题可以合成一句话:把客户分成几堆,每堆用不同的办法对待。 分堆这件事,最笨的办法是按消费额排名,前两成当重要客户。这个办法有两个硬伤。
它看不见「最近还来不来」。去年买了十万、今年一单没下的,照样排在前面。 它也看不见「来了几次」。一次买十万和十次各买一万,价值完全不同。
二、只有流水,没有客户表
数据是一张订单流水表,9308 行、4 个字段,覆盖 1200 个客户。
| 字段 | 含义 | 这次的情况 |
|---|---|---|
| 订单编号 | 每单一个号 | D000001 起 |
| 客户编号 | 谁下的单 | C0001 到 C1200 |
| 订单日期 | 下单那一天 | 2023-01 到 2025-06 |
| 订单金额 | 这一单多少钱 | 元,几百到几千 |
没有客户表,没有年龄性别,没有注册渠道。客户的画像得从流水里自己算出来。 这是真实项目最常见的形态:业务系统只记「谁在什么时候花了多少」,剩下的全靠分析。 所以第一步不是建模,是把流水按客户聚一遍——聚完之后才有「客户」这个单位。
三、RFM:三个字母顶一张画像
R 是最近一次消费距今多少天,F 是一共买了几次,M 是一共花了多少钱。 三样合起来,才勉强算一张客户画像:多久没来、来得多不多、花了多少。 算完三个值再用聚类分成几堆,最后给每堆起一个业务上说得通的名字。
命名那一步是人做的,不是算法做的。聚类只告诉你「这几个人像」,不会告诉你「他们是谁」。 这句话听着简单,做错的人不少:直接把 0 号簇叫「重要客户」,其实 0 号可能正好是最差的一堆。
四、四步流程
| 步骤 | 做什么 | 产出 |
|---|---|---|
| 一 | 抽数、洗净、看分布 | 一份能算的流水 |
| 二 | 按客户聚出 R、F、M | 每客户一行 |
| 三 | 标准化加聚类分堆 | 每客户一个堆号 |
| 四 | 给每堆起名、给策略 | 名单加处置办法 |
四步里第三步最容易出错:三个值的量纲差太远,不标准化,聚类只会看金额。 第 12.5 节会把这件事摊开算一遍:R 的标准差 182,M 的标准差 6750,差三十多倍。
五、项目准备:观察日要写死
要装 pandas、scikit-learn、matplotlib。本机这套都在。
pip install pandas scikit-learn matplotlib
本机 pandas 3.1.0、scikit-learn 1.9.1,够用。
观察日必须写死。R 是「距今多少天」,今天是哪天得固定,否则明天跑出来的数全变。
这次定在 2025-06-30,正好是数据最后一天之后。写成 pd.Timestamp.today() 是个坏习惯。
数据原样落成 订单流水.csv,脏的地方留着:负金额 6 条、客户编号空 4 条、重复 2 条。
六、动手 Demo:项目概述、效果与准备
这一节不建模:把三个问题、数据结构、RFM 三个字母、四步流程交代清楚。 最后把 9308 行流水原样落成 CSV,脏数据也一起留着。
import pandas as pd
df = pd.read_csv("订单流水.csv")
print("形状 %s" % (df.shape,))
print("客户数 %d" % df["客户编号"].nunique())
print("日期 %s 到 %s"
% (df["订单日期"].min(), df["订单日期"].max()))
OBS = pd.Timestamp("2025-06-30")
print("观察日 %s" % OBS.date())
print("坏数据:负金额 %d,客户空 %d,重复 %d"
% ((df["订单金额"] < 0).sum(), df["客户编号"].isnull().sum(),
df.duplicated().sum()))
实跑输出:
--------------------------------------------------------------------
项目概述、效果与准备
--------------------------------------------------------------------
① 这个项目要回答什么
--------------------------------------------------------------------
一家公司有一堆客户,不可能一样对待。老板要三个答案:
谁是最值钱的客户、谁快要走了、钱该花在谁身上。
这三个问题用一句话概括:把客户分成几堆,每堆用不同的办法对待。
这就是客户价值分析。它的产出不是一个数,是一张「分堆名单」加每堆的处置办法。
② 数据长什么样
--------------------------------------------------------------------
一张订单流水表,9308 行、4 个字段,覆盖 1200 个客户。
| 字段 | 含义 | 这次的情况 |
|---|---|---|
| 订单编号 | 每单一个号 | D000001 起 |
| 客户编号 | 谁下的单 | C0001 到 C1200 |
| 订单日期 | 下单那一天 | 2023-01-01 到 2025-06 |
| 订单金额 | 这一单多少钱 | 元,几十到几千 |
注意:这里没有「客户表」,只有流水。客户的画像得从流水里自己算出来。
这是真实项目最常见的形态:业务系统只记「谁在什么时候花了多少」,剩下的全靠分析。
! 数据是造的:四类客户各有各的下单节奏,忠诚客户买得多买得勤,流失客户很久没来。
③ RFM:三个字母代替一张画像
--------------------------------------------------------------------
R 是最近一次消费距今多少天,F 是一共买了几次,M 是一共花了多少钱。
三个维度合起来,才勉强算一张客户画像。只看 M,会把「一次买很多但再也不来」的人当宝贝。
算完三个值之后用聚类分成几堆,再给每堆起个业务上说得通的名字。
命名那一步是人做的,不是算法做的。聚类只告诉你「这几个人像」,不会告诉你「他们是谁」。
④ 四步流程
--------------------------------------------------------------------
| 步骤 | 做什么 | 产出 |
|---|---|---|
| 一 | 抽数、洗净、看分布 | 一份能算的流水 |
| 二 | 按客户聚出 R、F、M | 每客户一行 |
| 三 | 标准化 + 聚类分堆 | 每客户一个堆号 |
| 四 | 给每堆起名、给策略 | 一张名单加处置办法 |
四步里第三步最容易出错:三个值的量纲差太远,不标准化,聚类只会看金额。
第 12.5 节会把这件事摊开算一遍。
⑤ 项目准备
--------------------------------------------------------------------
[本沙箱已装齐]
| pip install pandas scikit-learn matplotlib
numpy 是 pandas 的依赖,会一起装上。
本机 pandas 3.1.0、scikit-learn 1.9.1。
观察日要写死:R 是「距今多少天」,今天是哪天必须固定,否则明天跑出来的数就变了。
这次把观察日定在 2025-06-30,和数据最后一天对齐。
⑥ 把流水落成 CSV
--------------------------------------------------------------------
原样存成 订单流水.csv,9308 行 4 列,UTF-8 带 BOM。
脏的地方留在里面:负金额 6 条、客户编号空 4 条、完全重复 2 条。
! 不提前洗。下一篇专门讲怎么查、怎么洗。
nunique() 数的是「不同值的个数」,比 len() 少掉重复——数客户必须用它。
观察日写成字符串再转 Timestamp,比直接写 (2025, 6, 30) 好读,也不容易记错顺序。
这一节故意不洗数据。isnull().sum() 和 duplicated().sum() 只是先看一眼,下一篇才动手。
30 秒实验
- 把观察日改成 2025-03-31,想想 R 会整体变大还是变小。
- 把
nunique()换成len(),看那个数差多少,想想差在哪。 - 想一想:如果公司还有一张客户表(年龄、城市、注册渠道),第一步该做什么?
常见误区
- 只用消费额排名:看不见「最近还来不来」和「来了几次」,会把睡着的客户当宝贝。
- 把观察日写成今天:明天跑出来的结果和今天不一样,没人敢拿它做决策。
- 以为有客户表:这份数据只有流水,客户画像是从流水里聚出来的。
- 直接给簇号贴业务名:0 号簇是什么,得看均值表,不能想当然。
自测三问(点开对答案)
1. 为什么「按消费额排名」不够? —— 它看不见最近是否还来、也看不见来了几次。一次买很多但再也不来的客户,照样排前面。 2. 观察日为什么必须写死? —— R 是距今多少天,基准日一变,全表 R 都变。写死才能复现,别人才敢用。 3. 这一章和前面三个项目最大的不同是什么? —— 产出不是数或图,是一张分堆名单加每堆的处置办法,要直接指导花钱。问题清楚了。下一篇把 RFM 三个字母和聚类这两件事讲透,尤其是标准化那个坑。
- ☐ (本篇完,下一篇 12.2 分析方法:RFM 模型与聚类)