天天看点

(二)常见的分类评价指标及代码实现与应用一、二分类指标(Binary Classification Metrics)二、多分类指标(Multi Classification Metrics)三、代码应用参考文献

在上一篇《(一)常见的回归评价指标及代码应用》中我们介绍了评价回归性能的指标。

sklearn的官方文档《 Model evaluation: quantifying the quality of predictions》中,对于二分类,多分类和多标签问题,有非常详细的指标介绍和实现。

本篇博客我们只介绍常见的分类评价指标,以及它们的代码实现与应用。

文章目录

  • 一、二分类指标(Binary Classification Metrics)
    • 1.1 混淆矩阵 Confusion Matrix
    • 1.2 精度 Accuracy
    • 1.3 准确率(查准率) Precision
    • 1.4 召回率(查全率)Recall
    • 1.5 Fβ Score
    • 1.6 特异度 Specificity && 灵敏度 Sensitivity
    • 1.7 ROC&&AUC
      • 1.7.1 ROC
      • 1.7.2 AUC
    • 1.8 对数损失 logloss
  • 二、多分类指标(Multi Classification Metrics)
    • 2.1 混淆矩阵
    • 2.2 对数损失 logloss
  • 三、代码应用
  • 参考文献

一、二分类指标(Binary Classification Metrics)

以下的指标介绍,我们基于二分类问题来讲。

1.1 混淆矩阵 Confusion Matrix

我们首先来介绍混淆矩阵,接下来的很多概念都是基于此。混淆矩阵牵扯到三个方面:真实值,预测值,预测值和真实值之间的关系,其中任意两个方面都可以确定第三个。

通常取预测值和真实值之间的关系对矩阵进行划分,形成了如下的混淆矩阵:

(二)常见的分类评价指标及代码实现与应用一、二分类指标(Binary Classification Metrics)二、多分类指标(Multi Classification Metrics)三、代码应用参考文献

可以看到,一共有4种情况:

  • True positive (TP):真实值为Positive,预测正确(预测值为Positive)
  • True negative (TN):真实值为Negative,预测正确(预测值为Negative)
  • False positive (FP):真实值为Negative,预测错误(预测值为Positive),第一类错误, Type I

    error。

  • False negative (FN):真实值为Positive,预测错误(预测值为 Negative),第二类错误, Type II

    error。

接下来,我们就要以TP,TN,FP,FN为基础,介绍各种评价指标了。

1.2 精度 Accuracy

精度 Accuracy是我们评估分类性能的最常用,也是最容易理解的指标了。它的定义如下:

A C C = T P + T N T P + T N + F P + F N ACC = \frac{TP+TN}{TP+TN+FP+FN} ACC=TP+TN+FP+FNTP+TN​

即预测正确的样本的占总样本的比例,取值范围为[0,1],取值越大,模型预测能力越好。

但是,精度在很多情况下容易失效,这是为什么呢?

① 对于有倾向性的问题,往往不能用精度指标来衡量 。比如,判断空中的飞行物是导弹还是其他飞行物,很显然为了减少损失,我们更倾向于相信是导弹而采用相应的防护措施。此时判断为导弹实际上是其他飞行物与判断为其他飞行物实际上是导弹这两种情况的重要性是不一样的;

② 对于样本类别数量严重不均衡的情况,也不能用精度指标来衡量。比如银行客户样本中好客户990个,坏客户10个。如果一个模型直接把所有客户都判断为好客户,得到精度为99%,但这显然是没有意义的。

对于以上两种情况,单纯根据Accuracy来衡量算法的优劣已经失效。这个时候就需要对目标变量的真实值和预测值做更深入的分析。

1.3 准确率(查准率) Precision

Precision 是分类器预测的正样本中预测正确的比例,取值范围为[0,1],取值越大,模型预测能力越好。它的定义如下:

P = T P T P + F P P = \frac{TP}{TP+FP} P=TP+FPTP​

如果分类问题是医生诊断病人是否患病,它背后的物理含义是这样的:诊断为患病的人们中有多少比例真的是患病。

1.4 召回率(查全率)Recall

Recall 是分类器所预测正确的正样本占所有正样本的比例,取值范围为[0,1],取值越大,模型预测能力越好。它的定义如下:

R = T P T P + F N R = \frac{TP}{TP+FN} R=TP+FNTP​

如果分类问题是医生诊断病人是否患病,它背后的物理含义是这样的:真的是患病的人们中有多少比例诊断为患病。

我们可以很明显的感觉到,Precision和Recall是存在“矛盾的”,我们既想把所有正例都找出来(Recall高),又想正确地把所有正例找出来(Precision高)。

我们举2个例子说明情况:

①地震的预测

对于地震的预测,我们希望的是Recall非常高,也就是说每次地震我们都希望预测出来。这个时候我们可以牺 牲Precision。情愿发出1000次警报,把10次地震都预测正确了;也不要预测100次对了8次漏了两次。即“宁错拿一万,不放过一个”,分类阈值较低。

②嫌疑人定罪

基于“疑罪从无”的原则,对于嫌疑人的定罪我们希望是非常准确的。即使有时候放过了一些罪犯,也不想冤枉一个好人。即我们希望有较高的Precision值,可以合理地牺牲Recall。“宁放过一万,不错拿一个”,分类阈值较高。

根据以上几个案,我们知道随着阈值的变化Recall和Precision往往会向着反方向变化,这种规律很难满足我们的期望,即Recall和Precision同时增大。

1.5 Fβ Score

那有没有什么方法权衡Recall和Precision 的矛盾?我们可以用一个指标来统一Recall和Precision的矛盾,即利用Recall和Precision的加权调和平均值(weighted harmonic mean)作为衡量标准。即Fβ Score,公式如下:

F β = ( 1 + β 2 ) T P ( 1 + β 2 ) T P + β 2 F N + F P = ( 1 + β 2 ) ⋅ P r e c i s i o n ⋅ R e c a l l β 2 ⋅ P r e c i s i o n + R e c a l l F_{\beta}=\frac{(1+\beta^{2})TP}{(1+\beta^{2})TP+\beta^{2}FN+FP}=\frac{(1+\beta^{2}) \cdot Precision \cdot Recall}{\beta^{2} \cdot Precision+Recall} Fβ​=(1+β2)TP+β2FN+FP(1+β2)TP​=β2⋅Precision+Recall(1+β2)⋅Precision⋅Recall​

β \beta β度量了Recall对Precision的相对重要性, β &gt; 1 \beta&gt;1 β>1 的时候,Recall有更大影响; β &lt; 1 \beta&lt;1 β<1 的时候Precision有更大影响。

当 β = 1 \beta=1 β=1时,Fβ就退回到经典的评价指标 F 1 F1 F1了, F 1 F1 F1的定义如下:

F 1 = 2 T P 2 T P + F N + F P = 2 ⋅ P r e c i s i o n ⋅ R e c a l l P r e c i s i o n + R e c a l l F1=\frac{2TP}{2TP+FN+FP}=\frac{2 \cdot Precision \cdot Recall}{Precision+Recall} F1=2TP+FN+FP2TP​=Precision+Recall2⋅Precision⋅Recall​

1.6 特异度 Specificity && 灵敏度 Sensitivity

在介绍著名的ROC&&AUC 之前,我们再根据混淆矩阵,介绍几个概念,先介绍特异度 Specificity 。

特异度(Specificity) 又称为真阴性率TNR:true negative rate,描述的是在所有的负样本中,分类器预测正确的比例 。计算公式为:

T N R = T N F P + T N TNR = \frac{TN}{FP + TN} TNR=FP+TNTN​

1-Specificity就是假阳性率(FPR):描述的是在所有的负样本中,分类器预测错误的比例

F P R = F P F P + T N FPR = \frac{FP}{FP + TN} FPR=FP+TNFP​

敏感度(Sensitivity) 又称为真阳性率TPR:true positive rate,描述的是在所有的正样本中,分类器预测正确的比例(等于Recall)

T P R = T P T P + F N TPR = \frac{TP}{TP + FN} TPR=TP+FNTP​

ROC曲线就是根据1-Specificity和Sensitivity画出的。

1.7 ROC&&AUC

我们首先应该分清ROC和AUC的概念:AUC是一种模型分类指标,且仅仅是二分类模型的评价指标。AUC是Area Under Curve的简称,那么Curve就是 ROC(Receiver Operating Characteristic),翻译为"接受者操作特性曲线"。也就是说ROC是一条曲线,AUC是 一个面积值。

1.7.1 ROC

ROC曲线为 FPR 与 TPR 之间的关系曲线,这个组合以 FPR 对 TPR,即是以代价 (costs) 对收益 (benefits),显然收益越高,代价越低,模型的性能就越好。

为了更好地理解ROC曲线,我们使用具体的实例来说明:

如在医学诊断的主要任务是尽量把生病的人群都找出来,也就是TPR越高越好。而尽量降低没病误诊为有病的人数,也就是FPR越低越好。

不难发现,这两个指标之间是相互制约的。如果某个医生对于有病的症状比较敏感,稍微的小症状都判断为有病,那么他的TPR应该会很高,但是FPR也就相应地变高。最极端的情况下,他把所有的样本都看做有病,那么TPR达到1,FPR也为1。即对于正样本,都预测对了;对于负样本,都预测错了。

我们以FPR为横轴,TPR为纵轴,得到如下ROC空间:

(二)常见的分类评价指标及代码实现与应用一、二分类指标(Binary Classification Metrics)二、多分类指标(Multi Classification Metrics)三、代码应用参考文献

我们可以看出,左上角的点(TPR=1,FPR=0),为完美分类,也就是这个医生医术高明,诊断全对,即对于正样本,都预测对了;对于负样本,也都预测对了。点A(TPR>FPR),医生A的判断大体是正确的。中线上的点B(TPR=FPR),也就是医生B全都是蒙的,蒙对一半,蒙错一半;下半平面的点C(TPR<FPR),这个医生说你有病,那么你很可能没有病,医生C的话我们要反着听。上图中一个阈值,得到一个点。现在我们需要一个独立于阈值的评价指标来衡量这个医生的医术如何,也就是遍历所有的阈值,得到 ROC 曲线。

假设下图是某医生的诊断统计图,上图和下图分别为未得病人群和得病人群的模型输出概率分布图(横坐标表示模型输出概率,纵坐标表示概率对应的人群的数量),显然未得病人群的概率值普遍低于得病人群的输出概率值(即正常人诊断出疾病的概率小于得病人群诊断出疾病的概率)。

竖线代表阈值。显然,图中给出了某个阈值对应的混淆矩阵,通过改变不同的阈值 ,得到一系列的混淆矩阵,进而得到一系列的TPR和FPR,绘制出ROC曲线。

我们来分析ROC曲线是如何画出的(从箭头方向分析):

一开始A点,阈值为1时,不管你什么症状,医生均未诊断出疾病(预测值都为N,只有大于阈值时,才会诊断出疾病),此时 ,正样本(患病样本)全部预测错,负样本(未患病样本)全部预测对,即TPR=0,FPR=0。位于左下。

最后C点,阈值为 0 时,不管你什么症状,医生都诊断结果都是得病(预测值都为P),此时 ,正样本(患病样本)全部预测对,负样本(未患病样本)全部预测错,即TPR=1,FPR=1。位于右上。

在中间时B点,是随着阈值不断变化,TPR和FPR也一直变化,从而构成了ROC曲线。

(二)常见的分类评价指标及代码实现与应用一、二分类指标(Binary Classification Metrics)二、多分类指标(Multi Classification Metrics)三、代码应用参考文献

1.7.2 AUC

AUC 值为 ROC 曲线所覆盖的区域面积,显然,AUC越大,分类器分类效果越好。

  • AUC = 1,是完美分类器。
  • 0.5 < AUC < 1,优于随机猜测。有预测价值。
  • AUC = 0.5,跟随机猜测一样(例:丢铜板),没有预测价值。
  • AUC < 0.5,比随机猜测还差;但只要总是反预测而行,就优于随机猜测。

注:对于AUC小于 0.5 的模型,我们可以考虑取反(模型预测为positive,那我们就取negtive),这样就可以保证模型的性能不可能比随机猜测差。

以下为ROC曲线和AUC值的实例:

(二)常见的分类评价指标及代码实现与应用一、二分类指标(Binary Classification Metrics)二、多分类指标(Multi Classification Metrics)三、代码应用参考文献

AUC的物理意义是正样本的预测结果大于负样本的预测结果的概率。所以AUC反映的是分类器对样本的排序能力。另外值得注意的是,AUC对样本类别是否均衡并不敏感,这也是不均衡样本通常用AUC评价分类器性能的一个原因。

我们举例来进一步说明AUC的意义:

小明一家四口,小明5岁,姐姐10岁,爸爸35岁,妈妈33岁,建立一个逻辑回归分类器,来预测小明家人为成年人概率。

以下为三种模型的输出结果,求三种模型的 AUC :

(二)常见的分类评价指标及代码实现与应用一、二分类指标(Binary Classification Metrics)二、多分类指标(Multi Classification Metrics)三、代码应用参考文献
  1. AUC更多的是关注对计算概率的排序,关注的是概率值的相对大小,与阈值和概率值的绝对大小没有关系

    例子中并不关注小明是不是成人,而关注的是,预测为成人的概率的排序。

  2. AUC只关注正负样本之间的排序,并不关心正样本内部,或者负样本内部的排序。这也体现了AUC的本质:

    任意个正样本的概率都大于负样本的概率的能力。

例子中AUC只需要保证(小明和姐姐)(爸爸和妈妈),小明和姐姐在前2个排序,爸爸和妈妈在后2个排序,而不会考虑小明和姐姐谁在前,或者爸爸和妈妈谁在前 。AUC只与概率的相对大小(概率排序)有关,和绝对大小没关系。由于三个模型概率排序的前两位都是未成年人(小明,姐姐),后两位都是成年人(妈妈,爸爸),因此三个模型的AUC都等于1。

再举一个例子:

以下已经对分类器输出概率从小到大进行了排列,哪些情况的AUC等于1, 情况的AUC为0(其中背景色表示True value,红色表示成年人,蓝色表示未成年人)

(二)常见的分类评价指标及代码实现与应用一、二分类指标(Binary Classification Metrics)二、多分类指标(Multi Classification Metrics)三、代码应用参考文献

D 模型, E模型和F模型的AUC值为1,C 模型的AUC值为0(爸妈为成年人的概率小于小明和姐姐,显然这个模型预测反了)。

AUC的计算

  • 法1:AUC为ROC曲线下的面积,那我们直接计算面积可得。面积为一个个小的梯形面积(曲线)之和。计算的精度与阈值的精度有关 。
  • 法2:根据AUC的物理意义,我们计算正样本预测结果大于负样本预测结果的概率。取N*M(N为正样本数,M为负样本数)个二元组,每个二元组比较正样本和负样本的预测结果,正样本预测结果高于负样本预测结果则为预测正确,预测正确的二元组占总二元组的比率就是最后得到的AUC。时间复杂度为O(N*M)。
  • 法3:我们首先把所有样本按照score排序,依次用rank表示它们,如最大score的样本,rank=n

    (n=n0+n1,其中n0为负样本个数,n1为正样本个数),其次为n-1。那么对于正样本中rank最大的样本,rank_max,有n1-1个其他正样本比他score小,那么就有(rank_max-1)-(n1-1)个负样本比他score小。其次为(rank_second-1)-(n1-2)。最后我们得到正样本大于负样本的概率为 :

    (二)常见的分类评价指标及代码实现与应用一、二分类指标(Binary Classification Metrics)二、多分类指标(Multi Classification Metrics)三、代码应用参考文献
    其计算复杂度为O(N+M)。

对于方法3,下面有一个简单的例子:

真实标签为 (1, 0, 0, 1, 0)。 预测结果1(0.9, 0.3, 0.2, 0.7, 0.5) 预测结果2(0.9, 0.3, 0.2, 0.7, 0.8))

分别对两个预测结果进行排序,并提取他们的序号。 结果1 (5, 2, 1, 4, 3) 结果2 (5, 2, 1, 3, 4)

对正分类序号累加 结果1:SUM正样本(rank(score))=5+4=9 结果2: SUM正样本(rank(score))=5+3=8

计算两个结果的AUC: 结果1:AUC= (9-23/2)/6=1 结果2:AUC= (8-23/2)/6=0.833

为什么说 ROC 和AUC都能应用于非均衡的分类问题?

ROC曲线只与横坐标 (FPR) 和 纵坐标 (TPR) 有关系 。我们可以发现TPR只是正样本中预测正确的概率,而FPR只是负样本中预测错误的概率,和正负样本的比例没有关系。因此 ROC 的值与实际的正负样本比例无关,因此既可以用于均衡问题,也可以用于非均衡问题。而 AUC 的几何意义为ROC曲线下的面积,因此也和实际的正负样本比例无关。

1.8 对数损失 logloss

对数损失,也称为逻辑回归损失或交叉熵损失,是根据概率估计定义的。它通常用于(多项式)逻辑回归和神经网络,以及EM的一些变体中,且可用于评估分类器的概率输出(predict_proba)而不是其离散预测。

对于具有真实标签和概率估计的二分类,每个样本的对数损失是给定真实标签的分类器的负对数似然:

L log ⁡ ( y , p ) = − log ⁡ Pr ⁡ ( y ∣ p ) = − ( y log ⁡ ( p ) + ( 1 − y ) log ⁡ ( 1 − p ) ) L_{\log}(y, p) = -\log \operatorname{Pr}(y|p) = -(y \log (p) + (1 - y) \log (1 - p)) Llog​(y,p)=−logPr(y∣p)=−(ylog(p)+(1−y)log(1−p))

对数损失是非负的,值越小越好。

二、多分类指标(Multi Classification Metrics)

多分类问题可以转换为二分类问题,常用的有两种转换方法:

(1)一对一

(2)一对多

因此,二分类指标基本可以用于多分类。

在这里,我们也介绍一些多分类的评价指标

2.1 混淆矩阵

举一个三分类的例子:

(二)常见的分类评价指标及代码实现与应用一、二分类指标(Binary Classification Metrics)二、多分类指标(Multi Classification Metrics)三、代码应用参考文献

基于上述的混淆矩阵,我们类比二分类,有:

P 0 = T P T P + F P = a a + d + g P_0 = \frac{TP}{TP+FP} = \frac{a}{a+d+g} P0​=TP+FPTP​=a+d+ga​

R 0 = T P R 0 = T P T P + F N = a a + b + c R_0 = TPR_0 = \frac{TP}{TP+FN}=\frac{a}{a + b+c} R0​=TPR0​=TP+FNTP​=a+b+ca​

T N R 0 = T N T N + F P = e + i e + i + d + g TNR_0 = \frac{TN}{TN+FP}=\frac{e+i}{e+i+d+g} TNR0​=TN+FPTN​=e+i+d+ge+i​

即, T P = a , T N = e + i , F P = d + g , F N = b + c TP=a,TN=e+i,FP=d+g,FN=b+c TP=a,TN=e+i,FP=d+g,FN=b+c。

2.2 对数损失 logloss

对于多分类问题,也有对数损失,定义如下:

L log ⁡ ( Y , P ) = − log ⁡ Pr ⁡ ( Y ∣ P ) = − 1 N ∑ i = 0 N − 1 ∑ k = 0 K − 1 y i , k log ⁡ p i , k L_{\log}(Y, P) = -\log \operatorname{Pr}(Y|P) = - \frac{1}{N} \sum_{i=0}^{N-1} \sum_{k=0}^{K-1} y_{i,k} \log p_{i,k} Llog​(Y,P)=−logPr(Y∣P)=−N1​i=0∑N−1​k=0∑K−1​yi,k​logpi,k​

假设一组样本的真实标签被编码为 K K K维二进制指示符矩阵 Y Y Y,即, y i , k = 1 y_{i,k} = 1 yi,k​=1,表示样本 i i i的真实标签为 k k k。 P P P是预测的概率矩阵,且 p i , k = Pr ⁡ ( y i , k = 1 ) p_{i,k} = \operatorname{Pr}(y_{i,k} = 1) pi,k​=Pr(yi,k​=1)。

三、代码应用

在本章中,我主要介绍二分类的代码应用。

sklearn的官方文档《 Model evaluation: quantifying the quality of predictions》中,对于二分类,多分类和多标签问题,有非常详细的指标介绍和实现。需要的时候再添加。

以下是非常简单的代码:

from sklearn.metrics import log_loss,precision_score,recall_score,f1_score,\
                fbeta_score,confusion_matrix


## confusion matrix

y_true = [0, 0, 0, 1, 1, 1, 1, 1]
y_pred = [0, 1, 0, 1, 0, 1, 0, 1]
tn, fp, fn, tp = confusion_matrix(y_true, y_pred).ravel()


## P,R,f1
alg_conf = {}
alg_conf["Mmetrics"] = {
    'precision_score:': precision_score,  # MSE, 
    'recall_score': recall_score,# MSLE
    'f1_score:': f1_score # MedAE  
}


y_true = [0, 1, 0, 1]
y_pred = [0, 1, 0, 0]
for key, valid_metrics in alg_conf["Mmetrics"].items():
    print(key, valid_metrics(y_true, y_pred))


## log-loss
alg_conf = {}
alg_conf["Mmetrics"] = {
    'log_loss:': log_loss  # log_loss   
}

y_true = [0, 0, 1, 1]
y_pred = [[.9, .1], [.8, .2], [.3, .7], [.01, .99]]
for key, valid_metrics in alg_conf["Mmetrics"].items():
    print(key, valid_metrics(y_true, y_pred))
           

参考文献

【1】机器学习评估指标

【2】特异度(specificity)与灵敏度(sensitivity)

【3】混淆矩阵(Confusion Matrix)