4. PSI(群体稳定性指标)原理
PSI(Population Stability Index,群体稳定性指标)是衡量模型评分或特征分布在时间维度上发生偏移程度的量化工具。在金融风控中,PSI 用于监控坏账率、评分卡输出、关键特征分布是否随客群变化而显著改变,是哨兵系统的核心指标之一。
4.1 PSI 数学公式
PSI 基于信息论中的 KL 散度(Kullback-Leibler divergence)对称化改造,计算公式如下:
PSI = Σ (实际占比_i - 预期占比_i) × ln(实际占比_i / 预期占比_i)
其中:
- 预期占比(Expected):基准期(如模型开发期、上一个月)各分箱内的样本比例。
- 实际占比(Actual):监控期(如当前周、当前月)各分箱内的样本比例。
- i:第 i 个分箱,共 N 个分箱。
PSI 的数学本质是衡量两个概率分布之间的差异程度。当两个分布完全一致时,PSI = 0;差异越大,PSI 值越高。
计算注意事项:当某个分箱的实际占比或预期占比为 0 时,ln(0) 无定义。工程实践中通常对占比做平滑处理(如加极小值 1e-6),或将该分箱与相邻分箱合并。
4.2 分箱方法
PSI 的计算依赖分箱策略,不同的分箱方法会直接影响 PSI 的敏感度和稳定性。以下是三种主流分箱方法:
| 分箱方法 | 原理 | 适用场景 | 优点 | 缺点 |
|---|---|---|---|---|
| 等距分箱 | 按数值范围等间隔切分 | 评分卡输出、连续特征 | 实现简单,分箱边界固定 | 数据稀疏时箱内样本过少 |
| 等频分箱 | 按样本数量等比例切分 | 高频 tick 数据、分布偏态特征 | 每箱样本量均衡,统计稳定 | 边界随数据分布变化 |
| 决策树分箱 | 基于目标变量(如坏账标签)做最优切分 | 特征工程阶段、坏账率敏感特征 | 与业务目标对齐,区分度强 | 过拟合风险,监控期可能失效 |
高频 tick 数据分箱避坑:tick 数据通常存在极端值(如单笔大额交易),等距分箱可能导致大部分样本集中在少数箱内。建议优先使用等频分箱,并设置最小箱占比阈值(如 5%),避免空箱或极稀疏箱。
4.3 PSI 阈值与业务含义
PSI 的数值大小直接对应分布偏移的严重程度。金融风控领域通用的阈值标准如下:
| PSI 范围 | 偏移等级 | 业务含义 | 建议动作 |
|---|---|---|---|
| 0.00 ~ 0.10 | 无偏移 / 轻微偏移 | 客群分布稳定,模型可继续使用 | 常规监控,无需干预 |
| 0.10 ~ 0.25 | 中度偏移 | 客群结构发生可见变化,需排查原因 | 触发预警,分析分箱贡献度 |
| > 0.25 | 严重偏移 | 分布发生结构性改变,模型可能失效 | 立即停用模型,启动重训或校准 |
坏账率 PSI 哨兵的特殊阈值:对于高频 tick 数据下的坏账率监控,建议将阈值收紧 20%~30%。例如,常规 PSI > 0.25 为严重偏移,在 tick 级坏账率场景下可调整为 > 0.18 即触发紧急告警,因为 tick 数据的高频特性使得偏移累积速度更快。
4.4 PSI 计算与偏移诊断流程
下图展示了从原始 tick 数据到 PSI 告警的完整链路:
4.5 分箱贡献度分析
当 PSI 超过阈值时,需要定位是哪些分箱导致了偏移。每个分箱对 PSI 的贡献度计算公式为:
贡献度_i = (实际占比_i - 预期占比_i) × ln(实际占比_i / 预期占比_i)
贡献度为正表示该分箱实际占比高于预期(客群向该区间集中),贡献度为负表示实际占比低于预期(客群流失)。通过排序贡献度绝对值,可以快速锁定偏移源。
高频 tick 数据贡献度分析案例:某消费金融产品监控到 PSI 从 0.08 跳升至 0.31,贡献度分析发现“交易金额 5000~10000 元”分箱的贡献度占比达 67%,实际占比从 12% 升至 28%。进一步排查发现该分箱坏账率同步上升 2.3 倍,确认是客群向高额度区间迁移导致模型失效。
4.6 PSI 与坏账率哨兵的联动逻辑
在哨兵系统中,PSI 并非孤立指标,而是与坏账率监控形成联动:
- PSI 正常 + 坏账率正常:客群稳定,模型表现稳定,继续常规监控。
- PSI 异常 + 坏账率正常:客群分布发生变化,但模型仍能正确区分好坏客户,需关注变化趋势。
- PSI 正常 + 坏账率异常:客群分布未变,但模型打分能力下降,需检查模型参数或外部环境。
- PSI 异常 + 坏账率异常:客群偏移与模型失效同时发生,需紧急停用并全面排查。
下图展示了 PSI 与坏账率在哨兵系统中的联合决策逻辑:
4.7 高频 tick 场景下的 PSI 工程实践
针对高频 tick 数据的特点,PSI 计算需要做以下工程适配:
- 滑动窗口基准:使用过去 7 天或 30 天的滑动窗口作为基准分布,而非固定历史基准,以适应市场周期性变化。
- 分箱数量控制:tick 数据量巨大,分箱数量建议控制在 10~20 箱,避免过细分箱导致 PSI 对微小波动过度敏感。
- 实时增量计算:采用增量更新算法,每次新 tick 到达时只更新受影响分箱的计数,避免全量重算。
- 多粒度监控:同时计算小时级、日级、周级 PSI,形成多时间尺度的偏移感知。
PSI 计算代码片段(Python 示例):
import numpy as np
def calculate_psi(expected, actual, bins=10):
# 等频分箱
percentiles = np.percentile(expected, np.linspace(0, 100, bins+1))
expected_bins = np.histogram(expected, bins=percentiles)[0]
actual_bins = np.histogram(actual, bins=percentiles)[0]
# 计算占比
expected_pct = expected_bins / np.sum(expected_bins)
actual_pct = actual_bins / np.sum(actual_bins)
# 平滑处理
expected_pct = np.clip(expected_pct, 1e-6, 1)
actual_pct = np.clip(actual_pct, 1e-6, 1)
# PSI 计算
psi = np.sum((actual_pct - expected_pct) * np.log(actual_pct / expected_pct))
return psi