roc_auc_score()和auc()的结果不同
machine-learning
python
scikit-learn
5
0

我很难理解scikit-learn中roc_auc_score()auc()之间的区别(如果有)。

试图预测具有不平衡类的二进制输出(Y = 1时约为1.5%)。

分类器

model_logit = LogisticRegression(class_weight='auto')
model_logit.fit(X_train_ridge, Y_train)

大鹏曲线

false_positive_rate, true_positive_rate, thresholds = roc_curve(Y_test, clf.predict_proba(xtest)[:,1])

AUC的

auc(false_positive_rate, true_positive_rate)
Out[490]: 0.82338034042531527

roc_auc_score(Y_test, clf.predict(xtest))
Out[493]: 0.75944737191205602

有人可以解释这种差异吗?我以为两者都只是在计算ROC曲线下的面积。可能是因为数据集不平衡,但我不知道为什么。

谢谢!

参考资料:
Stack Overflow
收藏
评论
共 3 个回答
高赞 时间 活跃

AUC并不总是在ROC曲线的曲线下方。曲线下面积为一些曲线下(抽象)地区,因此它比AUROC更一般的事情。对于不平衡的类,最好为精确调用曲线找到AUC。

见sklearn源roc_auc_score

def roc_auc_score(y_true, y_score, average="macro", sample_weight=None):
    # <...> docstring <...>
    def _binary_roc_auc_score(y_true, y_score, sample_weight=None):
            # <...> bla-bla <...>

            fpr, tpr, tresholds = roc_curve(y_true, y_score,
                                            sample_weight=sample_weight)
            return auc(fpr, tpr, reorder=True)

    return _average_binary_score(
        _binary_roc_auc_score, y_true, y_score, average,
        sample_weight=sample_weight) 

如您所见,这首先获得roc曲线,然后调用auc()获得面积。

我猜你的问题是predict_proba()调用。对于普通的predict() ,输出始终相同:

import numpy as np
from sklearn.linear_model import LogisticRegression
from sklearn.metrics import roc_curve, auc, roc_auc_score

est = LogisticRegression(class_weight='auto')
X = np.random.rand(10, 2)
y = np.random.randint(2, size=10)
est.fit(X, y)

false_positive_rate, true_positive_rate, thresholds = roc_curve(y, est.predict(X))
print auc(false_positive_rate, true_positive_rate)
# 0.857142857143
print roc_auc_score(y, est.predict(X))
# 0.857142857143

如果为此更改以上内容,有时会得到不同的输出:

false_positive_rate, true_positive_rate, thresholds = roc_curve(y, est.predict_proba(X)[:,1])
# may differ
print auc(false_positive_rate, true_positive_rate)
print roc_auc_score(y, est.predict(X))
收藏
评论

使用y_pred(类标签)时,您已经确定了阈值。当使用y_prob(正类概率)时,您可以使用阈值,并且ROC曲线应该可以帮助您确定阈值。

对于第一种情况,您使用的是概率:

y_probs = clf.predict_proba(xtest)[:,1]
fp_rate, tp_rate, thresholds = roc_curve(y_true, y_probs)
auc(fp_rate, tp_rate)

当您执行此操作时,您正在考虑“先于” AUC,然后再决定要使用的阈值。

在第二种情况下,您使用的是预测(而不是概率),在这种情况下,对两者都使用“ predict”而不是“ predict_proba”,您应该获得相同的结果。

y_pred = clf.predict(xtest)
fp_rate, tp_rate, thresholds = roc_curve(y_true, y_pred)
print auc(fp_rate, tp_rate)
# 0.857142857143

print roc_auc_score(y, y_pred)
# 0.857142857143
收藏
评论

predict只返回一个类别或另一个类别。然后,使用分类器上的predict结果来计算ROC,只有三个阈值(尝试所有一个类别,琐碎所有其他类别,以及介于两者之间)。您的ROC曲线如下所示:

      ..............................
      |
      |
      |
......|
|
|
|
|
|
|
|
|
|
|
|

同时, predict_proba()返回整个概率范围,因此现在您可以在数据上放置三个以上的阈值。

             .......................
             |
             |
             |
          ...|
          |
          |
     .....|
     |
     |
 ....|
.|
|
|
|
|

因此存在不同的领域。

收藏
评论
新手导航
  • 社区规范
  • 提出问题
  • 进行投票
  • 个人资料
  • 优化问题
  • 回答问题

关于我们

常见问题

内容许可

联系我们

@2020 AskGo
京ICP备20001863号