4、数据采集与清洗:数据来源、数据质量、缺失值处理、异常值处理、去重、时间窗口、数据版本管理

内容预测模型的精度上限,往往不取决于算法有多先进,而取决于输入数据的质量与治理水平。在模型搭建初期,数据工程师与算法工程师投入时间比例通常为 7:3,其中数据清洗与特征工程占据绝大部分工作量。本章围绕数据采集与清洗的七大核心议题展开:数据来源、数据质量、缺失值处理、异常值处理、去重、时间窗口与数据版本管理,帮助学员建立一套可落地、可追溯、可复用的数据治理框架。

数据采集与清洗工程链路 数据来源 业务库/日志/埋点 第三方API/外部数据 实时流/离线数仓 数据质量评估 完整性/一致性/准确性 及时性/唯一性 质量评分卡 清洗处理 缺失值/异常值/去重 时间窗口对齐 格式标准化 版本管理 数据快照 特征版本 回滚机制 时间窗口设计 滚动窗口(30/60/90天) | 事件窗口 | 日历窗口 特征时间点T | 标签时间点T+N | 避免未来信息泄漏 窗口长度敏感性分析 数据血缘与追溯 字段级血缘 | 表级依赖 | 任务调度依赖 清洗规则变更记录 | 数据质量监控看板 异常数据回溯定位 输出:高质量建模数据集 特征矩阵 + 标签 + 元数据 + 版本号

4.1 数据来源与采集策略

核心原理:内容预测模型的数据来源通常分为三类:第一方行为数据(用户点击、浏览时长、搜索记录、内容消费历史)、内容属性数据(标题、分类、标签、作者、发布时间、内容长度、多媒体类型)、以及外部增强数据(季节性日历、热点事件、竞品信息、天气等)。不同来源的数据在采集频率、格式规范、延迟容忍度上差异显著,需要分层设计采集管道。

数据源类型典型字段采集方式更新频率常见问题
业务数据库用户ID、内容ID、时间戳SQL抽取 / Binlog监听小时级 / 天级分库分表、主键冲突
埋点日志事件名、页面路径、设备信息日志采集Agent → Kafka实时 / 准实时日志丢失、字段缺失
内容管理系统标题、正文、标签、作者API拉取 / 定时同步天级内容下架、字段变更
第三方数据热搜榜、节假日、天气API调用 / 爬虫小时级接口限流、数据格式不稳定

操作流程:建议采用“离线批量 + 实时增量”双轨制。离线管道处理历史全量数据,用于模型训练;实时管道处理当日增量数据,用于特征更新和线上预测。采集过程中必须为每条记录添加 etl_time(抽取时间)和 source_system(来源系统)字段,便于后续追溯。

经验提醒:在采集阶段就应约定字段命名规范(snake_case)、时间格式统一为 UTC 毫秒时间戳、枚举值统一编码。否则后续清洗成本会指数级上升。

4.2 数据质量评估与监控

核心原理:数据质量不是事后补救,而是需要建立持续监控的量化指标体系。常用的五个维度包括:完整性(非空比例)、唯一性(重复率)、准确性(与真实值偏差)、一致性(跨表字段逻辑统一)、及时性(数据延迟时间)。建议为每个核心表建立质量评分卡,低于阈值的表自动触发告警。

质量评分卡示例:
表名: user_content_behavior
完整性: 0.97 (阈值≥0.95)
唯一性: 0.999 (阈值≥0.99)
准确性: 0.98 (抽样人工校验)
一致性: 0.96 (跨表join匹配率)
及时性: 延迟中位数 5min (阈值≤15min)
综合评分: 0.972 → 合格

判断方法:建议每天凌晨运行数据质量校验任务,输出质量报告并归档。当质量评分连续三天下降或低于阈值时,需要暂停模型训练任务,优先排查数据管道问题。

4.3 缺失值处理策略

核心原理:缺失值处理前必须先区分缺失机制:完全随机缺失(MCAR)、随机缺失(MAR)、非随机缺失(MNAR)。不同机制对应不同处理策略。例如,用户年龄字段缺失可能与用户注册时间有关(MAR),而付费金额缺失可能与系统故障有关(MNAR)。

缺失比例推荐策略适用场景注意事项
<5%直接删除 / 均值填充样本量充足删除前确认缺失非系统性
5%-20%中位数 / 众数 / 前向填充数值型 / 时序型前向填充需按时间排序
20%-50%模型预测填充(回归/树模型)有相关特征可用避免引入数据泄漏
>50%单独编码为“未知”类别类别特征保留缺失指示变量

实战场景:某内容平台预测文章阅读量时,发现“作者粉丝数”字段缺失率达 35%。分析发现缺失集中在近三个月新注册作者中,属于 MAR 机制。最终采用“注册时长 + 历史平均阅读量 + 作者领域”三特征构建 LightGBM 回归模型进行填充,填充后模型 AUC 提升 0.03。

风险提示:填充值本身也是信息,建议同时生成 is_missing 指示特征。切勿在训练集和测试集上使用不同的填充策略,必须将填充模型固化并版本化。

4.4 异常值检测与处理

核心原理:异常值检测需区分“真异常”(数据错误)与“假异常”(真实极端值)。例如,某篇文章阅读量突然从 1 万涨到 100 万,可能是刷量行为(真异常),也可能是被头部平台推荐(假异常)。检测方法包括:统计法(Z-Score、IQR)、距离法(DBSCAN)、树模型法(孤立森林)。

操作流程:

  1. 先绘制特征分布图(箱线图、直方图),人工判断异常阈值范围。
  2. 使用 IQR 方法标记初步异常点:Q1 - 3*IQR 和 Q3 + 3*IQR 为边界。
  3. 结合业务规则二次确认:例如阅读量不能超过粉丝数的 50 倍。
  4. 对确认的异常值执行处理:删除、截尾(Winsorize)、或单独标记。
案例拆解:某资讯 App 预测次日留存率时,发现“启动次数”字段存在大量 9999 的异常值。排查发现是 SDK 在特定机型上上报失败时默认写入 9999。处理方案:将 9999 视为缺失值,使用同用户前 7 天均值填充,并增加 is_sdk_error 特征。处理后模型 MAE 从 0.12 降至 0.09。

4.5 数据去重策略

核心原理:去重不仅是删除完全重复的记录,更重要的是处理“语义重复”。例如同一用户在同一篇文章上的多次曝光记录,或同一内容在不同渠道的重复采集。去重粒度分为:行级去重(完全相同)、键级去重(指定业务主键)、语义级去重(相似文本)。

判断方法:先定义业务主键,例如 user_id + content_id + event_time 作为唯一键。对于实时流数据,建议使用 Flink 的 KeyedProcessFunction 配合状态存储实现精确一次去重;对于离线数据,使用 Spark SQL 的 ROW_NUMBER() OVER (PARTITION BY ... ORDER BY etl_time DESC) 保留最新记录。

经验提醒:去重操作必须记录去重前后的行数变化,并写入数据质量报告。如果去重率超过 10%,需要检查上游采集逻辑是否存在重复发送问题。

4.6 时间窗口设计

核心原理:时间窗口决定了特征计算的时间范围,直接影响模型对“近期趋势”和“长期习惯”的捕捉能力。常见窗口类型包括:滚动窗口(最近 7/30/90 天)、事件窗口(距离上次操作的时间间隔)、日历窗口(自然周/月)。窗口设计的关键是避免未来信息泄漏——特征只能使用预测时间点 T 之前的数据。

窗口类型计算方式适用特征风险
滚动窗口固定天数聚合近30天阅读量均值窗口过长导致特征滞后
事件窗口距上次行为的时间差距上次登录小时数稀疏事件需特殊处理
衰减窗口时间衰减加权近期行为加权求和衰减系数需调参

实战场景:在内容推荐模型中,分别计算用户对某类内容在 1 天、7 天、30 天内的点击率,作为三个独立特征。实验发现 7 天窗口特征重要性最高,1 天窗口特征对突发新闻响应更快但噪声较大。最终采用多窗口拼接方式,模型 AUC 提升 0.025。

4.7 数据版本管理与回滚机制

核心原理:数据版本管理是模型可复现性的基石。当清洗逻辑变更、特征口径调整或上游数据修复时,必须能够回溯到历史某个版本的数据集。建议采用“三版本”策略:原始数据版本(Raw)、清洗后版本(Cleaned)、特征工程版本(Features)。

操作流程:

  1. 每次清洗任务运行时,生成数据快照并记录版本号(如 20240520_v3)。
  2. 版本信息存入元数据库,包含:清洗规则哈希值、输入数据版本、输出行数、质量评分。
  3. 模型训练时锁定特征版本,训练完成后将模型与数据版本绑定。
  4. 当线上效果下降时,可快速对比不同版本数据训练的模型表现。
风险提示:不要覆盖历史数据文件。建议使用 HDFS 或对象存储的不可变目录结构,例如 /data/cleaned/dt=2024-05-20/version=v3/。同时,清洗代码必须使用 Git 管理,确保代码版本与数据版本一一对应。

4.8 常见误区与总结复盘

常见误区:

  • 误区一:先建模再补数据。正确做法是先花 60% 时间做数据治理,否则后续返工成本更高。
  • 误区二:所有缺失值一律用均值填充。忽略了缺失机制差异,导致模型偏差。
  • 误区三:异常值直接删除。可能删除了真实的高价值样本(如爆款内容)。
  • 误区四:时间窗口随意设定。没有做敏感性分析,窗口过长导致特征无法反映近期变化。
  • 误区五:数据版本管理只记录日期,不记录清洗规则。导致无法复现实验结果。

总结复盘:数据采集与清洗是内容预测模型搭建中最耗时但回报率最高的环节。建议团队建立“数据质量日报 + 周度复盘”机制,将清洗规则沉淀为可配置的代码模块。每次模型迭代时,先确认数据版本未发生意外变更,再开始训练。最终目标是将数据治理从“救火式”转变为“预防式”,让模型始终建立在稳定、可信的数据地基之上。