ROC曲线及AUC值[通俗易懂]

ROC曲线及AUC值[通俗易懂]ROC曲线参考文献:【ROC曲线与AUC值】1.介绍及引入ROC的全名叫做ReceiverOperatingCharacteristic,其主要分析工具是一个画在二维平面上的曲线——ROCcurve。平面的横坐标是falsepositiverate(FPR),即假阳性率(1−Sp1-Sp1−Sp);纵坐标是truepositiverate(TPR),即真阳性率(SnSnSn)。对某个分类器而言,我们可以根据其在测试样本上的表现得到一个TPR和FPR点对。这样,此分类器就可以映射成

大家好,又见面了,我是你们的朋友全栈君。

ROC曲线及AUC值

参考文献:【ROC曲线与AUC值】【ROC,AUC最透彻的讲解(实例分析+matlab代码)】【AUC计算方法与Python实现】【AUC曲线计算方法及代码实现】

1. 介绍及引入

ROC的全名叫做Receiver Operating Characteristic,其主要分析工具是一个画在二维平面上的曲线——ROC curve。平面的横坐标是False Positive Rate(FPR),即假阳性率( 1 − S p 1-Sp 1Sp);纵坐标是True Positive Rate(TPR),即真阳性率( S n Sn Sn)。

对某个分类器而言,我们可以根据其在测试样本上的表现得到一个TPRFPR点对。这样,此分类器就可以映射成ROC平面上的一个点。调整这个分类器分类时候使用的阈值,我们就可以得到一个经过(0, 0)(1, 1)的曲线,这就是此分类器的ROC曲线

一般情况下,这个曲线都应该处于(0, 0)(1, 1)连线的上方。因为(0, 0)(1, 1)连线形成的ROC曲线实际上代表的是一个随机分类器。

(0,0)代表一种极端情况,即判定样本全为阴性;(1,1)则代表判断样本全为阳性

如果很不幸,你得到一个位于此直线下方的分类器的话,一个直观的补救办法就是把所有的预测结果反向,即:分类器输出结果为正类,则最终分类的结果为负类,反之,则为正类。虽然,用ROC curve来表示分类器的Performance很直观好用。可是,人们总是希望能有一个数值来标志分类器的好坏。于是Area Under roc Curve(AUC)就出现了。

顾名思义,AUC的值就是处于ROC curve下方的那部分面积的大小。通常,AUC的值介于0.51.0之间,较大的AUC代表了较好的performance

2. ROC的动机

对于01两类分类问题,一些分类器得到的往往不是01这样的标签,如神经网络得到诸如0.50.8这样的分类结果。这时我们人为取一个阈值,比如0.4,那么小于0.4的归为0类,大于等于0.4的归为1类,可以得到一个分类结果。
ROC曲线及AUC值[通俗易懂]

图中虚线C代表0类,虚线A代表1类,实线B代表人为划定的阈值(介于0~1

蓝色表示原始为阴性分类得到的统计图,红色表示原始为阳性得到的统计图。

那么我们取一条直线,直线左边分为负类,直线右边分为正类,这条直线也就是我们人为所取的阈值。

阈值不同,可以得到不同的结果,但是由分类器决定的统计图始终是不变的。这时候就需要一个独立于阈值,只与分类器有关的评价指标,来衡量特定分类器的好坏。还有在类不平衡的情况下,如正样本有90个,负样本有10个,直接把所有样本分类为正样本,得到识别率为90%,但这显然是没有意义的。如上就是ROC曲线的动机

3. ROC的定义

关于两类分类问题,原始类为PositiveNegative,分类后得到四个指标,分别为:真阳、假阳、假阴、真阴。ROC空间将假阳性率( F P R FPR FPR)定义为 X X X轴,真阳性率( T P R TPR TPR)定义为 Y Y Y轴。
公式如下:

  • TPR:在所有实际为阳性的样本中,被正确地判断为阳性之比率。 T P R ( S n ) = T P / ( T P + F N ) TPR(Sn)=TP/(TP+FN) TPR(Sn)=TP/(TP+FN)
  • FPR:在所有实际为阴性的样本中,被错误地判断为阳性之比率。 F P R ( 1 − S p ) = F P / ( F P + T N ) FPR(1-Sp)=FP/(FP+TN) FPR(1Sp)=FP/(FP+TN)

形象解释
在医学诊断中,判断有病的样本。那么尽量把有病的揪出来是主要任务,也就是第一个指标TPR,要越高越好。而把没病的样本误诊为有病的,也就是第二个指标FPR,要越低越好。不难发现,这两个指标之间是相互制约的。如果某个医生对于有病的症状比较敏感,稍微的小症状都判断为有病,那么他的第一个指标应该会很高,但是第二个指标也就相应地变高。最极端的情况下,他把所有的样本都看做有病,那么第一个指标达到1,第二个指标也为1。

4. ROC的图形化表示

FPR为横轴,TPR为纵轴,得到如下ROC空间:
ROC曲线及AUC值[通俗易懂]

将图中每个点视为不同医生的诊断水平,则有如下形象化地判断:

  1. 左上角的点(TPR=1,FPR=0),为完美分类,说明该医生诊断全对;
  2. 点A(TPR>FPR),医生A的判断大体是正确的
  3. 中线上的点B(TPR=FPR),也就是医生B全都是蒙的,蒙对一半,蒙错一半;
  4. 下半平面的点C(TPR<FPR),这个医生说你有病,那么你很可能没有病,医生C的话我们要反着听。

上图中一个阈值,得到一个点。不同的点代表不同的阈值。为了得到一个独立于阈值的评价指标来衡量这个医生的医术如何,也就是遍历所有的阈值,得到ROC曲线。假设如下就是某个医生的诊断统计图,直线代表阈值。我们遍历所有的阈值,能够在ROC平面上得到如下的ROC曲线。
ROC曲线及AUC值[通俗易懂]

曲线距离左上角越近,证明分类器效果越好。
ROC曲线及AUC值[通俗易懂]

如上图,有三条ROC曲线,在0.23处取一条直线。那么,在同样的FPR=0.23的情况下,红色分类器得到更高的TPR。也就表明,ROC越往上,分类器效果越好。可以用一个标量值AUC来量化它。

5. 如何绘制ROC曲线

假设已经得出一系列样本被划分为正类的概率,然后按照大小排序,下图是一个示例,图中共有20个测试样本, “ C l a s s ” “Class” Class一栏表示每个测试样本原始的标签( p p p表示正样本, n n n表示负样本), “ S c o r e ” “Score” Score表示每个测试样本属于正样本的概率。总计有10个正样本和10个负样本,从高到低,依次将 ” S c o r e ” “Score” Score值作为阈值 t h r e s h o l d threshold threshold,当测试样本属于正样本的概率大于或等于这 t h r e s h o l d threshold threshold时,我们认为它为正样本,否则为负样本。

Inst# Class Score (TPR,FPR)
1 p 0.9 (0.1,0)
2 p 0.8 (0.2,0)
3 n 0.7 (0.2,0.1)
4 p 0.6 (0.3,0.1)
5 p 0.55 (0.4,0.1)
6 p 0.54 (0.5,0.1)
7 n 0.53 (0.5,0.2)
8 n 0.52 (0.5,0.3)
9 p 0.51 (0.6,0.3)
10 n 0.505 (0.6,0.4)
11 p 0.4 (0.7,0.4)
12 n 0.39 (0.7,0.5)
13 p 0.38 (0.8,0.5)
14 n 0.37 (0.8,0.6)
15 n 0.36 (0.8,0.7)
16 n 0.35 (0.8,0.8)
17 p 0.34 (0.9,0.8)
18 n 0.33 (0.9,0.9)
19 p 0.30 (1.0,0.9)
20 n 0.1 (1.0,1.0)

在ROC空间平面上描的点
ROC曲线及AUC值[通俗易懂]

6. AUC值

6.1 AUC值的定义

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

  1. AUC=1,是完美分类器,采用这个预测模型时,不管设定什么阈值都能得出完美预测。然而绝大多数预测场合,不存在完美分类器。
  2. 0.5 < AUC < 1,优于随机猜测。这个分类器如果妥善设定阈值的话,能有预测价值。
  3. AUC=0.5,跟随机猜测一样,模型没有预测价值。
  4. AUC<0.5,比随机猜测还差;但是可以反预测而行,就优于随机猜测。

6.2 AUC值的物理意义

假设分类器的输出是样本属于正类的score(置信度),则AUC的物理意义为任取一对(正、负)样本,正样本的score大于负样本的score的概率

6.3 AUC值的计算

  1. AUC为ROC曲线下的面积,那我们直接计算面积可得。面积为一个个小的梯形面积之和,计算的精度与阈值的精度有关。
  2. 根据AUC的物理意义,我们计算正样本score大于负样本的score的概率。取N*MN为正样本数,M为负样本数)个二元组,比较score,最后得到AUC。时间复杂度为 O ( N ∗ M ) O(N*M) O(NM)
  3. 与第二种方法相似,直接计算正样本score大于负样本的score的概率。我们首先把所有样本按照score排序,依次用rank表示他们,如最大score的样本,rank=n(n=N+M),其次为n-1。那么对于正样本中rank最大的样本(rank_max),有M-1个其他正样本比他score小,那么就有(rank_max-1)-(M-1)个负样本比它score小。其次为(rank_second-1)-(M-2)。最后我们得到正样本大于负样本的概率为:
    A U C = ( ∑ i ∈ P o s i t i v e S a m p l e s r a n k i ) − M ( M + 1 ) / 2 M ∗ N AUC=\frac{(\sum_{i \in Positive Samples} rank_i)-M(M+1)/2}{M*N} AUC=MN(iPositiveSamplesranki)M(M+1)/2
    时间复杂度为 O ( N + M ) O(N+M) O(N+M)

自定义算法

import numpy as np
def calAUC(y_labels,y_scores):
    f = list(zip(y_scores, y_labels))
    rank = [values2 for values1, values2 in sorted(f, key=lambda x:x[0])]
    rankList = [i+1 for i in range(len(rank)) if rank[i] == 1]
    pos_cnt = np.sum(y_labels == 1)
    neg_cnt = np.sum(y_labels == 0)
    auc = (np.sum(rankList) - pos_cnt*(pos_cnt+1)/2) / (pos_cnt*neg_cnt)
    return auc
# 其中输入y_scores是得到的概率值,y_labels是分类的标签(1,0)

从sklearn库中调用

from sklearn.metrics import roc_auc_score
# 调用方法:roc_auc_score(y_labels, y_scores)

随机数据生成函数及调用方法

def get_score():
    # 随机生成100组label和score
    y_labels = np.zeros(100)
    y_scores = np.zeros(100)
    for i in range(100):
        y_labels[i] = np.random.choice([0, 1])
        y_scores[i] = np.random.random()
    return y_labels, y_scores

if __name__ == '__main__':
    y_labels, y_scores = get_score()
    # 调用sklearn中的方法计算AUC,与后面自己写的方法作对比
    print('sklearn AUC:', roc_auc_score(y_labels, y_scores))
    print('diy AUC:',calAUC(y_labels, y_scores))
版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请联系我们举报,一经查实,本站将立刻删除。

发布者:全栈程序员-站长,转载请注明出处:https://javaforall.net/145820.html原文链接:https://javaforall.net

(0)
全栈程序员-站长的头像全栈程序员-站长


相关推荐

  • 年度总结与来年计划_2016年一2021的工作总结

    年度总结与来年计划_2016年一2021的工作总结  光阴似箭,日月如梭!眨眼间已到年底,今年感慨颇丰,获益良多。因为我认为努力了就肯定会有收获,哪怕是收获那一滴滴辛勤的汗水。  我在公司任务轻松时,加了些前端群(重点推荐豪情群),在群里分享技术以及生活的点滴,同时认识了一些志同道合的朋友。有大牛建议我体验一番分享的乐趣,于是我下下半年开始写博。虽质量不高,但其中的乐趣博友们应该都能感受到。写完每篇博文后,我都能体会到了在这个浮躁的时代我平静…

    2025年9月4日
    3
  • java 4种 布局方法_JAVA布局模式:GridBagConstraints终极技巧

    java 4种 布局方法_JAVA布局模式:GridBagConstraints终极技巧JAVA布局模式:GridBagConstraints终极技巧(2006-11-1421:07:33)最近正在修改《公交线路查询系统》,做系统的时候都是用NULL布局,由于NULL布局调用windows系统的API,所以生成的程序无法在其他平台上应用,而且如果控件的数量很多,管理起来也比较麻烦,最近我发现一个非常强大的布局模式:GridBagConstraints布局,先发一个实例:gridx…

    2022年9月9日
    3
  • cf名字空格符号复制_字符为空格怎么表示

    cf名字空格符号复制_字符为空格怎么表示CF室内空间的姓名如何打?许多CF游戏玩家在游戏里面常常碰到角色名有空格符的状况,可是在建立CF人物角色的情况下,不管怎样也不可以根据按空白键让自身的姓名有空格符。下边的兔子游戏系列产品详解了怎样在CF游戏角色名字中应用空格符。第一步,保证电脑安裝了智能ABC电脑输入法。如今许多游戏玩家的电脑操作系统全是WIN7,可是WIN7一般沒有安裝智能ABC,因此必须下载一个智能ABC电脑输入法(下…

    2022年9月22日
    0
  • 2020最新版Net加壳工具

    2020最新版Net加壳工具VirboxProtector发布最新版本Net加壳工具:VirboxProtector2.VirboxProtector为.NETFramework编写的软件做代码保护,防止代码被反编译,防止IL代码在内存被Dump。同时可配合授权产品实现软件的许可管理。加密技术VirboxProtector.NET版通过多种保护方式来防止反编译,加密后可让任何现有工具都无法反编译。JIT加密将.NET所有方法的IL指令经过加密,仅在.NET虚拟机进行J.

    2022年6月27日
    80
  • MySQL (4) 第一范式 第二范式 第三范式 BC范式

    MySQL (4) 第一范式 第二范式 第三范式 BC范式第一范式第一范式:所有属性都是不可分割的原子值。也就是每个属性都是不可再分的。例如下图就不符合第一范式的要求实际上,1NF是所有关系型数据库的最基本要求,你在关系型数据库管理系统(RDBMS),例如SQLServer,Oracle,MySQL中创建数据表的时候,如果数据表的设计不符合这个最基本的要求,那么操作一定是不能成功的。如果我们要在RDBMS中表现表中的数据,就得设计为下图的

    2022年5月23日
    48
  • fast使用教程_ai基础教程入门图文

    fast使用教程_ai基础教程入门图文https://docs.fast.ai/如何利用好FASTAI——新版本fastai-v1.0快速入门https://m.oldpan.me/archives/fastai-1-0-quick-study

    2025年8月27日
    7

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

关注全栈程序员社区公众号