【问题标题】:How to optimize a sklearn pipeline, using XGboost, for a different `eval_metric`?如何使用 XGboost 针对不同的“eval_metric”优化 sklearn 管道?
【发布时间】:2017-08-05 05:52:04
【问题描述】:

我正在尝试使用XGBoost,并将eval_metric 优化为auc(如here 所述)。

直接使用分类器时效果很好,但当我尝试将其用作pipeline 时会失败。

.fit 参数传递给sklearn 管道的正确方法是什么?

例子:

from sklearn.pipeline import Pipeline
from sklearn.preprocessing import StandardScaler
from sklearn.datasets import load_iris
from xgboost import XGBClassifier
import xgboost
import sklearn

print('sklearn version: %s' % sklearn.__version__)
print('xgboost version: %s' % xgboost.__version__)

X, y = load_iris(return_X_y=True)

# Without using the pipeline: 
xgb = XGBClassifier()
xgb.fit(X, y, eval_metric='auc')  # works fine

# Making a pipeline with this classifier and a scaler:
pipe = Pipeline([('scaler', StandardScaler()), ('classifier', XGBClassifier())])

# using the pipeline, but not optimizing for 'auc': 
pipe.fit(X, y)  # works fine

# however this does not work (even after correcting the underscores): 
pipe.fit(X, y, classifier__eval_metric='auc')  # fails

错误:
TypeError: before_fit() got an unexpected keyword argument 'classifier__eval_metric'

关于 xgboost 的版本:
xgboost.__version__ 显示 0.6
pip3 freeze | grep xgboost 显示 xgboost==0.6a2

【问题讨论】:

  • 你试过'roc_auc'吗?
  • 它适用于 sklearn 版本:0.18 xgboost 版本:0.6

标签: python scikit-learn classification pipeline xgboost


【解决方案1】:

错误是因为您在管道中使用时在估算器名称及其参数之间使用了一个下划线。应该是两个下划线。

documentation of Pipeline.fit() 中,我们看到提供合适参数的正确方法:

传递给每个步骤的fit方法的参数,其中每个参数名称都带有前缀,以便步骤s的参数p具有键s__p。

所以在你的情况下,正确的用法是:

pipe.fit(X_train, y_train, classifier__eval_metric='auc')

(注意名称和参数之间有两个下划线)

【讨论】:

  • 不幸的是,这也不起作用,将其添加到原始问题的测试选项中。我认为如果它是分类器的参数(例如nr_estimators)会起作用,但它是该特定分类器的 fit 方法的参数。
  • 我正在使用来自 sklearn 的虹膜数据,它工作正常(没有抛出任何错误)。请更新您的 scikit 和/或 xgboost 版本,然后重试
  • 有趣,能告诉我你使用的版本吗?我正在使用 xgboost 版本 '0.6' 和 sklearn 版本 '0.18.1'
  • 肯定发生了一些奇怪的事情。 xgboost.__version__ 由于某种原因显示与 pip freeze 不同的东西。我更改了示例以使其可与 iris 数据集一起复制,请问您是否可以在您的数据集上运行它? (非常感谢,即使感谢人们不是这样的政策)
  • 我已经编辑了您的复制和粘贴代码。我还尝试了 Python 2.7.6 和 Python 3.4.3,它工作正常。
【解决方案2】:

当目标是优化时,我建议使用 sklearn 包装器和 GridSearchCV

from xgboost.sklearn import XGBClassifier
from sklearn.grid_search import GridSearchCV

看起来像

pipe = Pipeline([('scaler', StandardScaler()), ('classifier', XGBClassifier())])

score = 'roc_auc'
pipe.fit(X, y) 

param = {
 'classifier_max_depth':[1,2,3,4,5,6,7,8,9,10] # just as example
}

gsearch = GridSearchCV(estimator =pipe, param_grid =param , scoring= score)

你也可以使用交叉验证技术

gsearch.fit(X, y)

你会得到最好的参数和最好的分数

gsearch.best_params_, gsearch.best_score_

【讨论】:

    猜你喜欢
    • 2022-10-14
    • 1970-01-01
    • 1970-01-01
    • 2018-08-19
    • 2016-12-24
    • 2021-06-11
    • 2019-05-30
    相关资源
    最近更新 更多