文章目录
一. 交叉验证定义
交叉验证是用来验证分类器的性能一种统计分析方法,基本思想是把在某种意义下将原始数据(data set)进行分组,一部分做为训练集(training set),另一部分做为测试集(validation set),首先用训练集对分类器进行训练,在利用测试集来测试训练得到的模型(model),以此来做为评价分类器的性能指标。
二. 三种实现方法
2.1 留出法(holdout cross validation)
将原始数据集分为三部分:训练集、验证集和测试集。训练集用于训练模型,验证集用于模型的参数选择配置,测试集对于模型来说是未知数据,用于评估模型的泛化能力。
优点:操作简单
缺点:样本数比例,模型对数据划分敏感,分成三部分使得训练数据变少。
2.2 k折交叉验证(k-fold cross validation)
将数据集无替换的随机分为k份,k-1份用来训练模型,剩下一份用来模型性能评估。重复k次,得到k个模型和性能评估结果。得到k个性能评估后,取平均求出最终性能评估。即:
-
第一步:不重复抽样将原始数据随机分为k份。
-
第二步:每一次挑选其中 1 份作为测试集,剩余k-1份作为训练集用于模型训练。
-
第三步:重复第二步k次,每个子集都有一次作为测试集,其余子集作为训练集。在每个训练集上训练后得到一个模型,用这个模型在相应测试集上测试,计算并保存模型的评估指标。
-
第四步:计算k组测试结果的平均值作为模型精度的估计,并作为当前k折交叉验证下模型的性能指标。
优点:分组后取平均减少方差,使得模型对数据划分不敏感。
缺点:k取值需要尝试。
分成五份,示例如下所示:
2.3 留一法(leave one out cross validation)
当k折交叉验证法的k=m,m为样本总数时,称为留一法,即每次的测试集都只有一个样本,要进行m次训练和预测。
优点:适合数据缺乏时使用
缺点:计算繁琐,训练复杂度增加。
三.交叉验证代码实现
代码:
import pandas as pd
from sklearn.preprocessing import StandardScaler
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LogisticRegression
from sklearn.model_selection import cross_val_score
from sklearn.model_selection import StratifiedKFold
from sklearn.base import clone
data = pd.read_csv("E:/file/creditcard.csv")
# 将金额数据处理成 范围为[-1,1] 之间的数值
# 机器学习默认数值越大,特征就越重要,不处理容易造成的问题是 金额这个特征值的重要性远大于V1-V28特征
data['normAmount'] = StandardScaler().fit_transform(data['Amount'].values.reshape(-1, 1))
# 删除暂时不用的特征值
data = data.drop(['Time','Amount'],axis=1)
X = data.values[:, data.columns != 'Class']
y = data.values[:, data.columns == 'Class']
# 划分训练集和测试集
# 测试集比例为0.3,也可以根据时间情况进行调整
X_train, X_test, y_train, y_test = train_test_split(X,y,test_size = 0.3, random_state = 0)
skfolds = StratifiedKFold(
n_splits=3,
random_state=42, # 设置随机种子
shuffle=True
)
lr = LogisticRegression(C=0.01, penalty='l2')
y_train = y_train.astype('int')
lr_result = lr.fit(X_train, y_train)
lr.predict(X)
cross_val_score(lr, X_train, y_train, cv=3, scoring='accuracy')
for train_index, test_index in skfolds.split(X_train, y_train): # 切割训练的数据集和标签集
clone_clf = clone(lr_result) # 克隆构建模型
X_train_folds = X_train[train_index]
y_train_folds = y_train[train_index]
X_test_folds = X_train[test_index]
y_test_folds = y_train[test_index]
# fit方法:用随机梯度下降法拟合线性模型
clone_clf.fit(X_train_folds, y_train_folds)
# 预测
y_pred = clone_clf.predict(X_test_folds)
# 做对了的个数
n_correct = sum(y_pred == y_test_folds)
print(n_correct / len(y_pred))
测试记录:
[0.99826951 0.99826951 0.99826951 … 0.99826951 0.99826951 0.99826951]
[0.99826951 0.99826951 0.99826951 … 0.99826951 0.99826951 0.99826951]
[0.99826948 0.99826948 0.99826948 … 0.99826948 0.99826948 0.99826948]
参考:
- https://study.163.com/course/introduction.htm?courseId=1003590004#/courseDetail?tab=1