机器学习中的可解释性简述
背景
在机器学习领域中,人们往往会使用各种复杂的模型以求更高的评估效果。从一开始的LR、SVM到boosting算法以及神经网络,越来越高的复杂度往往能够在大型数据集下取得不错的效果。
也有很多人称复杂的模型为黑盒子,这是因为大部分人包括数据科学家都无法理解模型是怎样做出预测的。
所以这篇文章里面我们来谈谈“可解释性”方面的研究进展。
为什么需要注重“可解释”
利用“可解释性”可以改进模型。在kaggle比赛的手写数字识别中,往往都会通过混淆矩阵来查看模型在哪些数字上预测错误,从而改进模型。如果我们能够分析模型预测错误的case,得到每个特征对于预测结果的影响程度,我们就能够选择更多有用的特征加入模型,从而改善模型。
用户对于平台提供的预测结果也需要一个合理的理由。在实际的场景中,如淘宝买卖纠纷,或者是滴滴的司乘费用纠纷等等,这些场景除了要求模型给出其预测结果以外,还要去给出令人信服的原因,这样用户才会相信平台的判断,平台才会有更高的用户黏性和留存。
现状
笔者认为,现在主要有两种视角去观察的模型“可解释性”:①从所有的测试实例观察 ②从特定实例观察,其中第②种方法往往更受关注。
从所有测试实例观察特征的重要性以及影响次序
观察特征重要性
在训练结束后,可以通过一些手段来观察特征的重要性。
PermutationImportance
import eli5 from eli5.sklearn import PermutationImportance #my_model是一个随机森林模型 perm = PermutationImportance(my_model,random_state = 1).fit(val_X,val_y) eli5.show_weights(perm, feature_names = val_X.columns.tolist())
得出的重要性排列如下图所示,其方法的主要原理是训练好模型后,每次打乱验证集的一列并预测,用这个预测结果与真实标签进行比较,通过计算打乱后数据精度会受到多大影响来衡量被打乱列的重要性。
plot_importance_
#xgb_model是一个xgboost模型
ax = xgb.plot_importance(xgb_model, height=0.5, importance_type = 'weight') fig = ax.figure fig.set_size_inches(15,10) plt.show()
在xgboost中,可以通过`plot_importance_`或者`get_score`方法得到特征的重要性分数。
参数`importance_type`的取值有三种:`weight`使用特征在所有树中作为划分属性的次数作为分数、'gain'使用特征作为划分属性的loss平均降低量作为分数、'cover'使用特征作为划分属性时对样本的覆盖度作为分数。

此类方法有一个共同的缺点,那就是它所反应的特征重要性,是无法针对每个预测案例给出其可解释性原因的。比如之前提到的淘宝买卖纠纷,plot_importance_方法只会给出在训练数据上模型的特征重要性,此时若有一个订单经过模型判卖家有责,是无法根据订单相关信息给出卖家有责的原因的,换言之就是无法给出此订单的特征重要性。
从特定实例观察模型
SHAP Value
现在通过SHAP Value来看一下如何才能查看实例级别的预测原因。
import shap #model 是一个随机森林分类器 explainer = shap.TreeExplainer(model) #data_for_prediction是一个实例 shap_values = explainer.shap_values(data_for_prediction) shap.initjs() #我们只关注二分类预测为正类的原因 shap.force_plot(explainer.expected_value[1], shap_values[1], data_for_prediction)
可以看到下图中有三个关键的部分:base value为0.4979,预测结果output value为0.70(此实例有0.7的概率为正类),红色部分为导致预测结果增长的部分,而蓝色部分为导致预测结果下降的部分。可以看到在红色部分中 Goal Scored 的影响程度比较高,其次是 On-Target。

总结
简单介绍了一下从两种视角观察模型可解释性的方法,以及它们的应用背景。
总体来说,SHAP Value方法在模型后期优化方面用的比较多,通过会根据线上的bad case来看下一步如何优化模型;而plot_importance_方法常常用来做特征选择,在特征工程阶段出现场景比较多。

浙公网安备 33010602011771号