使用skopt贝叶斯搜索寻找scikit-learn中算法的最优超参数

栏目: 数据库 · 发布时间: 6年前

内容简介:机器学习的寻找最优超参数是个老大难问题,scikit-learn提供了网格搜索GridSearchCV和随机搜索RandomizedSearchCV这两个函数来帮助寻找这些超参数。网格搜索的本质就是对参数空间形成的所有参数组合进行一个个的尝试,然后选出得分最高的那个,可能会忽略这些组合以外的参数,同时随着参数的增多,计算量也会指数增加。随机搜索是对参数的随机搜索,但没有充分利用搜索空间的结构。skopt是一个超参数优化库,包括随机搜索、贝叶斯搜索、决策森林和梯度提升树等,用于辅助寻找机器学习算法中的最优超

机器学习的寻找最优超参数是个老大难问题,scikit-learn提供了网格搜索GridSearchCV和随机搜索RandomizedSearchCV这两个函数来帮助寻找这些超参数。网格搜索的本质就是对参数空间形成的所有参数组合进行一个个的尝试,然后选出得分最高的那个,可能会忽略这些组合以外的参数,同时随着参数的增多,计算量也会指数增加。随机搜索是对参数的随机搜索,但没有充分利用搜索空间的结构。

skopt是一个超参数优化库,包括随机搜索、贝叶斯搜索、决策森林和梯度提升树等,用于辅助寻找机器学习算法中的最优超参数。这里是利用skopt的贝叶斯搜索来替代scikit-learn中的默认搜索方法,从而更快更好地寻找到最优超参数。

本文是对这个 官方文档 的翻译。

上手实例

用skopt来优化sklearn的支持向量机分类器:

from skopt import BayesSearchCV
from sklearn.datasets import load_digits
from sklearn.svm import SVC
from sklearn.model_selection import train_test_split

X, y = load_digits(10, True)
X_train, X_test, y_train, y_test = train_test_split(X, y, train_size=0.75, random_state=0)

opt = BayesSearchCV(
    SVC(),
    {
        'C': (1e-6, 1e+6, 'log-uniform'),
        'gamma': (1e-6, 1e+1, 'log-uniform'),
        'degree': (1, 8), # 整型类型的空间
        'kernel': ['linear', 'poly', 'rbf'], # Categorical类型的空间
    },
    n_iter = 32
)

opt.fit(X_train, y_train)

print("val. score: %s" % opt.best_score_)
print("test score: %s" % opt.score(X_test, y_test))

由上面定义的搜索空间可以看出,skopt只需给定参数的上下界即可,它会自动在此范围内寻找。注意那个log-uniform,这样指定的话,就会以通过改变x而改变exp(x)这样的形式变动参数。

进阶实例

这个例子给出了使用多个模型及其对应的搜索空间:

from skopt import BayesSearchCV
from skopt.space import Real, Categorical, Integer

from sklearn.datasets import load_digits
from sklearn.svm import LinearSVC, SVC
from sklearn.pipeline import Pipeline
from sklearn.model_selection import train_test_split

X, y = load_digits(10, True)
X_train, X_test, y_train, y_test = train_test_split(X, y, train_size=0.75, random_state=0)

pipe = Pipeline(
    [
        ('model', SVC())
    ])

# 隐式地指定参数类型
linsvc_search = {
    'model': [LinearSVC(max_iter=10000)],
    'model__C': (1e-6, 1e+6, 'log-uniform'),
}
# 显式地指定参数类型
svc_search = {
    'model': Categorical([SVC()]),
    'model__C': Real(1e-6, 1e+6, prior='log-uniform'),
    'model__gamma': Real(1e-6, 1e+1, prior='log-uniform'),
    'model__degree': Integer(1,8),
    'model__kernel': Categorical(['linear', 'poly', 'rbf']),
}

opt = BayesSearchCV(
    pipe,
    [(svc_search, 20), (linsvc_search, 16)], # (parameter space, # of evaluations)
)

opt.fit(X_train, y_train)

print("val. score: %s" % opt.best_score_)
print("test score: %s" % opt.score(X_test, y_test))

使用fit函数的callback参数实现过程监控

可以实现在每一步子空间探索过程中通过一个事件句柄来监控BayesSearchCV的进度。对于串行任务,每一步评估后调用,对于并行任务,当并行执行了n_jobs后调用。

除此以外,如果callback返回了True,还可以停止进程。这可以用于当精度足够高时提前终止学习。

from skopt import BayesSearchCV

from sklearn.datasets import load_iris
from sklearn.svm import SVC

X, y = load_iris(True)

searchcv = BayesSearchCV(
    SVC(),
    search_spaces={'C': (0.01, 100.0, 'log-uniform')},
    n_iter=10
)


# callback handler
def on_step(optim_result):
    score = searchcv.best_score_
    print("best score: %s" % score)
    if score >= 0.98:
        print('Interrupting!')
        return True


searchcv.fit(X, y, callback=on_step)
``` 

# 计算探索所有子空间所需的总迭代次数
```python
from skopt import BayesSearchCV

from sklearn.datasets import load_iris
from sklearn.svm import SVC

X, y = load_iris(True)

searchcv = BayesSearchCV(
    SVC(),
    search_spaces=[
        ({'C': (0.1, 1.0)}, 19),  # 19 iterations for this subspace
        {'gamma':(0.1, 1.0)}
    ],
    n_iter=23
)

print(searchcv.total_iterations)

以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,也希望大家多多支持 码农网

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

挑战编程

挑战编程

斯基纳 / 刘汝佳 / 2009-7 / 39.00元

《挑战编程:程序设计竞赛训练手册》分为14章,分别介绍在线评测系统的基本使用方法、数据结构、字符串、排序、算术与代数、组合数学、数论、回溯法、图遍历、图算法、动态规划、网格、几何,以及计算几何,并在附录中介绍了一些著名的程序设计竞赛以及相应的备赛建议与比赛技巧。每章的正文用十余页的篇幅覆盖了该领域最核心的概念和算法,然后给出八道可在线提交的完整编程挑战题目供读者练习。 全书内容紧凑、信息量大......一起来看看 《挑战编程》 这本书的介绍吧!

JSON 在线解析
JSON 在线解析

在线 JSON 格式化工具

XML 在线格式化
XML 在线格式化

在线 XML 格式化压缩工具

HEX HSV 转换工具
HEX HSV 转换工具

HEX HSV 互换工具