news 2026/7/23 8:07:27

AI 智能营销数据分析:RFM + 聚类 + 推荐的全链路方案

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
AI 智能营销数据分析:RFM + 聚类 + 推荐的全链路方案

AI 智能营销数据分析:RFM + 聚类 + 推荐的全链路方案

一、营销数据分析的三个阶段

做营销数据分析久了,你会发现大部分公司的营销分析都停留在"第一阶段"——算算 ROI、看看转化率、出个周报。但实际上,真正能驱动业务增长的营销分析应该走完三个阶段:

  1. 用户分层:谁是你的高价值用户?谁快流失了?谁还有挖掘潜力?
  2. 精准推荐:知道用户是谁之后,给他推什么产品/活动最有效?
  3. 效果闭环:推完之后,用户有没有转化?没转化的原因是什么?

这篇文章就把这三个阶段串起来,用一套"RFM + 聚类 + 推荐"的全链路方案,从数据到决策到执行,一气呵成。

为什么大多数公司的营销分析都停留在第一阶段?原因不是技术能力不够,而是组织惯性。用户分层需要数据分析师跑 SQL,精准推荐需要算法工程师训练模型,效果闭环需要产品和运营配合设计 AB 测试。三个阶段涉及三个角色,任何一个环节掉链子,整个链路就断了。RFM + 聚类的优势在于:数据分析师或熟练的 Python 工程师一个人就能跑通全流程,不需要专门的算法团队——K-Means 够用了。跑通一次链路后,用数据结果去说服业务方配合做 AB 测试,阻力会小得多。先用轻量方案快速出成果,再用成果推动深度合作,这是在资源有限情况下的最佳实践。

二、RFM 模型:经典但不过时

RFM(Recency 最近一次消费、Frequency 消费频率、Monetary 消费金额)是用户分层的经典模型,简单好用,解释性极强。

为什么 30 年前的 RFM 模型到今天仍然管用?因为这三个维度直接对应了消费行为的三个底层驱动力:Recency 衡量用户的"记忆热度"(刚买过的人最容易再次购买),Frequency 衡量"习惯程度"(买得越多越容易接着买),Monetary 衡量"投入程度"(花得越多越不会轻易离开)。这三件事不随行业变化,电商、游戏、SaaS、金融都适用。RFM 的另一个巨大优势是"可解释"——你对着老板说"这是一个 R=5, F=1, M=5 的用户",老板可能听不懂;但你说"这个用户最近花了大钱但只买了一次",老板立刻知道该怎么运营。**

import pandas as pd import numpy as np from datetime import datetime, timedelta from sklearn.preprocessing import StandardScaler from sklearn.cluster import KMeans import warnings warnings.filterwarnings('ignore') # ==================== 第1步:计算RFM指标 ==================== # 模拟交易数据 np.random.seed(42) n_users = 1000 transactions = pd.DataFrame({ 'user_id': np.random.choice([f'U{i:04d}' for i in range(1, n_users + 1)], 5000), 'order_date': pd.to_datetime([ datetime(2026, 7, 1) - timedelta(days=np.random.randint(0, 365)) for _ in range(5000) ]), 'order_amount': np.random.lognormal(mean=4.0, sigma=0.8, size=5000), # 对数正态分布模拟交易金额 'order_id': [f'ORD{i:06d}' for i in range(1, 5001)] }) # 设置分析基准日期(比如今天是2026-07-23) REFERENCE_DATE = datetime(2026, 7, 23) # 计算每个用户的RFM指标 rfm = transactions.groupby('user_id').agg( # Recency: 最近一次购买距离今天的天数(越小越好) recency=('order_date', lambda x: (REFERENCE_DATE - x.max()).days), # Frequency: 购买次数(越多越好) frequency=('order_id', 'count'), # Monetary: 总消费金额(越多越好) monetary=('order_amount', 'sum') ).reset_index() print("=== RFM指标统计 ===") print(rfm.describe()) # ---- 给RFM打分(1-5分制) ---- # 按分位数将每个指标分为5个等级 def rfm_score(series: pd.Series, ascending: bool = True) -> pd.Series: """ 将连续值映射到1-5的评分 参数: series: 需要评分的序列 ascending: True表示值越小分数越高(适用于Recency), False表示值越大分数越高(适用于Frequency和Monetary) """ labels = [5, 4, 3, 2, 1] if ascending else [1, 2, 3, 4, 5] return pd.qcut(series, q=5, labels=labels, duplicates='drop').astype(int) rfm['R_score'] = rfm_score(rfm['recency'], ascending=True) # R: 越近分数越高 rfm['F_score'] = rfm_score(rfm['frequency'], ascending=False) # F: 越多分数越高 rfm['M_score'] = rfm_score(rfm['monetary'], ascending=False) # M: 越多分数越高 # RFM总分 rfm['RFM_score'] = rfm['R_score'] + rfm['F_score'] + rfm['M_score'] print(f"\n=== RFM评分分布 ===") print(rfm[['R_score', 'F_score', 'M_score', 'RFM_score']].describe())

三、K-Means 聚类:从 RFM 到用户画像

RFM 打分是一种粗分类,想得到更精细的用户画像,需要对 RFM 的原始值做聚类:

为什么不能直接用 RFM 打分,还要做 K-Means?RFM 打分的本质是"等分"——把用户按 R/F/M 三个维度分别切成 5 等份,然后组合出 125 种可能(5×5×5)。问题是:等分不反映数据的真实分布。如果 80% 的用户 Frequency=1(只买过一次),那你把"买过一次"的用户硬切成 5 组毫无意义。K-Means 的聚类是基于实际数据密度的——用户群在哪聚集,边界就在哪,不是人为硬分。另外,K-Means 前必须做 StandardScaler 标准化,原因是 recency(0-365 天)、frequency(1-50 次)、monetary(10-100000 元)这三个特征的量纲完全不同,如果不标准化,monetary 几乎会完全主导聚类结果,recency 和 frequency 的信息被淹没。这一点 90% 的新手会忽略,结果得出一个只有金额维度的分群。**

# ==================== 第2步:K-Means聚类 ==================== # 选择聚类特征:使用RFM原始值 cluster_features = rfm[['recency', 'frequency', 'monetary']].copy() # ---- 特征标准化(K-Means对尺度敏感) ---- scaler = StandardScaler() features_scaled = scaler.fit_transform(cluster_features) # ---- 确定最佳聚类数(手肘法) ---- # 计算不同K值下的SSE(误差平方和) sse_list = [] k_range = range(1, 11) for k in k_range: kmeans = KMeans(n_clusters=k, random_state=42, n_init=10) kmeans.fit(features_scaled) sse_list.append(kmeans.inertia_) # 找到手肘点(简化:选择SSE下降变缓的位置) # 实际项目中建议用轮廓系数(Silhouette Score)更严谨 # ---- 使用K=5进行聚类 ---- optimal_k = 5 kmeans = KMeans(n_clusters=optimal_k, random_state=42, n_init=10) rfm['cluster'] = kmeans.fit_predict(features_scaled) # ---- 分析每个聚类的特征,给分群命名 ---- cluster_profile = rfm.groupby('cluster').agg( avg_recency=('recency', 'mean'), avg_frequency=('frequency', 'mean'), avg_monetary=('monetary', 'mean'), user_count=('user_id', 'count'), avg_rfm_score=('RFM_score', 'mean') ).round(1) print("\n=== 聚类特征画像 ===") print(cluster_profile) # ---- 根据聚类特征自动打标签 ---- def label_cluster(row): """ 根据RFM均值给聚类打标签 判断逻辑: - 高Monetary + 高Frequency → 高价值用户 - 高Monetary + 低Frequency → 大单客户 - 低Monetary + 高Frequency → 活跃小客户 - 低Recency + 中低Frequency → 潜力用户(最近活跃但频次不高) - 高Recency + 低Frequency → 流失风险用户 """ r, f, m = row['avg_recency'], row['avg_frequency'], row['avg_monetary'] # 判断标准(相对于整体均值的比较) r_median = rfm['recency'].median() f_median = rfm['frequency'].median() m_median = rfm['monetary'].median() if m > m_median and f > f_median: return "高价值用户" elif m > m_median and f <= f_median: return "大单低频客户" elif m <= m_median and f > f_median: return "高频小单客户" elif r < r_median and f <= f_median: return "潜力新用户" else: return "流失风险用户" cluster_profile['segment_name'] = cluster_profile.apply(label_cluster, axis=1) # 将标签映射回用户表 segment_map = cluster_profile['segment_name'].to_dict() rfm['user_segment'] = rfm['cluster'].map(segment_map) print("\n=== 用户分群结果 ===") print(rfm['user_segment'].value_counts()) print(f"\n各分群人数占比:") for seg, count in rfm['user_segment'].value_counts().items(): print(f" {seg}: {count}人 ({count/len(rfm):.1%})")

四、个性化推荐:基于分群的协同过滤

有了用户分群之后,推荐就不再是盲目的了:

为什么分群推荐比全局统一推荐效果好得多?全局推荐的问题是"平均化"——对所有用户推一样的东西,结果是高价值用户觉得"太 low"、新用户觉得"太贵"、流失用户无感。分群推荐的核心逻辑是:同群用户有相似的消费能力和偏好。高价值用户群里的用户 A 买了某款高端产品,用户 B 很可能也会感兴趣——即使他们俩的历史行为完全不同。这就是"分群协同过滤"比"全局协同过滤"更精准的原因。更进一步,不同群的推送文案也该不同:高价值用户看到"为您臻选"会觉得被尊重,流失用户看到"好久不见,送你一张优惠券"才会点开。一句话总结:精准的秘密不在算法复杂度,而在"谁"收到"什么"的匹配度。

# ==================== 第3步:基于分群的推荐策略 ==================== class SegmentBasedRecommender: """ 基于用户分群的推荐引擎 根据不同用户群的特性,采用差异化的推荐策略 """ # 各分群的推荐策略 SEGMENT_STRATEGIES = { "高价值用户": { "priority": "vip_exclusive", # 优先推VIP专属/高客单价商品 "price_range": (200, 10000), # 价格区间 "discount_sensitivity": "low", # 对折扣不敏感,更关注品质 "channel": "push + sms", # 推送渠道 "message": "为您臻选的品质好物" # 文案风格 }, "大单低频客户": { "priority": "similar_upsell", # 推相似品类的高端款(升单) "price_range": (100, 5000), "discount_sensitivity": "medium", "channel": "sms + in_app", "message": "基于您的偏好,这些好物值得一试" }, "高频小单客户": { "priority": "bundle_deal", # 推组合套餐/凑单优惠 "price_range": (10, 200), "discount_sensitivity": "high", # 凑单敏感,适合推满减 "channel": "in_app + coupon", "message": "凑单满99减20,这些好物加购立减" }, "潜力新用户": { "priority": "new_user_bundle", # 推新人专享/入门爆款 "price_range": (10, 300), "discount_sensitivity": "high", "channel": "push + coupon", "message": "新人专属福利,首单立减30元" }, "流失风险用户": { "priority": "recall_coupon", # 推大额召回优惠券 "price_range": (10, 500), "discount_sensitivity": "very_high", "channel": "sms + push", "message": "好久不见,送你一张50元优惠券" }, } def get_strategy(self, user_segment: str) -> dict: """根据用户分群获取推荐策略""" return self.SEGMENT_STRATEGIES.get( user_segment, self.SEGMENT_STRATEGIES["潜力新用户"] # 默认策略 ) def generate_recommendations(self, user_id: str, user_segment: str, user_history: list, top_n: int = 5) -> list: """ 生成个性化推荐列表 参数: user_id: 用户ID user_segment: 用户分群标签 user_history: 用户历史购买商品ID列表 top_n: 推荐数量 """ strategy = self.get_strategy(user_segment) # 实际生产环境中,这里会调用协同过滤或内容推荐算法 # 简化示意: recommendations = [] priority = strategy['priority'] price_range = strategy['price_range'] # 根据策略筛选候选商品 # (实际会用向量检索或矩阵分解) # ... return { 'user_id': user_id, 'segment': user_segment, 'strategy': priority, 'message': strategy['message'], 'channel': strategy['channel'], 'candidates': recommendations # 推荐商品列表 } # ---- 使用示例 ---- recommender = SegmentBasedRecommender() # 为不同分群的用户生成推荐 test_users = [ ("U0001", "高价值用户"), ("U0500", "流失风险用户"), ("U0800", "潜力新用户"), ] print("\n=== 个性化推荐策略 ===") for uid, seg in test_users: result = recommender.generate_recommendations(uid, seg, user_history=[]) print(f"\n{uid} ({seg}):") print(f" 推荐策略: {result['strategy']}") print(f" 推送文案: {result['message']}") print(f" 推送渠道: {result['channel']}")

踩坑提醒

  • 坑1:RFM 基准日期选错导致用户分群全歪— 如果你用"今天"作为基准日期来计算 Recency,但你的交易数据只到 3 天前(数据延迟),那么所有用户的 Recency 都会多了 3 天。高价值用户可能因此被错分到流失风险群。基准日期应该是"数据的最新日期"而不是代码的执行日期。
  • 坑2:K-Means K 值拍脑袋选 5— 手肘法虽然简单,但很多数据集的肘点并不明显。真正的金标准是轮廓系数(Silhouette Score)和业务可解释性的折中。K=5 是一个经验值,但如果轮廓系数在 K=6 时明显更高,就应该用 K=6。
  • 坑3:聚类标签生成后不验标,直接推给运营— 自动打的标签(如"潜力新用户")跑出来后,必须人工抽样验标,确认标签和实际用户画像一致。否则运营按错误标签发了错误优惠券,效果为负还伤了用户体验。

五、总结

营销数据分析的"三段论"——用户分层、精准推荐、效果闭环——缺一不可。

  1. RFM + 聚类是用户分层的黄金组合。RFM 提供可解释的业务标签,K-Means 做精细化分群,两者结合比单一方法效果好几倍。
  2. 不同用户群要用不同的推荐策略。高价值用户推品质,流失用户推优惠券,新用户推爆款。千篇一律的推荐 = 没有推荐。
  3. 推荐必须有反馈闭环。AB 测试是标配,实验组和对照组的转化率差异,才是衡量推荐策略有没有用的唯一标准。
  4. 分群标签要定期更新。用户的行为模式会变,上个月的高价值用户这个月可能就流失了。建议至少每周做一次 RFM 重算。
  5. 不要只有标签,还要有画像。标签告诉你"用户属于哪个群",画像告诉你"这个群的用户喜欢什么",后者才是推荐的基础。

从"拍脑袋做营销"到"数据驱动做营销",这条路一旦走通,ROI 的提升是肉眼可见的。

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/7/23 8:06:52

AI生成数据可视化实战:从自然语言到交互式图表的完整技术路线

AI生成数据可视化实战&#xff1a;从自然语言到交互式图表的完整技术路线 数据可视化的三个核心层次 数据可视化是产品数据分析里"最耗时但价值最高"的环节。好的图表能让复杂数据变得直观&#xff0c;坏的图表会让用户困惑甚至误导决策。 我把AI辅助的数据可视化分为…

作者头像 李华
网站建设 2026/7/23 8:06:42

马鞍山120 平全屋智能报价

针对马鞍山120平方米的住宅打造全屋智能解决方案&#xff0c;采用华为鸿蒙智家全屋智能系统&#xff0c;我们可以提供一个概览性的报价参考。请注意&#xff0c;实际费用会根据具体需求、所选设备及服务内容有所差异。一、前装整套全屋鸿蒙智能方案对于新房装修或毛坯房改造&am…

作者头像 李华
网站建设 2026/7/23 8:00:22

提质增效再加速 | 东棠AI速创「填空式」短视频创作功能焕新上线!

当下线上获客竞争持续加剧&#xff0c;短视频已成为企业、商家引流获客的核心抓手。但多数用户仍面临脚本创作难、制作门槛高、内容试错成本高的困境&#xff0c;不少AI短视频创作工具仅停留在基础剪辑层面&#xff0c;与用户“低成本、高产出、易上手”的诉求存在差距。为贴合…

作者头像 李华