You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在for循环中更新Pandas DataFrame?KFold训练集大小疑问

问题解答

一、DataFrame存储系数报错的解决方法

你遇到的None of [Int64Index(...)] are in the [columns]错误,核心原因是你试图用训练集的观测行索引作为DataFrame的列名,但空DataFramevar一开始没有这些列,而且逻辑上也不应该这么存储系数。

你的需求是存储每次迭代(每个折叠)后的变量系数,正确的做法应该是把折叠次数或特征作为维度来组织数据,下面给你两种实用的实现方式:

方式1:按折叠次数作为行,特征作为列

这种方式适合查看每个折叠下所有特征的系数情况:

from sklearn.model_selection import KFold
import pandas as pd
import matplotlib.pyplot as plt
from sklearn.linear_model import Lasso

kf = KFold(n_splits=10)
cvlasso= Lasso(alpha=0.001)
count = 1
# 提前用特征名初始化DataFrame的列
var = pd.DataFrame(columns=X.columns)

for train, _ in kf.split(X, Y):
    cvlasso.fit(X.iloc[train, :], Y.iloc[train])
    importances_index_desc = cvlasso.coef_
    feature_labels = list(X.columns.values)
    
    # 绘图部分保持不变
    plt.figure()
    plt.bar(feature_labels, importances_index_desc)
    plt.xticks(feature_labels, rotation='vertical')
    plt.ylabel('Importance')
    plt.xlabel('Features')
    plt.title('Fold {}'.format(count))
    
    # 将当前折叠的系数作为一行加入DataFrame
    var.loc[f'Fold {count}'] = importances_index_desc
    
    count += 1
    plt.show()

最终var的每一行对应一个折叠的所有特征系数,列是特征名称,后续可以轻松对比不同折叠下的系数变化。

方式2:按特征作为行,折叠次数作为列

如果更关注单个特征在所有折叠中的系数波动,可改用这种结构:

# 初始化时用特征名作为行索引
var = pd.DataFrame(index=X.columns)

# 循环内替换存储逻辑:
var[f'Fold {count}'] = importances_index_desc

二、训练集大小不是33000的原因

KFold的拆分规则是把数据集平均分成n_splits份,每次用1份做测试集,剩下的n_splits-1份做训练集。

你提到训练集大小是28512,我们可以反推:28512 ÷ 9 × 10 = 31680,这说明你的数据集实际有效观测数是31680,而非你以为的33000。可能的原因包括:

  • 加载数据集时不小心过滤了部分行(比如删除了含缺失值的样本,或者索引不连续)
  • 原始数据集的行数本身就是31680,之前的统计有误

你可以先运行print(X.shape)确认数据集的实际行数,如果输出是(31680, N)(N为特征数),那训练集大小31680 × 9/10 = 28512完全符合KFold的拆分逻辑。

内容的提问来源于stack exchange,提问作者Warzone

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.06 15:32:36