多个分类器的网格搜索

新手上路,请多包涵

是否有更好的内置方法在单个管道中进行网格搜索和测试多个模型?当然,模型的参数会有所不同,这让我很难弄清楚。这是我所做的:

 from sklearn.pipeline import Pipeline
from sklearn.ensemble import RandomForestClassifier
from sklearn.neighbors import KNeighborsClassifier
from sklearn.svm import SVC
from sklearn.naive_bayes import MultinomialNB
from sklearn.grid_search import GridSearchCV

def grid_search():
    pipeline1 = Pipeline((
    ('clf', RandomForestClassifier()),
    ('vec2', TfidfTransformer())
    ))

    pipeline2 = Pipeline((
    ('clf', KNeighborsClassifier()),
    ))

    pipeline3 = Pipeline((
    ('clf', SVC()),
    ))

    pipeline4 = Pipeline((
    ('clf', MultinomialNB()),
    ))

    parameters1 = {
    'clf__n_estimators': [10, 20, 30],
    'clf__criterion': ['gini', 'entropy'],
    'clf__max_features': [5, 10, 15],
    'clf__max_depth': ['auto', 'log2', 'sqrt', None]
    }

    parameters2 = {
    'clf__n_neighbors': [3, 7, 10],
    'clf__weights': ['uniform', 'distance']
    }

    parameters3 = {
    'clf__C': [0.01, 0.1, 1.0],
    'clf__kernel': ['rbf', 'poly'],
    'clf__gamma': [0.01, 0.1, 1.0],

    }
    parameters4 = {
    'clf__alpha': [0.01, 0.1, 1.0]
    }

    pars = [parameters1, parameters2, parameters3, parameters4]
    pips = [pipeline1, pipeline2, pipeline3, pipeline4]

    print "starting Gridsearch"
    for i in range(len(pars)):
        gs = GridSearchCV(pips[i], pars[i], verbose=2, refit=False, n_jobs=-1)
        gs = gs.fit(X_train, y_train)
        print "finished Gridsearch"
        print gs.best_score_

然而,这种方法仍然是在每个分类器中给出最好的模型,而不是在分类器之间进行比较。

原文由 Aks 发布,翻译遵循 CC BY-SA 4.0 许可协议

阅读 475
2 个回答

您可以使用 “hyperopt”库,而不是使用网格搜索来选择超参数。

请查看 本页 的第 2.2 节。在上述情况下,您可以使用 hp.choice 表达式在各种管道中进行选择,然后分别为每个管道定义参数表达式。

在您的目标函数中,您需要根据所选管道进行检查并返回所选管道和参数的 CV 分数(可能通过 cross_val_score )。

执行结束时的试验对象将指示总体上最好的管道和参数。

原文由 Stergios 发布,翻译遵循 CC BY-SA 4.0 许可协议

尽管 dubek 的解决方案更直接,但它无助于分类器之前的管道元素参数之间的交互。因此,我写了一个 helper类 来处理它,并且可以包含在scikit的默认Pipeline设置中。一个最小的例子:

 from sklearn.pipeline import Pipeline
from sklearn.model_selection import GridSearchCV
from sklearn.preprocessing import StandardScaler, MaxAbsScaler
from sklearn.svm import LinearSVC
from sklearn.ensemble import RandomForestClassifier
from sklearn import datasets
from pipelinehelper import PipelineHelper

iris = datasets.load_iris()
X_iris = iris.data
y_iris = iris.target
pipe = Pipeline([
    ('scaler', PipelineHelper([
        ('std', StandardScaler()),
        ('max', MaxAbsScaler()),
    ])),
    ('classifier', PipelineHelper([
        ('svm', LinearSVC()),
        ('rf', RandomForestClassifier()),
    ])),
])

params = {
    'scaler__selected_model': pipe.named_steps['scaler'].generate({
        'std__with_mean': [True, False],
        'std__with_std': [True, False],
        'max__copy': [True],  # just for displaying
    }),
    'classifier__selected_model': pipe.named_steps['classifier'].generate({
        'svm__C': [0.1, 1.0],
        'rf__n_estimators': [100, 20],
    })
}
grid = GridSearchCV(pipe, params, scoring='accuracy', verbose=1)
grid.fit(X_iris, y_iris)
print(grid.best_params_)
print(grid.best_score_)

它也可以用于管道的其他元素,而不仅仅是分类器。代码在 github 上,如果有人想查看的话。

编辑:如果有人感兴趣,我已经在 PyPI 上发布了这个,只需使用 pip install pipelinehelper 安装 ti。

原文由 bmurauer 发布,翻译遵循 CC BY-SA 4.0 许可协议

撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进
推荐问题
logo
Stack Overflow 翻译
子站问答
访问
宣传栏