【机器学习-评估方法】评价指标
在选择模型的时候,我们会选择好的模型,丢弃不好的模型。模型的好或者不好是根据评价指标来衡量的,这篇文章介绍了分类任务中几种常用的评价指标,包括:错误率(error rate)和精度(accuracy)、查准率(precision)、查全率(recall)和 F1、ROC-AUC。
错误率和精度
错误率(error rate)和精度(accuracy)是一对互补的指标,既可以应用于二分类任务,也可以应用于多分类任务。错误率是分类错误的样本数占总样本数的比例,而精度是分类正确的样本数占总样本数的比例。假设样本总数为 n,分类错误的样本为 m,则
查准率、查全率和 F1
首先看一下真正例(true positive,TP)、假正例(false positive,FP)、真反例(true negative,TN)和假反例(false negative,FN),用 TP、FP、TN、FN 分别代表这 4 类样本的数量。假设问题为二分类问题(样本有两个类别:正例或者反例)。真正例和真反例都是我们的模型预测对的那些样本,比如对于一些样本模型预测为正例,实际也为正例,那么这些样本就是真正例 TP;模型预测为反例,实际也为反例,那么这些样本就是真反例 TN。假正例和假反例是模型预测错误的样本:如果对于一些样本模型预测为正例,而实际为反例,说明模型预测错了,那么这些样本叫做假正例 FP(真假是对模型的预测结果做判断,而不是实际的结果);同样地,如果对于一些样本模型预测为反例,而实际为正例,那么这些样本叫做假反例 FN。
上图中的矩阵被称为混淆矩阵(confusion matrix)。对于真正例(TP)、假正例(FP)、真反例(TN)和假反例(FN),有 TP + FP + TN + FN = 样本总数,样本中实际为正例的数量为 TP + FN,样本中实际为反例的数量为 TN + FP。
有了 TP、FP、TN、FN,我们就可以定义查准率(precision,P,又称“准确率”)和查全率(recall,R,又称“召回率”):
查准率就是我们模型预测为正例的样本(TP+FP)当中,实际为正例(TP)的比例,而查全率是实际为正例的样本(TP+FN)当中,有多少被预测为正例(TP),注意这里不是 TP+FP,因为虽然 FP 也被预测为正例,但 FP 不在 TP+FN 当中。
举个例子,假设我们有 6 个样本,样本的实际标签和模型预测的标签如下,1 代表正例,0 代表反例:
实际:[1, 1, 1, 0, 0, 0]
预测:[1, 1, 0, 0, 1, 1]
那么,查准率 = TP / (TP+FP) = 2 / (2+2) = 1/2,查全率 = TP / (TP + FN) = 2 / (2+1) = 2/3.
查准率和查全率是一对矛盾的度量。也就是说,查准率较高时,查全率会比较低;查全率较高时,查准率会比较低。使用单一的查准率或者查全率来度量一个模型显得有些片面,所以根据查准率(P)和查全率(R)引出了 F1 度量:
F1 实际上是查准率和查全率的调和平均:\(\frac{1}{F1}=\frac{1}{2}(\frac{1}{p}+\frac{1}{R})\)。F1 度量综合考虑了查准率和查全率。对于一些情况,我们比较重视查准率,例如推荐系统,而另一些情况我们更加重视查全率,例如在逃犯信息检索系统中,我们希望少漏掉逃犯。当对查准率和查全率有不同的重视情况时,我们可以使用 F1 度量的一般形式 \(F_{\beta}\):
其中,\(\beta>0\) 度量了查全率对查准率的相对重要性。\(\beta=1\) 时,\(F_{\beta}\) 退化为普通的 \(F1\),\(\beta>1\) 时查全率有更大的影响,\(\beta<1\) 时查准率有更大的影响。
有时,我们会得到多个混淆矩阵。例如,我们进行了多次训练和测试,每次都能得到一个混淆矩阵;或者是在多分类任务中,每两个类别都对应一个混淆矩阵。假如我们想要根据这 n 个混淆矩阵中综合考察查准率和查全率。一种方法是我们可以先对每个混淆矩阵计算查准率(P)和查全率(R),对于 n 个混淆矩阵,有 \((P_1, R_1),(P_2,R_2),\dots,(P_n,R_n)\),然后计算查准率的平均值,可以得到宏查准率(macro-P);计算查全率的平均值,可以得到宏查全率(macro-recall);根据宏查准率和宏查全率,可以得到宏F1(macro-F1):
还有一种方法就是先计算出所有混淆矩阵中 TP、FP、TN、FN 的平均值 \(\overline{TP}、\overline{FP}、\overline{TN}、\overline{FN}\),然后再基于这些平均值计算出微查准率(micro-P)、微查全率(micro-R)和微F1(micro-F1):
ROC-AUC
很多分类模型的输出是一个概率,我们将输出的概率与阈值比较,如果输出概率大于阈值,则预测为正例,否则预测为反例. 我们将输出概率降序排序,阈值实际上就是输出概率中的一个截断点,在该截断点前的样本都是正例,之后的都是反例。这样的话,假设有 n 个样本,就会有 n 个输出概率,我们将这 n 个概率降序排序,然后每次拿一个概率作为截断点,该截断点之前的都预测为正例,之后的都预测为反例。每次分类后计算两个值叫做假正例率(False Positive Rate,FPR)和真正例率(True Positive Rate,TPR):
将坐标(FPR,TPR)画在二维坐标系中,就会得到ROC曲线(Receiver Operating Characteristic,受试者工作特征),如下图:
ROC 曲线下的面积叫做AUC(Area Under Curve),图中的斜对角虚线代表随机猜测的模型。随机猜测的 AUC 是 0.5,所以正常情况下,ROC-AUC 的取值范围为 [0.5, 1]。左图是理想情况,而实际只有有限个样本,所以 ROC 曲线并不是光滑的。如果模型 A 的 AUC 大于 模型 B 的 AUC,我们说模型 A 优于模型 B。
AUC 还可以从概率角度进行解释:我们取一个正例和一个负例,正例得分大于负例得分的概率就是 AUC。或者说,模型根据样本的输出值将正例排在负例前面的概率就是 AUC。从这个角度,我们可以很容易地计算 AUC:给定正样本M个,负样本N个,以及他们的预测概率(0-1)之间,那么 AUC 的含义就是穷举所有的正负样本对,如果正样本的预测概率大于负样本的预测概率,那么就+1;如果如果正样本的预测概率等于负样本的预测概率,那么就+0.5, 如果正样本的预测概率小于负样本的预测概率,那么就+0;最后把统计处理的个数除以M×N就得到我们的 AUC,公式描述如下:
代码实现如下:
def roc_auc(y_true, y_pred):
pos = [i for i in range(len(y_true)) if y_true[i]==1]
neg = [i for i in range(len(y_true)) if y_true[i]==0]
score = 0
for i in pos:
for j in neg:
if y_pred[i]>y_pred[j]:
score += 1
elif y_pred[i]==y_pred[j]:
score += 0.5
return score/(len(pos)*len(neg))
测试:
y_true = [1,1,0,0,0]
y_pred = [0.3,0.8,0.1,0.5,0.4]
roc_auc(y_true, y_pred) # 0.6666666666666666
sklearn.metrics.roc_auc_score(y_true, y_pred) # 0.6666666666666667
y_true = [1,1,0,0,0,1,1,0,0]
y_pred = [0.3,0.8,0.1,0.5,0.4,0.6,0.7,0.2,0.3]
roc_auc(y_true, y_pred) # 0.875
sklearn.metrics.roc_auc_score(y_true, y_pred) # 0.875
参考
1、周志华《机器学习》