关注教AI的郑老师,和我一起成长。
精确率、召回率、准确率、F1值、ROC和AUC这几个指标在分类问题中经常使用,用来衡量模型的能力,因此了解它们的确切含义以及如何调用中的相应函数,是十分有必要的。
精确率、召回率、准确率
对于一个两分类问题,它有正例和负例。
TP:True 。预测为1,实际为1,预测正确。
FP:False 。预测为1,实际为0,预测错误。
FN:False 。预测为0,实际为1,预测错误。
TN:True 。预测为0,实际为0,预测正确。
TP和TN表示预测对了,FP和FN表示预测错了。
;How many items are 。精确率,又叫查准率,不是准确率,
; How many items are 。召回率,又叫查全率,
;How many items are hit。准确率,使用最多的,
Error= 1 - ; How many items are ,为错误率。
这四个概念非常重要。
准确率表示做对的部分与所有样本的比例。
精确率表示预测为正例的样本中,多少为真正的正例。为什么选它,因为它被预测为正例了。但是选出来后,发现他们不完全是正例。
为什么关心精确率,因为一般而言,对于一个模型,我们只关心预测为正例的那些样本。比如去医院检查,有个机器可以自动帮你诊疗,我们会关心机器会不会把你诊断为阳性(正例)。被诊断为正例的样本就有可能要进行后续的治疗或检查。筛选出为负例的样本就不再管了。
召回率是指所有的正例中,你预测出了多少。
上面的概念在实际中应用得非常广泛。比如我查询 ,搜索引擎返回给了我100条信息,这100条就是预测的正例。因为搜索引擎把它预测为正例,所以才返回给我。经查看,只有30条是相关的。所以精确率是30%。精确率并不高,但对我已经够用了。
召回率的意思是在某次搜索中,真实样例可能是不知道的,你必须遍历整个搜索引擎的后台,你才能知道多少是负例,多少是正例。
F指数是精确率和召回率的调和平均数。根据调和平均的性质,我们知道,只要P和R有一个是小的,F就小。若F较大,就意味着P和R均较大。
也就有了混淆矩阵 。
如果模型不够准确,到底是哪一类错误,是错分成哪一类带来的,一个模型并不是所有类都做错了,我们需要debug这个模型。需要通过指标debug这个模型。比如是不是把猫和老虎混淆了,然后去改进你的特征提取的过程,使得后续模型更加准确。
指标计算
预测标签= [0,1,1,0,0,0,1,0,0,0],
真实标签= [0,0,1,1,0,0,1,1,0,0]
混淆矩阵中,TP=2,FP=1, FN=2,TN=5。
=(TP+TN) / 10 = 0.7
P = (TP) / (TP + FP) = 2 / 3 = 0.67
R = (TP) / (TP + FN) = 2 / 4 = 0.5
F1 = 2PR / (P + R) = 0.57
准确率虽然有0.7,但是F1值只有0.4,因此模型的情感分类能力其实是很差的,10个样本中有4个,然而模型只预测出了两个,所以召回率很低,进而导致了F1值很低。
from sklearn.metrics import *
import matplotlib.pyplot as plt
y_pred = [0, 1, 1, 0, 0, 0, 1, 0, 0, 0]
y_true = [0, 0, 1, 1, 0, 0, 1, 1, 0, 0]
# 准确率
## normalize=False返回做对的个数,normalize=True返回做对的占比
acc = accuracy_score(y_true, y_pred)
acc_nums = accuracy_score(y_true, y_pred, normalize=False)
print(acc, acc_nums) # 0.7 7
0.7 7
# 由于是二分类问题,所有其他参数都使用默认,只需要输入y_true和y_pred
# 精确率
p = precision_score(y_true, y_pred)
# 召回率
r = recall_score(y_true, y_pred)
# f1-score
f1 = f1_score(y_true, y_pred)
print(p, r, f1) # 0.6666666666666666 0.5 0.5714285714285715
0. 0.5 0.57715
matrix=confusion_matrix(y_true,y_pred)
print(matrix)
disp = ConfusionMatrixDisplay(confusion_matrix=matrix)
disp.plot()
plt.show()
[[5 1]
[2 2]]
ROC 和 AUC
前面提出的指标中,如果类别不平衡,比如在医院诊断时,大部分人都没有病,比如只有0.1%会犯某一个病,这时会出现真实的正例很少,真实的负例却极多的情况,数据类别极度不平衡时,这些准则都可能会失效。
比方说在一个10000个人的数据集中,实际有100个人得了某种病症,你的任务是来预测哪些人得了这种病症。你预测出了200人得了癌症,其中:
TP,True :得了癌症而且你也预测出来的病人有60人;
FP,False :没有的癌症但是你预测得了癌症的有140人。
TN,True :没有得癌症并且你也预测对没有得癌症的有9760人;
FN,False :得了癌症但是你没有预测出来的病人有40人;
那么:
True Rate(TPR): 60/(60+40)=0.6
False Rate(FPR): 140/(9760+140)=0.0141
: (9760+60)/10000=0.982
: 60/(60+140)=0.3
: 60/100=0.6
简单的说,在上述癌症检测中(正反例极度不平衡的情况下),意义不大,从结果中可看出,因为正例比较少,所以检测再不怎么准确,其值都很高。则是相对于真实情况而言的,你正确检测了60例癌症病人,总癌症病人有100例,那么则为60%。则是相对于模型预测情况而言的,你预测了200例癌症病人,其中预测准确的有60例,那么则为30%;所以我们是希望能看到模型的和都很高,但是一般两者难以同时达到最优值,需要做一个权衡。——AUC和ROC可用来评判二分类的权衡召回率,即评估算法模型的泛化能力。
ROC, ,接受者操纵指数
ROC 曲线图是反映敏感性与特异性之间关系的曲线。
对于两分类问题,所谓的不平衡体现在边缘分布上。P(Y=1)=0.01, P(Y=0)=0.99,
在基础上考虑下面两个准则:真实正例预测为正例的概率以及真实负例预测为负例的概率。他们不会受到类别比例平衡的影响,也就解决了类别不平衡问题。
边缘概率:
敏感度
特异度
ROC就是以FPR为横轴,TPR为纵轴的曲线,ROC下方的面积被称为AUC(Area Under the Curve)。
通过调整模型的不同参数,就可以输出不一样的正负例,TPR和FPR的值就会发生变化,从0变化到1。
最为常见的是分类问题,你需要取阈值,比如0.5预测为正例,0.2预测为负例。在你调整阈值的时候,模型预测结果是不一样的,因而你可以画出一条曲线来。
显然,这条曲线靠上,面积接近1时,这个模型是好的。意味着能将正例预测为正例的同时,还能将负例预测为负例,而不管正负例之间的不平衡。因为这两个概率与类别不平衡是没有关系的。
如在医学诊断中,判断有病的样本。那么尽量把有病的揪出来是主要任务,也就是指标TPR要越高越好。而把没病的样本误诊为有病的,也就是指标FPR要越低越好。
不难发现,这两个指标之间是相互制约的。如果某个医生对于有病的症状比较敏感,稍微的小症状都判断为有病,那么他的TPR指标应该会很高,但是FPR指标也就相应地变高。最极端的情况下,他把所有的样本都看做有病,那么TPR达到1,FPR指标也为1。
左上角的点(FPR=0,TPR=1),为完美分类,也就是这个医生医术高明,诊断全对。点(TPR>FPR),医生的判断大体是正确的。
中线上的点(TPR=FPR),也就是医生全都是蒙的,蒙对一半召回率,蒙错一半。
下半平面的点(TPR,这个医生说你有病,那么你很可能没有病,医生的话我们要反着听,为真庸医。
一个阈值,得到一个点。现在我们需要一个独立于阈值的评价指标来衡量这个医生的医术如何,也就是遍历所有的阈值,得到ROC曲线。曲线距离左上角越近,证明分类器效果越好。
它的统计含义是对于样例(x+,x-),一个是真实的正例,一个是真实的负例,分类结果为(y+,y-),模型也预测出P(y+>y-)的概率就是AUC。机器学习不一定输出y+>y-。输出概率越大,说明模型越准确。
import matplotlib.pyplot as plt
import numpy as np
from sklearn import metrics
y = np.array([0, 0, 1, 1])
pred = np.array([0.1, 0.4, 0.35, 0.8])
fpr, tpr, thresholds = metrics.roc_curve(y, pred)
print(fpr)
print(tpr)
print(thresholds)
[0. 0. 0.5 0.5 1. ]
[0. 0.5 0.5 1. 1. ]
[1.8 0.8 0.4 0.35 0.1 ]
roc_auc = metrics.auc(fpr, tpr)
print(roc_auc)#auc面积
display = metrics.RocCurveDisplay(fpr=fpr, tpr=tpr, roc_auc=roc_auc,
estimator_name='example estimator')
display.plot()
plt.show()
0.75
回归误差
平均误差受离群点影响很大,鲁棒性不好,应用中多使用绝对误差,没有平方,相对较小。
如果更好,就取平方对数误差。如果是指数变化,不管你采用平方误差还是绝对值误差,都会很大,比如中国人口,可以刻画一些变化特别大的变量。
绝对值比例误差,如果你的样本差异特别大,前面的指标均失效。比如,不同样本的范围不一样。归一化然后计算比较有意义。
这些指标均来源于实际,指标的使用决定了你后续模型的好坏。
如果大家喜欢我的文章,欢迎点个在看,转发到朋友圈,带动更多的ta来享受编程的快乐!
你好,我是郑开心,
一个持续专注于个人成长、专业精进的计算机专业教师。
希望通过写作和短视频影响更多的人一起成为更好的自己。
扫码添加我的微信,咱们一起成长。
限时特惠:本站持续每日更新海量各大内部创业课程,一年会员仅需要98元,全站资源免费下载
点击查看详情
站长微信:Jiucxh