在解决分类问题的时候,可以选择的评价指标简直不要太多。但基本可以分成两2大类,我们今分别来说道说道

  • 基于一个概率阈值判断在该阈值下预测的准确率
  • 衡量模型整体表现(在各个阈值下)的评价指标

在说指标之前,咱先把分类问题中会遇到的所有情况简单过一遍。36度的北京让我们举个凉快一点的例子-我们预测会不会下雨!横轴是预测概率从0-1,红色的部分是没下雨的日子(负样本),蓝色的部分是下雨的日子(正样本)。在真实情况下我们很难找到能对正负样本进行完美分割的分类器,所以我们看到在预测概率靠中间的部分,正负样本存在重合,也就是不管我们阈值卡在哪里都会存在被错误预测的样本。

上述分布中的四种情况,可以简单的用confusion matrix来概括

TP:预测为正&真实为正
FP:预测为正&真实为负
TN:预测为负&真实为负
FN:预测为负&真实为正

基于阈值的指标

分类模型输出的是每个样本为正的概率,我们要先把概率转换成0/1预测。给定一个阈值,我们把预测概率大于阈值的样本预测为正,小于的为负。这时就会出现上述confustion matrix里面的四种情况。那我们该如何去评价模型表现呢?

新手视角- Accuracy!

这应该是大多数人第一个知道的评价指标,它把正负样本混在一起去评价整体的分类准确率。

\[Accuracy = \frac{TP + TN}{TP + TN + FN + FP}\]

老手会用一个在所有tutorial里面都能看到的Imbalance Sample的例子来告诉你,如果你的正样本只有1%,那全部预测为负你的准确率就是99%啦 - so simple and naive ~.~

当然Accuracy也不是不能用,和正样本占比放在一起比较也是能看出来一些信息的。但Accuracy确实更适用正负样本55开,且预测不止针对正样本的情况。

Accuracy知道咋算就可以啦,在解决实际问题的时候,往往会使用更有指向性的指标, 而且一般都会同时选用2个以上的指标因为不同指标之间往往都有trade-off

当目标是对正样本进行准确预测 - precision, recall, F1

precision从预测的角度衡量预测为正的准确率,recall从真实分布的角度衡量预测为正的准确率。precision和recall存在trade-off, 想要挑选出更多的正样本,就要承担预测为正准确率下降的风险。例如在飞机过安检时,想要保证危险物品基本都被识别出来,就肯定要承担一定的误判率。不过在这种情境下查不出危险物品显然比让误判乘客多开包检查一遍要重要的多。

\[
\begin{align}
precision &= \frac{TP}{TP+FP} \\
recall &= \frac{TP}{TP+FN}
\end{align}
\]

既然有trade-off,一般就会用可以综合两个指标的复合指标 - F1 Score
\[
F1 =\frac{1}{\frac{1}{precision} + \frac{1}{recall}}= \frac{precision * recall}{precision + recall}
\]

其实简单一点直接对precision,recall求平均也可以作为复合指标,但F1用了先取倒数再求平均的方式来避免precision或recall等于0这种极端情况的出现

当目标是对真实分布进行准确预测 - sensitivity(recall), specifity, fpr

sensitivity, sepcifity都从真实分布的角度,分别衡量正/负样本预测的准确率。这一对搭配最常在医学检验中出现,衡量实际生病/没生病的人分别被正确检验的概率。正确检验出一个人有病很重要,同时正确排除一个人没生病也很重要。

\[
\begin{align}
sensitivity &= recall \\
specifity & =\frac{TN}{TN + FP} \\
\end{align}
\]

如果specifity对很多人来说很陌生的话,它兄弟很多人一定知道fpr。fpr和recall(tpr)一起构成了ROC曲线。这一对的tradeoff同样用医学检验的逻辑来解释就是,医生既不希望遗漏病人的病情(recall),要不希望把本身没病的人吓出病来(fpr)。
\[
fpr = \frac{FP}{TN+FP} = 1- specifity
\]

和阈值相关经常用到的指标差不多就是这些。这些指标的计算依赖于阈值的确定,所以在应用中往往用验证集来找出使F1/accuracy最大的阈值,然后应用于测试集,再用测试集的F1/accuracy来评价模型表现。下面是几个应用上述指标的kaggle比赛

  1. F1 score
    https://www.kaggle.com/c/quora-insincere-questions-classification/overview/evaluation
  2. accuracy
    https://www.kaggle.com/c/titanic/overview/evaluation

不过开始用到和阈值相关的评价指标有时是在模型已经确定以后。第一步在确定模型时,往往还是需要一些可以综合衡量模型整体表现的指标。简单!粗暴!别整啥曲线阈值的,你给我个数就完了!

综合评价指标

综合评价指标基本都是对上述指标再加工的产物。对应的kaggle比赛会持续更新。

tpr(recall) + fpr = ROC-> AUC

随着阈值从1下降到0,我们预测为正的样本会逐渐变多,被正确筛选出的正样本会逐渐增多,但同时负样本被误判为正的概率也会逐渐上升。

整个遍历阈值的过程可以用ROC曲线来表示,横轴是误判率(fpr),纵轴是准确率(tpr/recall/sensitivity)。但是给你两个分类器想要直接比较谁的ROC曲线会有点困难,所以我们用一个scaler来描述ROC曲线就是AUC - Area under curve。 ROC曲线下的面积越大越接近完美的分类器,而对角线50%是随机猜正负就可以得到的AUC。

Kaggle链接 https://www.kaggle.com/c/santander-customer-transaction-prediction/overview/evaluation

AUC 适用于正负样本相对balance的情况,且分类问题对模型预测概率的准确度没有要求的情况。详见【实战篇】

precision + recall = AUCPR(AP)

和上述ROC-AUC的思路相同。随着阈值从1下降到0,预测为正的样本变多,被正确筛选出的正样本增多,但同时预测为正的准确率会下降。

这样我们得到PR曲线,以及曲线下的面积AUCPR。有时AUCPR也被称作AP,就是对所有recall取值对应的precision求平均。第一眼看上去我也被糊弄了,一直当成两个概念来记。但是式子一写出来,妈呀这俩不是一个东西么。
\[
AUCPR = \sum_1^K\Delta{r(k)} * p(k) = \int_o^1 {p(r) dr} = AP
\]

AP 刚好弥补AUC曲线的不足,适用于正负样本imbalance的情况,或者我们更关心模型在正样本上表现的情况。但AP同样不能保证模型预测概率的准确率。详见【实战篇】

cross-entropy loss

cross-entropy放在这里会有点奇怪,因为本质上它是和这里其他所有指标都不同的存在。其他的评价指标评价的是0/1的分类效果,或者更准确说是对排序效果(根据阈值把预测值从大到小分成0/1两半)进行评价。但是cross-entropy是直接对预测概率是否拟合真实概率进行评价。
\[
L = -\sum_{i=1}^N y_i * log p_i + (1-y_i) * log(1-p_i)
\]

kaggle链接 https://www.kaggle.com/c/statoil-iceberg-classifier-challenge/overview/evaluation

cross-entropy弥补了AP和AUC的不足。如果分类目标其实是获得对真实概率的估计的话,使用cross-entropy应该是你的选择。详见【实战篇】

*Mean F1 Score

kaggle链接 https://www.kaggle.com/c/instacart-market-basket-analysis/overview/evaluation

第一次见到这个指标是在Instacart的kaggle比赛里面。这里的mean不是指的对所有阈值下的F1求平均值而是对每个order_id的多个product_id求F1,再对所有order_id的F1求平均,有点绕...

之所以把这个评价指标也放在这里是因为这个特殊的评价方法会对你如何split训练集/测试集,以及如何选定最优的阈值产生影响。有兴趣的可以来试一试,反正我觉得自己是把能踩的坑都踩了一个遍,欢迎大家一起来踩坑 >_<


Reference

  1. Alaa Tharwat,Classification assessment methods,Applied Computing and Informatics
  2. Nan Ye,Kian Ming A. Chai,Wee Sun Lee,Hai Leong Chieu,Optimizing F-Measures: A Tale of Two Approaches,
  3. https://en.wikipedia.org/wiki/Confusion_matrix

Binary classification - 聊聊评价指标的那些事儿【回忆篇】的更多相关文章

  1. Binary classification - 聊聊评价指标的那些事儿【实战篇】

    分类问题就像披着羊皮的狼,看起来天真无害用起来天雷滚滚.比如在建模前你思考过下面的问题么? 你的分类模型输出的概率只是用来做样本间的相对排序,还是概率本身? 你的训练数据本身分布如何是否存在Imbal ...

  2. Logistic Regression Using Gradient Descent -- Binary Classification 代码实现

    1. 原理 Cost function Theta 2. Python # -*- coding:utf8 -*- import numpy as np import matplotlib.pyplo ...

  3. 【Linear Models for Binary Classification】林轩田机器学习基石

    首先回顾了几个Linear Model的共性:都是算出来一个score,然后做某种变化处理. 既然Linear Model有各种好处(训练时间,公式简单),那如何把Linear Regression给 ...

  4. 聊聊多线程哪一些事儿(task)之 一

    多线程,一个多么熟悉的词汇,作为一名程序员,我相信无论是从事什么开发语言,都能够轻轻松松说出几种实现多线程的方式,并且在实际工作种也一定用到过多线程,比如:定时器.异步作业等等,如果你说你没有用过多线 ...

  5. 聊聊多线程哪一些事儿(task)之 二 延续操作

    hello,又见面啦,昨天我们简单的介绍了如何去创建和运行一个task.如何实现task的同步执行.如何阻塞等待task集合的执行完毕等待,昨天讲的是task的最基本的知识点,如果你没有看昨天的博客, ...

  6. 聊聊多线程那一些事儿(task)之 三 异步取消和异步方法

    hello,咋们又见面啦,通过前面两篇文章的介绍,对task的创建.运行.阻塞.同步.延续操作等都有了很好的认识和使用,结合实际的场景介绍,这样一来在实际的工作中也能够解决很大一部分的关于多线程的业务 ...

  7. 聊聊多线程哪一些事儿(task)之 三 异步取消和异步方法

    hello,咋们又见面啦,通过前面两篇文章的介绍,对task的创建.运行.阻塞.同步.延续操作等都有了很好的认识和使用,结合实际的场景介绍,这样一来在实际的工作中也能够解决很大一部分的关于多线程的业务 ...

  8. 聊聊多线程那一些事儿 之 五 async.await深度剖析

     hello task,咱们又见面啦!!是不是觉得很熟读的开场白,哈哈你哟这感觉那就对了,说明你已经阅读过了我总结的前面4篇关于task的文章,谢谢支持!感觉不熟悉的也没有关系,在文章末尾我会列出前四 ...

  9. 聊聊RabbitMQ那一些事儿之一基础应用

    聊聊RabbitMQ那一些事儿之一基础应用 Hi,各位热爱技术的小伙伴您们好,今年的疫情害人啊,真心祝愿您和您的家人大家都平平安安,健健康康.年前到现在一直没有总结点东西,写点东西,不然久了自己感觉自 ...

随机推荐

  1. SQL2008错误:当 MUST_CHANGE 为 ON (开)时,不能将 CHECK_POLICY 和 CHECK_EXPIRATION 选项设为 OFF (关)。

    假设出现这样的情况,第一个选择是: 在数据库用户管理中去掉了"强制password过期"! 假设把"强制实施password策略"的勾也去掉了,出现例如以下错误 ...

  2. SSH框架的搭建与配置文件的书写格式

    通常Java Web 开发的时候,我们一般会采用三大框框架的整合来架构,这样做主要是为方便维护.但是有时候会忘了一些配文件(*.xml)的格式头,这里主要就三大框架Spring.struts.hibe ...

  3. 使用XCA(X Certificate and key management)可视化项目经理SSL 凭证(4)--凭借自身的凭证管理中心的定义(Certificate Authority)签名证书申请

    随着XCA(X Certificate and key management)可视化项目经理SSL 证书系列文章(2)和(3)中.我们学习了怎样用XCA(X Certificate and key m ...

  4. BLAS 与 Intel MKL 数学库

    0. BLAS BLAS(Basic Linear Algebra Subprograms)描述和定义线性代数运算的规范(specification),而不是一种具体实现,对其的实现包括: AMD C ...

  5. 极简代码(七)—— SNR

    10⋅log10∑x=1Nx∑y=1Nyf2(x,y)∑x=1Nx∑y=1Ny(f(x,y)−f^(x,y))2 这里不妨先用 matlab 所支持的函数对象(函数式编程)定义这样一个函数变量,可作为 ...

  6. Bootstrap Button 使用方法

    Getting Started <!-- basic button --> <com.beardedhen.androidbootstrap.BootstrapButton andr ...

  7. C#调用JS

    cmd调用phantomjs 官方资料:http://phantomjs.org/quick-start.html 手动执行 从官方下载phantomjs.exe,拷贝它与要执行的js同目录打开cmd ...

  8. 【码云周刊第 22 期】GO :互联网时代的 C 语言!

    技术干货 标签:独家译文 1.Go 很好,为什么我们不使用它? 在这篇文章中,我将分享一下为什么我认为它很棒,使用它的一些缺点,以及为什么它还不是我们 Zapier 堆栈中的一部分. 2.从 Scal ...

  9. glibc内存管理方式

    程序员接触的内存空间和系统接触的物理内存空间是有所区别的.对于一般进程来讲,他面对的是一个线性虚拟内存空间:地址从0到最大值.每一个进程面对的虚拟内存空间都是一样的,都享有全部的内存地址.虚拟内存空间 ...

  10. 如何在XAML中转义大括号

    原文:如何在XAML中转义大括号 如何在XAML中转义大括号                                       周银辉 我们知道大括号"{}"在XAML中 ...