缺失值产生机制:MCAR、MAR、MNAR 原理与风控案例

在风控数据质量治理中,缺失值并非随机噪声,其背后往往隐藏着特定的数据生成逻辑。理解缺失值的产生机制,是选择正确填充策略、避免模型偏差的前提。本节将系统讲解三种缺失机制:完全随机缺失(MCAR)、随机缺失(MAR)和非随机缺失(MNAR),并结合风控场景给出典型案例。

三种缺失机制的核心定义

机制 英文全称 核心定义 缺失概率与数据关系
MCAR Missing Completely At Random 缺失完全独立于观测数据和未观测数据 缺失概率 = 常数,与任何变量无关
MAR Missing At Random 缺失依赖于已观测到的其他变量,但与缺失变量本身的值无关 缺失概率 = f(已观测变量),与缺失变量无关
MNAR Missing Not At Random 缺失依赖于缺失变量本身的值(即使控制了其他变量) 缺失概率 = f(缺失变量本身)
风控提示: 在信贷风控建模中,MNAR 是最危险但最常见的缺失机制。例如,高逾期风险的客户更可能“故意”不填写收入字段,导致缺失值本身成为风险信号。

MCAR:完全随机缺失

原理: 数据缺失完全是一个随机事件,与任何已知或未知的特征无关。缺失数据可以看作是完整数据集的一个简单随机子样本。

风控案例:

  • 系统故障: 某风控系统在 2024-03-15 14:00–14:05 期间因网络抖动,随机丢失了 0.3% 的申请记录中的“征信查询次数”字段。该故障与客户资质、申请时间(除该5分钟外)均无关。
  • 传输丢包: 第三方数据源在接口调用时,因网络拥塞随机丢弃了约 0.1% 的数据包,导致部分客户的“社保缴纳月数”字段缺失。

处理策略: 由于 MCAR 不会引入系统性偏差,可以直接删除缺失样本(若缺失率低),或使用均值/中位数填充。但风控场景中,MCAR 实际占比通常不足 5%。

MAR:随机缺失

原理: 缺失概率依赖于其他已观测到的变量,但与缺失变量本身的值无关。例如,高收入群体更倾向于完整填写收入信息,而低收入群体可能因隐私顾虑而跳过该字段。

风控案例:

  • 年龄与收入缺失: 在信贷申请数据中,年龄字段完整,但“月收入”字段缺失。分析发现,年龄 < 25 岁的申请人中,收入缺失率为 12%;年龄 ≥ 25 岁的申请人中,收入缺失率仅为 3%。缺失概率依赖于已观测的“年龄”变量,但与申请人真实的收入水平无关。
  • 学历与职业信息: 学历为“高中及以下”的申请人,其“单位性质”字段缺失率(18%)显著高于学历为“本科及以上”的申请人(5%)。缺失概率依赖于已观测的“学历”变量。

处理策略: 不能简单删除,否则会引入选择偏差。应使用基于已观测变量的模型进行填充,如回归插补、多重插补(MICE)或基于决策树的填充方法。

MNAR:非随机缺失

原理: 缺失概率直接依赖于缺失变量本身的值。这是最复杂、最难处理的缺失机制,因为缺失本身携带了信息。

风控案例:

  • 逾期天数缺失: 在贷后管理数据中,部分客户的“当前逾期天数”字段缺失。进一步分析发现,缺失的客户实际上已经逾期超过 90 天(处于核销流程中),系统因状态异常未正常记录该字段。缺失与否直接由“逾期天数”本身的值决定。
  • 收入隐瞒: 高风险客户(真实收入极低或不稳定)更倾向于不填写“月收入”字段,以避免被拒贷。缺失概率与收入水平本身呈负相关。
  • 征信查询次数: 多头借贷严重的客户(征信查询次数极高),其部分征信报告可能因机构限制而无法完整获取,导致“近3个月查询次数”字段缺失。
模型偏差警告: 在 MNAR 场景下,如果直接使用均值填充或删除缺失样本,会严重低估高风险客户的特征分布,导致风控模型对坏客户的识别能力大幅下降。此时,缺失值本身应作为一个重要的风险特征参与建模。

三种机制在风控中的识别与应对

实际风控数据中,三种机制往往混合存在。以下表格总结了识别方法和应对策略:

机制 识别方法 风控应对策略
MCAR 分组检验:将数据按缺失/非缺失分组,检验其他变量均值是否存在显著差异(t检验/卡方检验) 直接删除(缺失率 < 5%);均值/中位数填充
MAR 逻辑回归:以缺失标志为因变量,其他完整变量为自变量,检验回归系数显著性 多重插补(MICE);基于模型的回归插补;保留缺失标志作为特征
MNAR 敏感性分析:假设不同的缺失机制,评估模型结果稳定性;领域专家判断 将缺失值编码为独立类别;使用 Heckman 选择模型;构建缺失指示变量作为特征

缺失机制与风控模型偏差的关系

缺失机制 → 风控模型偏差路径图 MCAR 完全随机缺失 MAR 随机缺失 MNAR 非随机缺失 无系统性偏差 选择偏差 严重信息偏差 模型无偏,效率略降 参数估计有偏 模型失效,风险低估 风控建议:MNAR 场景下,缺失值应作为独立风险特征参与建模,而非简单填充

Python 实战:模拟三种缺失机制

以下代码演示如何在风控模拟数据中生成 MCAR、MAR 和 MNAR 三种缺失模式,帮助理解其生成逻辑:

import pandas as pd
import numpy as np

# 生成模拟风控数据
np.random.seed(42)
n = 10000
data = pd.DataFrame({
    'age': np.random.randint(22, 60, n),
    'income': np.random.normal(15000, 5000, n).clip(3000, 50000),
    'credit_score': np.random.randint(300, 850, n),
    'overdue_days': np.random.poisson(5, n)  # 逾期天数
})

# 1. MCAR:完全随机缺失(系统故障)
data_mcar = data.copy()
mask_mcar = np.random.random(n) < 0.05  # 5% 随机缺失
data_mcar.loc[mask_mcar, 'credit_score'] = np.nan

# 2. MAR:随机缺失(缺失依赖于年龄)
data_mar = data.copy()
# 年龄 < 30 的申请人,收入缺失概率 15%;年龄 ≥ 30 的,缺失概率 3%
prob_mar = np.where(data_mar['age'] < 30, 0.15, 0.03)
mask_mar = np.random.random(n) < prob_mar
data_mar.loc[mask_mar, 'income'] = np.nan

# 3. MNAR:非随机缺失(缺失依赖于逾期天数本身)
data_mnar = data.copy()
# 逾期天数 > 10 的客户,缺失概率 80%;否则 2%
prob_mnar = np.where(data_mnar['overdue_days'] > 10, 0.80, 0.02)
mask_mnar = np.random.random(n) < prob_mnar
data_mnar.loc[mask_mnar, 'overdue_days'] = np.nan

# 验证缺失率
print(f"MCAR - credit_score 缺失率: {data_mcar['credit_score'].isna().mean():.2%}")
print(f"MAR  - income 缺失率: {data_mar['income'].isna().mean():.2%}")
print(f"MNAR - overdue_days 缺失率: {data_mnar['overdue_days'].isna().mean():.2%}")
输出示例:
MCAR - credit_score 缺失率: 5.01%
MAR - income 缺失率: 6.84%
MNAR - overdue_days 缺失率: 12.35%

风控场景中的缺失机制诊断流程

风控缺失机制诊断流程 步骤1:缺失模式可视化 步骤2:分组差异检验 步骤3:逻辑回归建模 步骤4:敏感性分析 诊断要点 • 缺失热力图 + 条形图 • 缺失/非缺失组 t 检验 • 缺失标志 ~ 完整变量回归 • 系数显著 → 拒绝 MCAR • 领域专家判断 MNAR • 不同填充策略对比 • 模型稳定性评估 • 缺失标志作为特征 • 最终机制判定

总结:风控缺失机制选择矩阵

缺失机制 典型风控场景 推荐填充方法 是否保留缺失标志
MCAR 系统故障、传输丢包 均值/中位数填充;直接删除 通常不需要
MAR 年龄影响收入缺失、学历影响职业信息缺失 多重插补(MICE);回归插补 建议保留
MNAR 逾期天数缺失、高风险客户隐瞒收入 缺失值编码为独立类别;Heckman 模型 必须保留
实战建议: 在风控建模中,建议始终保留缺失指示变量(is_missing)作为候选特征。即使初步判断为 MCAR 或 MAR,保留该标志也不会带来额外风险,反而可能在 MNAR 场景下捕获关键风险信号。