机器学习之支持向量机SVM之python实现ROC曲线绘制(二分类和多分类)

一、ROC曲线

二、TP、FP、TN、FN

三、 python绘制ROC曲线(二分类)

1、思路

2、关键代码

3、完整代码

四、 python绘制ROC曲线(多分类)

五、参考文献

一、ROC曲线

定义可见:

《机器学习——支持向量机SVM实例》

机器学习之支持向量机SVM之python实现ROC曲线绘制(二分类和多分类)

作用:通过ROC曲线可以获取相关性能指标,如EER、AUC等,这些性能指标可以用来评价一个SVM训练出来模型的优劣

二、TP、FP、TN、FN

机器学习之支持向量机SVM之python实现ROC曲线绘制(二分类和多分类)

三、 python绘制ROC曲线(二分类)

1、思路

python主要的思路是通过roc_curve函数和测试样本的实际标签集test_label、由训练模型预测得到的标签集test_predict_label获得。通过比对实际标签和预测标签来计算TP、FP、TN、FN,通过roc_curve函数可以实现,返回的是TP、FP、以及阈值threshold。计算ROC曲线只需要TPFP即可。

2、关键代码


  1. ................
  2. #train_data用于训练的样本集, test_data用于测试的样本集, train_label训练样本对应的标签集, test_label测试样本对应的标签集
  3. ###通过decision_function()计算得到的test_predict_label的值,用在roc_curve()函数中
  4. test_predict_label = svm.fit(train_data, train_label).decision_function(test_data)
  5. #首先通过fit来对训练样本和训练样本标签进行训练得到模型,然后通过decision_function来获得模型对于测试样本集预测的标签集
  6. # Compute ROC curve and ROC area for each class#计算tp,fp
  7. #通过测试样本输入的标签集和模型预测的标签集进行比对,得到fp,tp,不同的fp,tp是算法通过一定的规则改变阈值获得的
  8. fpr,tpr,threshold = roc_curve(test_label, test_predict_label) ###计算真正率和假正率
  9. roc_auc = auc(fpr,tpr) ###计算auc的值,auc就是曲线包围的面积,越大越好
  10. ..................

机器学习之支持向量机SVM之python实现ROC曲线绘制(二分类和多分类)

  1. #test_predict_label
  2. [ 0.17284263 0.65445393 -0.54087101 0.3555818 0.00579262 -0.20174248
  3. 0.0565328 0.00571205 -0.1517872 0.25656427 0.39764688 0.04549989
  4. 0.33455816 -0.12499602 0.23724787 -0.36250412 -0.0874348 -0.11575856
  5. -0.25270656 -0.23457408 -0.18239472 -0.10728706 -0.32201471 0.71954289
  6. -0.29292995 -0.22073314 -0.32473373 -0.19383585 -0.24296148 0.37524795]

在二分类问题中,阈值的改变其实就是相当于从一个边界移动到另一个边界,阈值的改变也就使得tp和fp的改变


  1. #阈值threshold
  2. [ 1.71954289 0.71954289 0.25656427 0.0565328 0.00571205 -0.0874348
  3. -0.10728706 -0.12499602 -0.1517872 -0.18239472 -0.20174248 -0.23457408
  4. -0.24296148 -0.54087101]

  1. #tp
  2. [0. 0. 0. 0.2 0.2 0.26666667
  3. 0.26666667 0.4 0.4 0.46666667 0.46666667 0.6
  4. 0.6 1. ]

  1. #fp
  2. [0. 0.06666667 0.46666667 0.46666667 0.66666667 0.66666667
  3. 0.73333333 0.73333333 0.8 0.8 0.93333333 0.93333333
  4. 1. 1. ]

3、完整代码


  1. # -*- coding: utf-8 -*-
  2. import numpy as np
  3. import matplotlib.pyplot as plt
  4. from sklearn import svm, datasets
  5. from sklearn.metrics import roc_curve, auc ###计算roc和auc
  6. from sklearn import model_selection
  7. # Import some data to play with
  8. iris = datasets.load_iris()
  9. X = iris.data#得到样本集
  10. y = iris.target#得到标签集
  11. ##变为2分类
  12. X, y = X[y != 2], y[y != 2]#通过取y不等于2来取两种类别
  13. # Add noisy features to make the problem harder添加扰动
  14. random_state = np.random.RandomState(0)
  15. n_samples, n_features = X.shape
  16. X = np.c_[X, random_state.randn(n_samples, 200 * n_features)]
  17. # shuffle and split training and test sets划分样本集
  18. train_data, test_data, train_label, test_label = model_selection.train_test_split(X, y, test_size=.3,random_state=0)
  19. #train_data用于训练的样本集, test_data用于测试的样本集, train_label训练样本对应的标签集, test_label测试样本对应的标签集
  20. # Learn to predict each class against the other分类器设置
  21. svm = svm.SVC(kernel='linear', probability=True,random_state=random_state)#使用核函数为线性核,参数默认,创建分类器
  22. ###通过decision_function()计算得到的test_predict_label的值,用在roc_curve()函数中
  23. test_predict_label = svm.fit(train_data, train_label).decision_function(test_data)
  24. #首先通过fit来对训练样本和训练样本标签进行训练得到模型,然后通过decision_function来获得模型对于测试样本集预测的标签集
  25. print(test_predict_label)
  26. # Compute ROC curve and ROC area for each class#计算tp,fp
  27. #通过测试样本输入的标签集和模型预测的标签集进行比对,得到fp,tp,不同的fp,tp是算法通过一定的规则改变阈值获得的
  28. fpr,tpr,threshold = roc_curve(test_label, test_predict_label) ###计算真正率和假正率
  29. print(fpr)
  30. print(tpr)
  31. print(threshold)
  32. roc_auc = auc(fpr,tpr) ###计算auc的值,auc就是曲线包围的面积,越大越好
  33. plt.figure()
  34. lw = 2
  35. plt.figure(figsize=(10,10))
  36. plt.plot(fpr, tpr, color='darkorange',
  37. lw=lw, label='ROC curve (area = %0.2f)' % roc_auc) ###假正率为横坐标,真正率为纵坐标做曲线
  38. plt.plot([0, 1], [0, 1], color='navy', lw=lw, linestyle='--')
  39. plt.xlim([0.0, 1.0])
  40. plt.ylim([0.0, 1.05])
  41. plt.xlabel('False Positive Rate')
  42. plt.ylabel('True Positive Rate')
  43. plt.title('Receiver operating characteristic example')
  44. plt.legend(loc="lower right")
  45. plt.show()

机器学习之支持向量机SVM之python实现ROC曲线绘制(二分类和多分类)

虚线表示auc为0.5,正确率与错误率一样的情况

四、 python绘制ROC曲线(多分类)

对于多分类问题,ROC曲线的获取主要有两种方法:
假设测试样本个数为m,类别个数为n。在训练完成后,计算出每个测试样本的在各类别下的概率或置信度,得到一个[m, n]形状的矩阵P,每一行表示一个测试样本在各类别下概率值(按类别标签排序)。相应地,将每个测试样本的标签转换为类似二进制的形式,每个位置用来标记是否属于对应的类别(也按标签排序,这样才和前面对应),由此也可以获得一个[m, n]的标签矩阵L。
①方法一:每种类别下,都可以得到m个测试样本为该类别的概率(矩阵P中的列)。所以,根据概率矩阵P和标签矩阵L中对应的每一列,可以计算出各个阈值下的假正例率(FPR)和真正例率(TPR),从而绘制出一条ROC曲线。这样总共可以绘制出n条ROC曲线。最后对n条ROC曲线取平均,即可得到最终的ROC曲线。
②方法二:
首先,对于一个测试样本:1)标签只由0和1组成,1的位置表明了它的类别(可对应二分类问题中的”正”),0就表示其他类别(”负”);2)要是分类器对该测试样本分类正确,则该样本标签中1对应的位置在概率矩阵P中的值是大于0对应的位置的概率值的。基于这两点,将标签矩阵L和概率矩阵P分别按行展开,转置后形成两列,这就得到了一个二分类的结果。所以,此方法经过计算后可以直接得到最终的ROC曲线。
上面的两个方法得到的ROC曲线是不同的,当然曲线下的面积AUC也是不一样的。 在python中,方法1和方法2分别对应sklearn.metrics.roc_auc_score函数中参数average值为’macro’和’micro’的情况。下面参考sklearn官网提供的例子,对两种方法进行实现。


  1. # 引入必要的库
  2. import numpy as np
  3. import matplotlib.pyplot as plt
  4. from itertools import cycle
  5. from sklearn import svm, datasets
  6. from sklearn.metrics import roc_curve, auc
  7. from sklearn.model_selection import train_test_split
  8. from sklearn.preprocessing import label_binarize
  9. from sklearn.multiclass import OneVsRestClassifier
  10. from scipy import interp
  11. # 加载数据
  12. iris = datasets.load_iris()
  13. X = iris.data
  14. y = iris.target
  15. # 将标签二值化
  16. y = label_binarize(y, classes=[0, 1, 2])
  17. # 设置种类
  18. n_classes = y.shape[1]
  19. # 训练模型并预测
  20. random_state = np.random.RandomState(0)
  21. n_samples, n_features = X.shape
  22. # shuffle and split training and test sets
  23. X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=.5,random_state=0)
  24. # Learn to predict each class against the other
  25. classifier = OneVsRestClassifier(svm.SVC(kernel='linear', probability=True,
  26. random_state=random_state))#一对多
  27. y_score = classifier.fit(X_train, y_train).decision_function(X_test)
  28. # 计算每一类的ROC
  29. fpr = dict()
  30. tpr = dict()
  31. roc_auc = dict()
  32. for i in range(n_classes):
  33. fpr[i], tpr[i], _ = roc_curve(y_test[:, i], y_score[:, i])
  34. roc_auc[i] = auc(fpr[i], tpr[i])
  35. # Compute micro-average ROC curve and ROC area(方法二)
  36. fpr["micro"], tpr["micro"], _ = roc_curve(y_test.ravel(), y_score.ravel())
  37. roc_auc["micro"] = auc(fpr["micro"], tpr["micro"])
  38. # Compute macro-average ROC curve and ROC area(方法一)
  39. # First aggregate all false positive rates
  40. all_fpr = np.unique(np.concatenate([fpr[i] for i in range(n_classes)]))
  41. # Then interpolate all ROC curves at this points
  42. mean_tpr = np.zeros_like(all_fpr)
  43. for i in range(n_classes):
  44. mean_tpr += interp(all_fpr, fpr[i], tpr[i])
  45. # Finally average it and compute AUC
  46. mean_tpr /= n_classes
  47. fpr["macro"] = all_fpr
  48. tpr["macro"] = mean_tpr
  49. roc_auc["macro"] = auc(fpr["macro"], tpr["macro"])
  50. # Plot all ROC curves
  51. lw=2
  52. plt.figure()
  53. plt.plot(fpr["micro"], tpr["micro"],
  54. label='micro-average ROC curve (area = {0:0.2f})'
  55. ''.format(roc_auc["micro"]),
  56. color='deeppink', linestyle=':', linewidth=4)
  57. plt.plot(fpr["macro"], tpr["macro"],
  58. label='macro-average ROC curve (area = {0:0.2f})'
  59. ''.format(roc_auc["macro"]),
  60. color='navy', linestyle=':', linewidth=4)
  61. colors = cycle(['aqua', 'darkorange', 'cornflowerblue'])
  62. for i, color in zip(range(n_classes), colors):
  63. plt.plot(fpr[i], tpr[i], color=color, lw=lw,
  64. label='ROC curve of class {0} (area = {1:0.2f})'
  65. ''.format(i, roc_auc[i]))
  66. plt.plot([0, 1], [0, 1], 'k--', lw=lw)
  67. plt.xlim([0.0, 1.0])
  68. plt.ylim([0.0, 1.05])
  69. plt.xlabel('False Positive Rate')
  70. plt.ylabel('True Positive Rate')
  71. plt.title('Some extension of Receiver operating characteristic to multi-class')
  72. plt.legend(loc="lower right")
  73. plt.show()

机器学习之支持向量机SVM之python实现ROC曲线绘制(二分类和多分类)

五、参考文献

ROC和AUC介绍以及如何计算AUC

《ROC原理介绍及利用python实现二分类和多分类的ROC曲线》
ROC曲线、AUC、Precision、Recall、F-measure理解及Python实现
ROC曲线
多分类下的ROC曲线和AUC
用Python画ROC曲线

任何程序错误,以及技术疑问或需要解答的,请添加

机器学习之支持向量机SVM之python实现ROC曲线绘制(二分类和多分类)

机器学习之支持向量机SVM之python实现ROC曲线绘制(二分类和多分类)

Original: https://blog.csdn.net/sinat_28371057/article/details/113749034
Author: 青年夏日科技
Title: 机器学习之支持向量机SVM之python实现ROC曲线绘制(二分类和多分类)

原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/665434/

转载文章受原作者版权保护。转载请注明原作者出处!

(0)

大家都在看

亲爱的 Coder【最近整理,可免费获取】👉 最新必读书单  | 👏 面试题下载  | 🌎 免费的AI知识星球