为什么KFold每折训练集大小不同 如何实现每折样本量一致
现象原因
你用于交叉验证的输入数据集X_train总样本量为404,无法被设置的折数k=5整除。Sklearn的KFold默认拆分逻辑为:如果总样本数n_samples除以折数n_splits的余数为r,则前r折的验证集大小为n_samples//n_splits +1,剩余n_splits-r折的验证集大小为n_samples//n_splits。
对应到你的场景:404除以5余数为4,前4折验证集大小为81,第5折验证集大小为80,因此训练集大小分别为404-81=323、404-80=324,和你观测到的输出一致。你输出中Test的大小固定为102,是因为你预测的是固定的外部测试集X_test,和KFold的拆分逻辑无关。
实现每折训练集大小相同的方案
- 方案1:裁剪输入数据集,使总样本数可被k整除
直接丢弃少量样本,将X_train总样本数调整为k的整数倍,比如404可以丢弃4个样本得到400(400/5=80),后续KFold拆分的每折验证集大小一致,训练集自然相同。示例代码:import numpy as np # 裁剪样本使总数可被k=5整除 total_sample = len(X_train) keep_num = (total_sample // k) * k X_train = X_train[:keep_num] y_train = y_train[:keep_num] - 方案2:每折训练集固定采样相同大小的样本
不修改原始数据集,在每折训练前从拆分得到的训练索引中随机采样固定数量的样本(比如统一取323个),实现训练集大小一致。注意设置replace=False避免重复采样:kf = KFold(n_splits=k, shuffle=True) for train_index, _ in kf.split(X_train): # 固定采样323个训练样本 train_index = np.random.choice(train_index, size=323, replace=False) fitted_model = model.fit(X_train[train_index], y_train[train_index]) train_preds = fitted_model.predict(X_train[train_index]) test_preds = fitted_model.predict(X_test) print("Train", train_preds.shape) print("Test", test_preds.shape) - 方案3:调整折数适配总样本量
如果不想丢弃样本,可以将折数调整为总样本数的约数,比如404的约数有2、4、101等,设置k=4时,404/4=101,每折验证集大小一致,训练集也会相同。
内容的提问来源于stack exchange,提问作者Opps_0
相关产品推荐
相关产品推荐

