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

xgboost验证用手动拆分功能的数据集拆分实现问题

实现步骤

首先明确认知:你之前对subsample参数的理解有误,该参数是xgboost训练每棵树时对训练样本的随机采样比例,作用是降低过拟合,并不会完成全局的训练集/测试集拆分,这也是你之前生成的分类报告实际是全量数据的训练集表现、而非独立测试集表现的原因。

你可以按照以下步骤完成数据拆分和逻辑改造:

步骤1:读取标签并关联特征路径

首先读取CSV标签文件,把每个样本的标签和对应的特征文件路径做一一关联,避免拆分时出现标签和特征错配的问题:

import pandas as pd
import os
import numpy as np
from sklearn.model_selection import train_test_split
import xgboost as xgb
from sklearn.metrics import classification_report
import time

# 替换为你自己的实际路径
LABEL_CSV_PATH = "你的标签文件存储路径.csv"
FEATURE_DIR = "你的特征文件存放目录路径"
WORKING_DIR = "你的模型存储/运行工作目录路径"

# 假设CSV包含两列:sample_id(特征文件的文件名去掉后缀的标识)、label(对应样本标签)
label_df = pd.read_csv(LABEL_CSV_PATH)
# 拼接每个样本对应的特征文件完整路径,后缀根据你实际的特征文件格式修改,比如.pkl、.png等
label_df['feature_path'] = label_df['sample_id'].apply(lambda x: os.path.join(FEATURE_DIR, f"{x}.npy"))

步骤2:拆分训练/测试集元数据

直接对关联好的元数据表做拆分,保证标签分布一致:

# stratify参数保证训练集、测试集的标签分布和全量数据一致,避免分布偏移导致评估结果失真
train_meta, test_meta = train_test_split(label_df, test_size=0.2, random_state=1, stratify=label_df['label'])

步骤3:编写通用数据加载函数

写函数根据拆分后的元数据批量加载特征和标签:

def load_data(meta_df):
    X = []
    y = []
    for _, row in meta_df.iterrows():
        # 特征读取逻辑根据你的文件格式调整,比如pkl文件用pickle.load、图像用PIL.Image.open等
        feat = np.load(row['feature_path'])
        X.append(feat)
        y.append(row['label'])
    return np.array(X), np.array(y)

# 分别加载训练集和测试集
X_train, y_train = load_data(train_meta)
X_test, y_test = load_data(test_meta)

步骤4:修改原训练函数,新增独立测试集评估

调整原有train函数的逻辑,训练仅使用80%的训练集,最终分别输出训练集和独立测试集的分类报告:

def train(X_train, y_train, X_test, y_test):
    os.chdir(WORKING_DIR)
    start_time = time.time()
    dtrain = xgb.DMatrix(X_train, label=y_train)
    dtest = xgb.DMatrix(X_test, label=y_test)

    try:
        model = xgb.Booster({'nthread': 4})
        model.load_model("model_file.bin")
        print("已有模型加载完成")
    except:
        print('开始训练模型.....')
        param = {'num_class':4,'objective':'multi:softmax','eval_metric':['merror'],'max_depth':7,'eta':0.04,'subsample':0.8,'min_child_weight':0.5,'max_delta_step':7,'gamma':2,'lambda':10,'colsample_bytree':0.5}
        # 可选择将测试集加入eval_set,查看训练过程中测试集的指标变化
        model = xgb.train(param, dtrain, 420, [(dtrain,'train'), (dtest, 'test')], verbose_eval=20)
        print('保存模型....')
        model.save_model('model_file.bin')
        print('模型保存完成!')
        print("训练耗时 :", time.time() - start_time)

    # 输出训练集分类报告
    print('===== 训练集分类报告 =====')
    train_pred = model.predict(dtrain, ntree_limit=420)
    print(classification_report(y_train, train_pred))

    # 输出独立测试集分类报告
    print('===== 独立测试集分类报告 =====')
    test_pred = model.predict(dtest, ntree_limit=420)
    print(classification_report(y_test, test_pred))

# 调用函数执行
train(X_train, y_train, X_test, y_test)

注意事项

  • 请先确认CSV中的sample_id和特征目录下的文件名是一一对应的,避免出现文件找不到的报错
  • 原有subsample=0.8参数可正常保留,该参数的随机采样逻辑仅作用于训练过程,不会影响全局的训练/测试拆分结果
  • 如果你的特征维度较高、样本量较大,可以考虑提前把所有特征加载后再做拆分,减少重复IO耗时

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.03 18:00:04