量化交易学习笔记(9) 使用Hyperopt 对L策略的超参数优化

使用Hyperopt 对策略的超参数优化

    • 前言
    • BOLL策略
    • 数据回测
      • 初始化
      • 优化后
      • 测试数据
    • 代码
      • Hyperopt 优化器
      • Boll策略
      • 主程序
    • 总结

前言

一文详解模型调参神器:Hyperopt,体验后真的很棒

在实现量化交易策略后,对模型参数调优可以通过框架自带的调优器,也可自己些调优的小程序,或者一些参数调优的库,Hyperopt使用贝叶斯优化的形式进行参数调整,允许你为给定模型获得最佳参数,它可以在大范围内优化具有数百个参数的模型,Hyperopt功能强大,性能优异,所以本文带来Hyperopt对模型参数优化。

BOLL策略

  • 介绍

布林带宽度(Bollinger Band Width)是美国股市分析家约翰·布林于2010年发明,用于测量布林带(Bollinger Bands于1980年发明)上下轨道线之间的相对距离。它随带宽变窄而减小,而随着带宽放宽而增加。因为布林带基于标准差,所以带宽的波动幅度可以反映波动性,并且可视为波动率指标。布林带由三条不同的线组成,包括简单移动平均线及正负距离两个标准差的上下轨道线。可为日常股票交易决策提供参考依据,是金融市场常用的技术指标之一。

  • 信号

在突破boll通道上轨买入
在跌破boll通道下轨平仓

-订单

交易价格:昨日收盘价*(1 - C)
止损价格: 交易价格*(1 - L)
止盈价格:交易价格*(1 + S)
交易量:min(可用资金/ SMA,交易量)

数据回测

初始化

回测 Value
DOTUSDT_1h 2020-08-24 到 2022-07-08
boll周期 9
收益率 228%

量化交易学习笔记(9) 使用Hyperopt 对L策略的超参数优化_第1张图片

优化后

回测 Value
DOTUSDT_1h 2020-08-24 到 2022-07-08
boll周期 43
收益率 1726.07%
量化交易学习笔记(9) 使用Hyperopt 对L策略的超参数优化_第2张图片

测试数据

下面的数据有兴趣的小伙伴自行尝试

{
    "策略名称":"BollStrategy",
    "运行时间":"12.786108616987864分钟",
    "数据源":"D:\\work\\git\\Tools\\static\\data\\SOLUSDT_1h.csv",
    "收益率":"163874.15299064145 %",
    "参数":{
        "period":278.34501260009176
    }
}
{
    "策略名称":"BollStrategy",
    "运行时间":"0.9963125467300415分钟",
    "数据源":"D:\\work\\git\\Tools\\static\\data\\OPUSDT_1h.csv",
    "收益率":"234.9051745737002 %",
    "参数":{
        "period":299.9132638182971
    }
}
{
    "策略名称":"BollStrategy",
    "运行时间":"13.492177633444468分钟",
    "数据源":"D:\\work\\git\\Tools\\static\\data\\KNCUSDT_1h.csv",
    "收益率":"5901.495375774953 %",
    "参数":{
        "period":142.0523650680161
    }
}
{
    "策略名称":"BollStrategy",
    "运行时间":"2.452657969792684分钟",
    "数据源":"D:\\work\\git\\Tools\\static\\data\\GMTUSDT_1h.csv",
    "收益率":"56170.06056933173 %",
    "参数":{
        "period":93.09081580846353
    }
}
{
    "策略名称":"BollStrategy",
    "运行时间":"64.45960373481115分钟",
    "数据源":"D:\\work\\git\\Tools\\static\\data\\ETHUSDT_30m.csv",
    "收益率":"754213.6102849536 %",
    "参数":{
        "period":235.62271521989342
    }
}
{
    "策略名称":"BollStrategy",
    "运行时间":"32.046370434761045分钟",
    "数据源":"D:\\work\\git\\Tools\\static\\data\\BTCUSDT_1h.csv",
    "收益率":"32261.19551698138 %",
    "参数":{
        "period":285.67352340101354
    }
}
{
    "策略名称":"BollStrategy",
    "运行时间":"30.425016216437022分钟",
    "数据源":"D:\\work\\git\\Tools\\static\\data\\BNBUSDT_1h.csv",
    "收益率":"839850.7548190868 %",
    "参数":{
        "period":271.69678493757556
    }
}

代码

Hyperopt 优化器

class Optimizer:

    def __init__(self, data, space, strategy_func, max_evals=500, is_send_ding_task=False):
    	# 数据
        self.data = data
        # 迭代次数
        self.max_evals = max_evals
        # 是否把结果发送钉钉
        self.is_send_ding_task = is_send_ding_task
        # 策略参数
        self.params = None
        # 初始资金
        self.cash = 10000
        # 参数空间
        self.space = space
        # 添加策略函数
        self.strategy_func = strategy_func

    def target_func(self, params):

        cerebro = run_strategy(func=self.strategy_func, data=self.data,
                               cash=self.cash, params=params)
        return -cerebro.broker.getvalue()

    def run(self):
        trials = Trials()
        self.params = fmin(fn=self.target_func, space=self.space, algo=tpe.suggest, max_evals=self.max_evals,
                           trials=trials)
        logging.info(self.params)
        return self.params

    def plot(self):
        run_strategy(func=self.strategy_func, data=self.data, params=self.params, is_show=True)

Boll策略

class BollStrategy(bt.Strategy):
    params = dict(
        is_log=False,
        period=20
    )

    def log(self, txt, dt=None):
        if self.p.is_log:
            dt = dt or self.datas[0].datetime.date(0)
            print('%s,%s' % (dt.isoformat(), txt))

    def __init__(self):
        # 指定价格序列
        self.dataclose = self.datas[0].close
        # 交易订单状态初始化
        self.order = None
        # 上轨
        self.lines.top = bt.indicators.BollingerBands(period=self.p.period).top
        # 下轨
        self.lines.bot = bt.indicators.BollingerBands(period=self.p.period).bot

    def get_buy_unit(self):
        size = self.broker.getcash() / self.data.high[0] * 0.5
        if size == 0:
            size = 0
        return size

    def next(self):
        # 检查订单状态
        if self.order:
            return

        # 检查持仓
        if not self.position:
            # 没有持仓,买入开仓
            if self.dataclose <= self.lines.bot[0]:
                self.order = self.buy(size=self.get_buy_unit())


        else:
            # 手里有持仓,判断卖平
            if self.dataclose >= self.lines.top[0]:
                self.close()

    def notify(self, order):

        if order.status in [order.Submitted, order.Accepted]:
            if order.status in [order.Submitted]:
                self.log("提交订单......")
            if order.status in [order.Accepted]:
                self.log("接受订单......")
            return

        # Check if an order has been completed
        # Attention: broker could reject order if not enougth cash
        if order.status in [order.Completed, order.Canceled, order.Margin]:
            if order.isbuy():
                self.log('执行买入, %.2f' % order.executed.price)
                gloVar['buy_count'] = gloVar['buy_count'] + 1
            elif order.issell():
                self.log('执行卖出, %.2f' % order.executed.price)
                gloVar['sell_count'] = gloVar['sell_count'] + 1
            self.bar_executed = len(self)

        self.log("订单完成......")

        # Write down: no pending order
        self.order = None

主程序


if __name__ == '__main__':
    space = dict(
        period=hp.uniform("period", 10, 400)
    )
    opt = Optimizer(data=get_data("D:\\work\\git\\Tools\\static\\data\\DOTUSDT_1h.csv"),

                    strategy_func=add_bool_boll_strategy, space=space, max_evals=500)
    params = opt.run()
    print(params)
    opt.plot()

总结

目前从回测结果来看,该策略表现还行,把bool周期调大,减少开仓的次数,较小市场的波动,可持续性盈利。未来10年,实现财富自由,加油!!!!

你可能感兴趣的:(量化交易,学习,python,金融)