使用管道和网格搜索在交叉验证中嵌套cross_val_score

5

我正在使用scikit进行工作,尝试调整我的XGBoost。 我尝试使用嵌套交叉验证技术,使用管道对训练集进行重缩放(以避免数据泄漏和过拟合),并与GridSearchCV并行进行参数调整,在最后使用cross_val_score获取roc_auc分数。

from imblearn.pipeline import Pipeline 
from sklearn.model_selection import RepeatedKFold 
from sklearn.model_selection import GridSearchCV
from sklearn.model_selection import cross_val_score
from xgboost import XGBClassifier


std_scaling = StandardScaler() 
algo = XGBClassifier()

steps = [('std_scaling', StandardScaler()), ('algo', XGBClassifier())]

pipeline = Pipeline(steps)

parameters = {'algo__min_child_weight': [1, 2],
              'algo__subsample': [0.6, 0.9],
              'algo__max_depth': [4, 6],
              'algo__gamma': [0.1, 0.2],
              'algo__learning_rate': [0.05, 0.5, 0.3]}

cv1 = RepeatedKFold(n_splits=2, n_repeats = 5, random_state = 15)

clf_auc = GridSearchCV(pipeline, cv = cv1, param_grid = parameters, scoring = 'roc_auc', n_jobs=-1, return_train_score=False)

cv1 = RepeatedKFold(n_splits=2, n_repeats = 5,  random_state = 15)                       
outer_clf_auc = cross_val_score(clf_auc, X_train, y_train, cv = cv1, scoring = 'roc_auc')

问题1. 如何将cross_val_score适配于训练数据?

问题2. 由于我在流水线中包括了StandardScaler(),因此在cross_val_score中是否包括X_train是有意义的,还是应该使用标准化形式的X_train(即std_X_train)?

std_scaler = StandardScaler().fit(X_train)
std_X_train = std_scaler.transform(X_train)
std_X_test = std_scaler.transform(X_test)
1个回答

11

你选择了避免数据泄露的正确方式,就像你说的一样 - 嵌套交叉验证

问题在于,在嵌套交叉验证中,你评估的不是一个真正的估计器的分数,而是一个不存在的“元估计器”,它描述了你的模型选择过程。

也就是说,在每一轮外部交叉验证(在你的情况下由cross_val_score表示)中,估计器clf_auc会经历内部交叉验证,从而在外部交叉验证的给定折叠下选择最佳模型。 因此,对于外部交叉验证的每个折叠,你都会得到一个由内部交叉验证选择的不同估计器的分数。

例如,在一个外部交叉验证折叠中,模型得分可能是选择参数algo__min_child_weight为1的模型,在另一个折叠中则可能是选择参数为2的模型。

因此,外部交叉验证的分数代表了一个更高层次的分数:“在合理的模型选择过程中,我的选择模型将有多好的泛化能力”。

现在,如果你想要最终得到一个真正的模型,你需要以某种方式选择它(cross_val_score不会为你完成这个任务)。

做法是现在在整个数据上适合你的内部模型。 也就是执行:

clf_auc.fit(X, y)

现在是理解你所做的事情的时刻:

  1. 您拥有一个可以使用的模型,该模型适用于所有可用数据。
  2. 当您被问及“该模型在新数据上表现如何?”时,答案是您在嵌套交叉验证期间得到的分数 - 它捕获了模型选择过程作为模型评分的一部分。

至于问题#2-如果缩放器是管道的一部分,则无需在外部操作X_train。


@ShaharA 感谢你的帮助,我真的感激不尽。非常感谢你清晰明了的回答和友善的态度。我非常赞赏你花时间提供如此详细的解释。你帮助我更好地理解了问题。再次感谢你! - inatos
1
不确定为什么OP需要在xgboost模型中使用std_scaling? - HC_2016

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接