metrics.roc_curve()输出的tpr或fpr的结果为nan

本文深入探讨了在使用sklearn.metrics.roc_curve()函数时,tpr和fpr出现NaN值的原因,主要归咎于标签数据中缺乏正负样本。通过源码分析,解释了在正样本或负样本缺失的情况下,警告信息的触发机制及如何避免此类问题。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

在用metrics.roc_curve()函数计算tpr的时候,出现tpr为nan的情况,主要是因为label里面没有正样本的标签。

下面是roc_curve()里面的一段源码,其中tps[-1]存放的是所有的正样本。同理,如果fpr出现nan的情况是因为label里面没有负样本。

 if fps[-1] <= 0:
        warnings.warn("No negative samples in y_true, "
                      "false positive value should be meaningless",
                      UndefinedMetricWarning)
        fpr = np.repeat(np.nan, fps.shape)
    else:
        fpr = fps / fps[-1]

    if tps[-1] <= 0:
        warnings.warn("No positive samples in y_true, "
                      "true positive value should be meaningless",
                      UndefinedMetricWarning)
        tpr = np.repeat(np.nan, tps.shape)
    else:
        tpr = tps / tps[-1]

我们来看个?,正样本的标签为2,负样本的标签为1:

from sklearn import metrics
import numpy as np

y = np.array([1,1,1,1])
scores = scores = np.array([0.1, 0.4, 0.35, 0.8])
fpr, tpr, thresholds = metrics.roc_curve(y, scores, pos_label=2)

 因为样本中没有怎样本,所以tpr的值就为nan

tpr
Out[16]: array([nan, nan, nan])

 

import pandas as pd import numpy as np import matplotlib.pyplot as plt from sklearn.linear_model import LogisticRegression from sklearn.metrics import confusion_matrix, classification_report # 设置默认字体和解决负号显示问题 plt.rcParams['font.sans-serif'] = ['SimHei'] plt.rcParams['axes.unicode_minus'] = False # 读取数据 data = pd.read_excel(r'C:\Users\冯雪玲\Desktop\北京市空气质量数据.xlsx') # 修正拼写错误 read_excel → read_excel data = data.replace(0, np.nan) # 替换0值为NaN data = data.dropna() # 删除缺失值 # 创建目标变量 # 修正字典语法错误(冒号→逗号,删除多余小数点) data['有无污染'] = data['质量等级'].map({ '优': 0, '良': 0, '轻度污染': 1, '中度污染': 1, # 修正 1.'重度污染' → 1, '重度污染': 1, '严重污染': 1}) # 划分特征与标签 X = data.loc[:, ['PM2.5', 'PM10', 'SO2', 'CO', 'NO2', 'O3']] Y = data.loc[:, '有无污染'] # 模型训练与评估 modelNB = GaussianNB() modelNB.fit(X, Y) modelLR = LogisticRegression() modelLR.fit(X, Y) # 输出朴素贝叶斯模型结果 print('朴素贝叶斯模型结果:\n', classification_report(Y, modelNB.predict(X))) import matplotlib.pyplot as plt from sklearn.metrics import roc_curve, auc, precision_recall_curve # --------------------- 绘图代码 --------------------- fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(10,4)) # ROC曲线 fpr, tpr, _ = roc_curve(Y, modelNB.predict_proba(X)[:, 1], pos_label=1) fpr1, tpr1, _ = roc_curve(Y, modelLR.predict_proba(X)[:, 1], pos_label=1) axes[0].plot(fpr, tpr, color='r', label=f'朴素贝叶斯 ROC (AUC={auc(fpr, tpr):.3f})') axes[0].plot(fpr1, tpr1, color='blue', label=f'逻辑回归 ROC (AUC={auc(fpr1, tpr1):.3f})') axes[0].plot([0, 1], [0, 1], linestyle='--', color='navy') axes[0].set(xlabel='假正率 (FPR)', ylabel='真正率 (TPR)', title='ROC曲线对比') axes[0].legend() # PR曲线 pre, rec, _ = precision_recall_curve(Y, modelNB.predict_proba(X)[:, 1], pos_label=1) pre1, rec1, _ = precision_recall_curve(Y, modelLR.predict_proba(X)[:, 1], pos_label=1) axes[1].plot(rec, pre, color='r', label=f'朴素贝叶斯 (AP={auc(rec, pre):.3f})') axes[1].plot(rec1, pre1, color='blue', label=f'逻辑回归 (AP={auc(rec1, pre1):.3f})') axes[1].set(xlabel='召回率 (Recall)', ylabel='精确率 (Precision)', title='P-R曲线对比') axes[1].legend() plt.tight_layout() plt.show()解析代码
03-29
·贝叶斯分类器的应用:空气质量等级的贝叶斯分类 data=pd. read excel('北京市空气质量数据.xlsx') data-data. replace(0.np.NaN) data-data_ dropna ( data[有无污染]=data[’质量等级'].map({’优':0,'良':0,"轻度污染':1,"中度污染':1,"重度污染':1,"严重污染':1}) data["有无污染'1.value counts0 X-data.loc[:,['PM2.5',"PM10’,'s02','c0','N02' ,' 03' ]] 1|fig,axes-plt. subplots(nrows-l,ncols-2,figsize-(10,4)) Y-data.loc[:,’有无污染'] fpr,tpr,thresholds - roc_curve(Y,modelNB.predict_proba(X)[:,1), pos_label-1) fprl,tprl, thresholds1 - roc_curve (Y,modelLR. predict_proba(X)[:,1], pos_labe1-1) modelNB -GaussianNB() axes[0].plot(fpr, tpr, color-'r',label-'贝叶斯ROC(AUC - %0.5f)’% auc (fpr,tpr)) 10 modelNB.fit(X, Y) axes[0].plot(fpr1, tpr1, color='blue', linestyle='-.',label-'Logistic回归ROC(AUC = %0.5f)’% auc(fpr1,tpr1)) modelLR-LM. LogisticRegression () axes[0].plot([0,1],[0,1],color-'navy', linewidth-2, linestyle='--') modelLR.fit(X,Y) print('评价模型结果:\n',classification_report (Y,modelNB. predict (X))) axes[0].set_ylim([-0.01,1.01]) axes[0].set_xlin([-0.01,1.01]) 9 axes[0].set_xlabel ('FPR') 评价模型结果: 10 axes[0].set vlabel('TPR') precision recall fl-score support 11 axes[0].set_title('两个分类模型的ROC曲线') 12 axes[0].legend(loc="lower right") 0.86 0.94 0.90 1204 1 0.90 0.79 0.84 892 14 pre, rec, thresholds = precision_recall_curve(Y,modelNB.predict_proba(X)[:,1], pos_labe1-1) 15 prel, recl, thresholds1 -precision_recall_curve(Y,modelLR. predict_proba(X)[:,1], pos_labe1=1) accuracy 0.88 2096 16 axes[1]. plot (rec, pre, color='r', label='贝叶斯总正确率= %0.3f)’% accuracy_score(Y,modelNB. predict (X))) weighted avg macro avg 0.88 0.88 0.87 0.88 0.87 0.87 2096 2096 18 axes[1]. plot ([0,1],[1,pre.min(],color='navy', linewidth=2, linestyle='--') 17 axes[1]. plot (rec1, pre1, color='blue', linestyle=' -.',label='Logistic回归总正确率= %0.3f)’% accuracy_score(Y,modelLR. predict (X))) 19 axes[1l.set xlim([-0.01.1.01]) 两个分类模型的ROC曲线 两个分类模型的P-R曲线 20 axes[1].set_ylim([pre.min()-0.01,1.01]) 1.00 21 axes[1].set_xlabel('查全率R axes[1].set_ylabel('查准率) 05 23 axes[1].set_title("两个分类模型的P-R曲线) 24 axes[1].legend(loc-'lower left') 090 25 plt.show() 000 贝叶斯ROC(ALC=0.96177) 0.75 同叶期总正确率:0.876 LogintiofR0(MIG=0.9017E - Legistic国归总正确率=0921) 修改成正确的代码
03-27
import pandas as pd import numpy as np import matplotlib.pyplot as plt from sklearn.linear_model import LogisticRegression from sklearn.metrics import confusion_matrix, classification_report # 设置默认字体和解决负号显示问题 plt.rcParams['font.sans-serif'] = ['SimHei'] plt.rcParams['axes.unicode_minus'] = False # 读取数据 data = pd.read_excel(r'C:\Users\冯雪玲\Desktop\北京市空气质量数据.xlsx') data = data.replace(0, np.nan) # 替换0值为缺失值 data = data.dropna() # 删除缺失值 data['有无污染'] = data['质量等级'].map({'优': 0, '良': 0, '轻度污染': 1, '中度污染': 1, '重度污染': 1, '严重污染': 1}) # 目标变量转换(确保字典键使用英文引号) quality_mapping = {'优':0, '良':0, '轻度污染':1, '中度污染':1, '重度污染':1, '严重污染':1} data['有无污染'] = data['质量等级'].map(quality_mapping) # 2. 特征与目标变量定义 X = data.loc[:, ['PM2.5', 'PM10', 'SO2', 'CO', 'NO2', 'O3']] # 修正列名大小写和空格 y = data.loc[:, '有无污染'] # 确保列名与数据一致 # 3. 模型训练 modelNB = GaussianNB() modelNB.fit(X, y) modelLR = LogisticRegression(max_iter=1000) # 增加迭代次数确保收敛 modelLR.fit(X, y) # 4. 模型评估 print("贝叶斯分类器报告:\n", classification_report(y, modelNB.predict(X))) print("\n逻辑回归分类器报告:\n", classification_report(y, modelLR.predict(X)))# 5. 可视化对比(修正绘图参数) fig, axes = plt.subplots(nrows=1, ncols=2, figsize=(14, 6)) # ROC曲线绘制 fpr, tpr, _ = roc_curve(y, modelNB.predict_proba(X)[:,1], pos_label=1) fpr1, tpr1, _ = roc_curve(y, modelLR.predict_proba(X)[:,1], pos_label=1) axes[0].plot(fpr, tpr, color='r', label=f'贝叶斯 (AUC={auc(fpr,tpr):.4f})') axes[0].plot(fpr1, tpr1, 'b--', label=f'逻辑回归 (AUC={auc(fpr1,tpr1):.4f})') axes[0].plot([0,1], [0,1], 'k--') axes[0].set(xlim=[-0.01,1.01], ylim=[-0.01,1.01], xlabel='False Positive Rate', ylabel='True Positive Rate', title='ROC曲线对比') # PR曲线绘制 precision, recall, _ = precision_recall_curve(y, modelNB.predict_proba(X)[:,1], pos_label=1) precision1, recall1, _ = precision_recall_curve(y, modelLR.predict_proba(X)[:,1], pos_label=1) axes[1].plot(recall, precision, 'r', label=f'贝叶斯 (准确率={accuracy_score(y, modelNB.predict(X)):.3f})') axes[1].plot(recall1, precision1, 'b--', label=f'逻辑回归 (准确率={accuracy_score(y
03-27
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值