3. 实体解析基础流程
实体解析(Entity Resolution, ER)是将来自一个或多个数据源中描述同一现实世界实体的记录识别并合并的过程。其核心流程可归纳为四个阶段:数据预处理、属性相似度计算、实体匹配、聚类与合并。每个阶段解决特定的数据质量问题,并为下一阶段提供输入。
3.1 数据预处理
原始数据通常包含噪声、缺失值、格式不一致等问题。预处理的目标是清洗和标准化数据,为后续相似度计算提供干净、一致的输入。
核心任务:
- 字段抽取与分割:将复合字段拆分为原子属性(如将“张三,北京”拆分为姓名和城市)。
- 标准化:统一格式(日期统一为 YYYY-MM-DD,电话号码统一为 E.164 格式)。
- 缺失值处理:标记或填充缺失值,避免影响相似度计算。
- 噪声过滤:去除明显错误或异常值(如年龄为 999)。
- 数据分块(Blocking):通过分块键(如姓氏首字母、邮政编码)将数据划分为较小的候选块,减少后续匹配的计算量。
| 预处理步骤 | 输入示例 | 输出示例 | 常用技术 |
|---|---|---|---|
| 字段分割 | "张三,北京" | 姓名: "张三", 城市: "北京" | 正则表达式、分隔符解析 |
| 日期标准化 | "2024/1/5"、"05-01-2024" | "2024-01-05" | 日期解析库、模板匹配 |
| 缺失值标记 | 邮箱: "" | 邮箱: NULL | 空值检测、占位符替换 |
| 数据分块 | 全量 1000 万条记录 | 按姓氏首字母分块,每块约 50 万条 | 哈希分块、排序邻居分块 |
3.2 属性相似度计算
在预处理后的记录对上,计算各属性的相似度得分。不同数据类型需要不同的相似度算法。
- 字符串相似度:用于姓名、地址、标题等文本属性。
- 编辑距离(Levenshtein):计算将一个字符串转换为另一个所需的最少编辑操作次数。
- Jaro-Winkler:适用于短字符串,对前缀匹配给予更高权重。
- 余弦相似度(TF-IDF):适用于长文本,基于词频向量。
- 数值相似度:用于年龄、价格、坐标等数值属性。
- 绝对差归一化:
1 - |a - b| / (max - min)。 - 对数变换:处理指数级分布的数据。
- 绝对差归一化:
- 日期相似度:计算时间戳之间的绝对差,或使用层次化的日/月/年匹配。
- 集合相似度:用于标签、关键词等多值属性,常用 Jaccard 系数。
实践建议: 不要对所有属性使用同一算法。例如,姓名更适合 Jaro-Winkler,而地址更适合编辑距离或基于地理编码的相似度。为每个属性独立配置相似度函数和权重。
3.3 实体匹配
基于属性相似度得分,判断两条记录是否指向同一实体。匹配阶段通常分为两步:候选对生成和匹配决策。
- 候选对生成:利用分块结果,仅对可能匹配的记录对计算相似度,避免全量笛卡尔积。
- 匹配决策:将各属性相似度加权求和,得到总相似度,并与阈值比较。
- 规则匹配:人工定义阈值和权重(如总相似度 > 0.85 判定为匹配)。
- 机器学习匹配:使用标注数据训练分类器(逻辑回归、随机森林、深度学习),自动学习最优权重和阈值。
- 概率匹配:基于 Fellegi-Sunter 模型,计算匹配与非匹配的概率比。
# 示例:基于加权规则的匹配决策(伪代码)
def is_match(record_a, record_b, weights, threshold):
total_score = 0.0
for attr, weight in weights.items():
sim = compute_similarity(attr, record_a[attr], record_b[attr])
total_score += weight * sim
return total_score >= threshold
3.4 聚类与合并
匹配阶段产生的是两两记录之间的匹配关系,但一个实体可能对应多条记录。聚类阶段将这些匹配关系聚合为实体簇,合并阶段将簇内记录融合为一条干净、完整的实体记录。
- 传递闭包聚类:如果 A 匹配 B,B 匹配 C,则 A、B、C 属于同一实体。这是最常用的方法,简单但可能因传递错误导致簇膨胀。
- 中心聚类:选择簇内代表性记录作为中心,其他记录与中心匹配则加入该簇。
- 层次聚类:自底向上合并相似度最高的簇,或自顶向下分裂。
注意: 传递闭包可能导致“连锁错误”——一个错误的匹配会将大量无关记录合并到同一实体。建议在聚类后增加人工审核或置信度阈值过滤。
合并策略:
| 策略 | 描述 | 适用场景 |
|---|---|---|
| 多数投票 | 选择簇内出现频率最高的值 | 离散属性(性别、国家) |
| 最长/最短值 | 选择最完整或最简洁的值 | 地址、公司名称 |
| 置信度加权 | 选择数据源可信度最高的值 | 多源数据融合 |
| 保留所有值 | 将冲突值作为多值属性保留 | 需要保留历史记录的场景 |
3.5 流程总结与关键指标
实体解析流程并非严格的线性流水线,实际工程中常需要迭代优化。例如,匹配结果可以反馈回预处理阶段调整分块策略,或用于重新训练匹配模型。
| 阶段 | 输入 | 输出 | 关键质量指标 |
|---|---|---|---|
| 数据预处理 | 原始记录 | 标准化记录 + 分块索引 | 分块缩减率、数据完整率 |
| 属性相似度计算 | 标准化记录对 | 相似度向量 | 计算耗时、相似度分布 |
| 实体匹配 | 相似度向量 | 匹配对集合 | 精确率、召回率、F1 值 |
| 聚类与合并 | 匹配对集合 | 实体簇 + 融合记录 | 簇纯度、合并冲突率 |
工程要点: 在 Kafka 图谱构建场景中,实体解析流程需要设计为可增量执行的流式管道。预处理和相似度计算应支持无状态并行,聚类与合并则需要维护实体状态存储(如 RocksDB 或内存状态表),以支持实时记录到达时的增量聚类。