【python机器学习基础教程】(五)

模型评估与改进

交叉验证

交叉验证是一种评估泛化性能的统计学方法,它比单次划分训练集和测试集的方法更加稳定、全面。在交叉验证中,数据被多次划分,并且需要训练多个模型。
最常用的交叉验证是k折交叉验证,其中k是由用户指定的数字,通常取5或者10。
在执行5折交叉验证时,首先将数据划分为(大致)相等的5部分,每一部分叫做
接下来训练一系列模型,使用第一折作为测试集、其他折(2~5)作为训练集来训练第一个模型。
利用2~5折中的数据来构建模型,然后在1折上评估精度。
之后构建另一个模型,这次使用2折 作为测试集,1、3、4、5折中的数据作为训练集。
利用3、4、5折作为测试集重复这一过程。
对于将数据划分为训练集和测试集的这五次划分 ,每一次都需要计算精度。
最后我们得到了5个精度值。

mglearn.plots.plot_cross_validation()

在这里插入图片描述
通常来说,数据的前五分之一是第1折,第二个五分之一是第2折,其此类推。

scikit-learn中的交叉验证

scikit-learn是利用model_selection模块中的cross_val_score函数来实现交叉验证的。
cross_val_score函数的参数是我们想要评估的模型、训练数据与真实标签。
我们在iris数据集上对LogisticRegression进行评估:

from sklearn.model_selection import cross_val_score
from sklearn.datasets import load_iris
from sklearn.linear_model import LogisticRegression

iris=load_iris()
logreg=LogisticRegression()

scores=cross_val_score(logreg,iris.data,iris.target,cv=5)
print("Cross-validation scores:{}".format(scores))

Cross-validation scores:[0.96666667 1. 0.93333333 0.96666667 1. ]

总结交叉验证精度的一种常用方法是计算平均值:

print("Average cross-validation score:{:.2f}".format(scores.mean()))

Average cross-validation score:0.97

分层k折交叉验证和其他策略

首先,我们康康iris数据集:

from sklearn.datasets import load_iris
iris=load_iris()
print("Iris labels:\n{}".format(iris.target))

输出:

Iris labels:
[0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
 0 0 0 0 0 0 0 0 0 0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1
 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 2 2 2 2 2 2 2 2 2 2 2
 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2
 2 2]

数据前三分之一是类别0,中间三分之一是类别1,最后三分之一是类别2。
简单k折策略在这里失效了,故我们使用分层k折交叉验证
在分层交叉验证中,我们划分数据,使每个折中类别之间的比例与整个数据集中的比例相同。

mglearn.plots.plot_stratified_cross_validation()

在这里插入图片描述
留一交叉验证
另一种常用的交叉验证方法是留一法
可以将留一法交叉验证看作是每折只包含单个样本的k折交叉验证。
对于每次划分,选择单个数据点作为测试集。

from sklearn.model_selection import LeaveOneOut
loo=LeaveOneOut()
logreg = LogisticRegression()
scores=cross_val_score(logreg,iris.data,iris.target,cv=loo)
print("Number of cv iterations:",len(scores))
print("Mean accuracy:{:.2f}".format(scores.mean()))

Number of cv iterations: 150
Mean accuracy:0.97

打乱划分交叉验证

在打乱划分交叉验证中,每次划分为训练集取样train_size个点,为测试集取样test_size个(不相交的)点。
将这一划分方法重复n_iter次。

mglearn.plots.plot_shuffle_split()

在这里插入图片描述
下面的代码将数据集划分为50%的训练集和50%的测试集,共运行10次迭代:

from sklearn.model_selection import ShuffleSplit
shuffle_split =ShuffleSplit(test_size=.5,train_size=.5,n_splits=10)
scores=cross_val_score(logreg,iris.data,iris.target,cv=shuffle_split)
print("Cross-validation scores:\n{}".format(scores))

Cross-validation scores:
[0.97333333 0.96 0.98666667 0.98666667 0.97333333 0.98666667
0.92 0.97333333 0.97333333 0.93333333]

分组交叉验证

另一种交叉验证适用于数据中的分组高度相关时。

下面这个示例用到了一个由groups数组指定分组的模拟数据集。
这个数据集包含12个数据点,且对于每个数据点,groups指定了该点所属的分组。
一共分成四组,前3个样本属于第一组,接下来4个样本属于第二组,以此类推:

from sklearn.model_selection import GroupKFold
from sklearn.datasets import make_blobs
#创建模拟数据集
X,y=make_blobs(n_samples=12,random_state=0)
#假设前三个样本属于同一组,接下来4个样本属于同一组,以此类推
groups=[0,0,0,1,1,1,1,2,2,3,3,3]
scores=cross_val_score(logreg,X,y,groups,cv=GroupKFold(n_splits=3))
print("Cross-validation scores:\n{}".format(scores))
mglearn.plots.plot_group_kfold()

在这里插入图片描述

网格搜索

简单网格搜索

参数过拟合的风险与验证集

mglearn.plots.plot_threefold_split()

在这里插入图片描述

带交叉验证的网格搜索

mglearn.plots.plot_cross_val_selection()
mglearn.plots.plot_grid_search_overview()

在这里插入图片描述

评估指标与评分

二分类指标

对于二分类问题,我们通常会说正类反类
错误的阳性预测叫做假正例,错误的阴性预测叫做假反例
在统计学中,假正例也叫做第一类错误,假反例也叫作第二类错误。

mglearn.plots.plot_confusion_matrix_illustration()

在这里插入图片描述
"9与其他"分类任务的混淆矩阵

mglearn.plots.plot_binary_confusion_matrix()

在这里插入图片描述
二分类混淆矩阵

mglearn.plots.plot_decision_threshold()

在这里插入图片描述

受试者工作特征(ROC)和AUC

有一种常用的工具可以分析不同阈值的分类器行为:受试者工作特征曲线,简称为ROC曲线。与准确率-召回率曲线类似,ROC曲线考虑了给定分类器的所有可能的阈值,但它显示的是假正例率真正例率 ,而不是报告准确率和召回率。
真正例率只是召回率的另一个名称,而假正例率则是假正例占所有反类样本的比例

from sklearn.metrics import roc_curve
from sklearn import svm
from sklearn.svm import SVC
fpr,tpr,thresholds=roc_curve(y_test,svc.decision_function(X_test))

X,y=make_blobs(n_samples=(4000,500),centers=2,cluster_std=[7.0,2],random_state=22)
X_train,X_test,y_train,y_test=train_test_split(X,y,random_state=0)
svc=SVC(gamma=.05).fit(X_train,y_train)
precision,recall,thresholds=precision_recall_curve(y_test,svc.decision_function(X_test))
plt.plot(fpr,tpr,label="ROC Curve")
plt.xlabel("FPR")
plt.ylabel("TPR(recall)")
#找到最接近于0的阈值
close_zero=np.argmin(np.abs(thresholds))
plt.plot(fpr[close_zero],tpr[close_zero],'o',markersize=10,label="threshold zero",fillstyle="none",c='k',mew=2)
plt.legend(loc=4)

未完待续

多分类指标

一般来说,多分类结果比二分类结果更加难以理解。
除了精度,常用的工具有混淆矩阵和分类报告,下面我们将这两种详细的评估方法应用于对digits数据集中10种不同的手写数字进行分类的任务:

from sklearn.metrics import accuracy_score
from sklearn.metrics import confusion_matrix

from sklearn import datasets
digits = datasets.load_digits()
X_train,X_test,y_train,y_test=train_test_split(digits.data,digits.target,random_state=0)
lr=LogisticRegression().fit(X_train,y_train)
pred=lr.predict(X_test)
print("Accuracy:{:.3f}".format(accuracy_score(y_test,pred)))
print("Confusion matrix:\n{}".format(confusion_matrix(y_test,pred)))
Accuracy:0.951
Confusion matrix:
[[37  0  0  0  0  0  0  0  0  0]
 [ 0 40  0  0  0  0  0  0  2  1]
 [ 0  1 40  3  0  0  0  0  0  0]
 [ 0  0  0 43  0  0  0  0  1  1]
 [ 0  0  0  0 37  0  0  1  0  0]
 [ 0  0  0  0  0 46  0  0  0  2]
 [ 0  1  0  0  0  0 51  0  0  0]
 [ 0  0  0  1  1  0  0 46  0  0]
 [ 0  3  1  0  0  0  0  0 43  1]
 [ 0  0  0  0  0  1  0  0  1 45]]
scores_image=mglearn.tools.heatmap(confusion_matrix(y_test,pred),xlabel='predicted label',ylabel='true label',xticklabels=digits.target_names,yticklabels=digits.target_names,cmap=plt.cm.gray_r,fmt="%d")
plt.title("confusion matrix")
plt.gca().invert_yaxis()

在这里插入图片描述
10个数字分类任务的混淆矩阵

利用classification_report函数,我们可以计算每个类别的准确率、召回率和 f f f-分数:

from sklearn.metrics import classification_report
print(classification_report(y_test,pred))
              precision    recall  f1-score   support

           0       1.00      1.00      1.00        37
           1       0.89      0.93      0.91        43
           2       0.98      0.91      0.94        44
           3       0.91      0.96      0.93        45
           4       0.97      0.97      0.97        38
           5       0.98      0.96      0.97        48
           6       1.00      0.98      0.99        52
           7       0.98      0.96      0.97        48
           8       0.91      0.90      0.91        48
           9       0.90      0.96      0.93        47

    accuracy                           0.95       450
   macro avg       0.95      0.95      0.95       450
weighted avg       0.95      0.95      0.95       450

回归指标

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值