sheng的学习笔记-AI-模型评估-留出法、交叉验证法、自助法
评估方法:
数据集可以分为 训练集,交叉验证集,测试集。
- 训练集相当于自己做作业,
- 验证集相当于考试测试一下自己的实力,
- 测试集就是真刀真枪的干(当你训练好了模型以后,就算模型的数据告诉你它很牛逼,你最好在测试集试一试,不然直接上生产可能不及预期)
一般训练集,验证集,测试集的数据比例是 60%:20%:20%,但如果数据量很大,比如上百万的,验证集和测试集分别用几万就行
上面的集合需要互斥,最好别出现训练集和验证集出现重复数据的事情(比如你偷看了考试答案,就算考过了,真实场景上的时候也得输)。
留出法
将所有的数据按照比例划分,然后别动,比如10万个数据,6万是训练集,2万是验证集,2万是测试集,划分完了别动,就那么训练
如果数据量很大,比如几百万的数据,训练集一次性加载那么多内存会爆,需要分批次进行训练(比如一次加载10万),验证集的选择方式有两种主要的做法:
固定验证集(Validation Set不变):
- 在这种情况下,你从训练集(或者整个数据集)中预先划分出一部分数据作为验证集。这个验证集在整个训练过程中保持不变。每次模型训练时,无论训练数据如何分批,验证集都会是相同的。
- 这种方法的优势在于,你可以确保验证集的数据不受每次训练中数据分批的影响,从而获得一个稳定的模型评估标准。
- 缺点是,验证集可能会在一定程度上与训练集有重叠,这可能导致过拟合的问题,特别是当数据量较小或验证集划分不够随机时。
from sklearn.model_selection import train_test_split
# 假设你的数据是 X_train 和 y_train
X_train, X_val, y_train, y_val = train_test_split(X_train, y_train, test_size=0.2, random_state=42)
# 模型训练时使用相同的验证集
model.fit(X_train, y_train, epochs=10, batch_size=32, validation_data=(X_val, y_val))
动态验证集(每次都拆分不同的验证集):
- 另一种方法是在每次模型训练时,都从训练集中重新划分一个验证集。这意味着每次训练使用不同的验证集,这种方式适用于数据量非常大,且希望每次训练都使用不同的验证数据。
- 这种方式的好处是可以确保验证集与训练集之间不会有任何交叉,从而避免某些过拟合问题。但是,这种方法可能会导致验证过程的波动,因为每次验证集不同,模型的评估标准也会有所不同。
model.fit(X_train, y_train, epochs=10, batch_size=32, validation_split=0.2)
以上的场景是,比如100万的数据,留下5万作为最终测试集, 还剩下95万的数据作为训练集和验证集,那我是90万作为训练集,5万作为固定的,将90万的数据分为10个批次(每个批次互斥,每个批次10万的数据)每次fit的时候训练集是10万。问题是:
- 每次训练的时候验证集是固定的5万数据?
- 还是95万的数据划分10个批次(每个批次9万5的数据),在训练的时候9万五再(80%训练集,20%验证集),这种方案每次的验证集都不一样
方案1,训练迭代的时候比较慢,因为验证机太大了
方案2,训练迭代的时候不太稳定,本来loss都下去了,第二个迭代又上去了
我不是土豪,算力还是很重要的
交叉验证法(cross validation)
注意,以下的测试集,都是上面说的交叉验证集,真正的测试集是最终评估模型的数据
“k折交叉验证”(k-fold cross validation)
K折交叉验证(K-Fold Cross-Validation)是一种常用的模型评估和模型选择方法,它通过将数据集分成K个大小相等的子集(或尽可能相等),然后使用其中K-1个子集进行训练,剩下的1个子集用于测试,这个过程重复K次,每次选择不同的子集作为测试集
步骤
对于每一折(即每一次迭代):
- 选择一个子集作为验证集(测试集)。
- 选择剩余的K-1个子集作为训练集。
- 使用训练集训练模型。
- 使用验证集评估模型的性能。
在每次迭代中,记录模型的性能指标,如准确率、精确度、召回率、F1分数或损失值等。
在所有K次迭代完成后,计算模型性能指标的平均值
示意图
示例代码
from sklearn.model_selection import KFold
from sklearn.datasets import load_boston
from sklearn.linear_model import LinearRegression
from sklearn.metrics import mean_squared_error
import numpy as np
# 加载数据集
X, y = load_boston(return_X_y=True)
# 初始化K折交叉验证
kf = KFold(n_splits=5, shuffle=True, random_state=42)
# 初始化模型
model = LinearRegression()
# 用于存储每次迭代的MSE
mse_scores = []
# 进行K折交叉验证
for train_index, test_index in kf.split(X):
X_train, X_test = X[train_index], X[test_index]
y_train, y_test = y[train_index], y[test_index]
# 训练模型
model.fit(X_train, y_train)
# 预测
y_pred = model.predict(X_test)
# 计算MSE
mse = mean_squared_error(y_test, y_pred)
mse_scores.append(mse)
# 计算平均MSE
average_mse = np.mean(mse_scores)
print(f"Average MSE: {average_mse}")
在这个例子中,我们使用了波士顿房价数据集,并应用了线性回归模型。我们设置了5折交叉验证,并计算了每次迭代的平均均方误差(MSE)。这个过程可以帮助我们评估模型的泛化能力和稳定性
留一法(Leave-one-out,简称LOO)
留一法(Leave-One-Out, LOO)是一种特殊的交叉验证方法,它是 K 折交叉验证的一个特例,其中 K 等于数据集中的样本数。在留一法中,每次迭代只留下一个样本作为测试集,而其余所有样本构成训练集。这个过程会重复进行,直到数据集中的每个样本都被用作一次测试集。
计算成本太高了,大数据量下别想这个了
步骤:
- 数据分割:对于数据集中的每个样本,将其单独留出作为测试集,其余样本组成训练集。
- 模型训练:使用训练集训练模型。
- 模型评估:使用留下的单个样本作为测试集来评估模型的性能。
- 重复过程:对数据集中的每个样本重复步骤1-3。
- 结果汇总:计算所有迭代中模型性能指标的平均值,以得到模型的整体性能估计。
特点:
- 计算成本高:由于需要对每个样本都进行一次训练和测试,因此当数据集较大时,留一法的计算成本非常高。
- 结果稳定性:留一法提供了对模型性能的非常稳定的估计,因为它考虑了数据集中每个样本的独立影响。
- 适用性:留一法适用于小样本数据集,或者当数据集非常宝贵,需要尽可能利用每个样本的信息时。
优缺点:
-
优点:
- 提供了对模型性能的无偏估计。
- 可以给出每个样本的预测结果,有助于分析模型对特定样本的表现。
-
缺点:
- 计算成本高,特别是对于大型数据集。
- 可能会过度拟合,因为每个样本都被用作测试集,模型可能会学习到数据中的噪声。
自助法
自助法(Bootstrap)是一种统计学上的重采样技术,它通过从原始数据集中进行有放回的随机抽样来创建多个新的样本集,从而估计统计量(如平均值、中位数、方差等)的分布。这种方法因其简单和强大而被广泛应用于科学研究、商业分析、工程问题等多个领域
步骤:
-
数据重采样:从原始数据集中随机抽取样本,允许重复抽样。通常,样本数量与原始数据集相同。由于允许重复抽样,某些样本可能在新样本集中出现多次,而另一些样本可能完全不被选中。
-
模型训练与评估:使用重采样得到的训练集训练模型,并使用未被选中的样本(即测试集)评估模型性能。
-
重复过程:重复上述步骤多次(例如,1000次),每次都生成不同的训练集和测试集。
-
性能汇总:计算每次评估的性能指标(如准确率、均方误差等),并最终取平均值,以获得模型的整体性能评估。
特点:
- 充分利用数据:自助法能够在样本量较小的情况下有效利用数据,提供更多的训练样本。
- 不确定性估计:可以通过多次重采样来估计模型性能的方差和置信区间。
- 适用于小样本数据集:自助法在数据集较小、难以有效划分训练/测试集时很有用。
- 集成学习:自助法能从初始数据集中产生多个不同的训练集,这对集成学习方法有很大的好处。
缺点:
- 偏差问题:由于某些样本可能在训练集中重复出现,而另一些样本可能完全不被选中,可能导致模型评估的偏差。
- 计算成本:需要多次训练模型,计算成本较高。
原文地址:https://blog.csdn.net/coldstarry/article/details/144711370
免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!