Backtrader量化&回测6——分析师Analyzer使用与添加

Backtrader Analyzer文档:https://www.backtrader.com/docu/analyzers/analyzers/

Backtrader 已有的Analyzer:https://www.backtrader.com/docu/analyzers-reference/

Analyzer 在 Backtrader 的框架中作为一个分析师而存在,用来分析回测的结果,使用方法如下:

  1. 继承backtrader.Analyzer
  2. 覆写def next()函数即可,这里不同于backtrader.Strategynext(),analyzer的next()不会从所有数据集的公共时间的第一天开始,而是从第一个回测时间开始,类似于backtrader.Strategyprenext()

比如下面的示例中,计算日收益率:

class DailyReturnAnalyzer(Analyzer):
    def __init__(self):
        super(DailyReturnAnalyzer, self).__init__()
        self.fund_record = [] # 这里添加自定义的属性

    def next(self):
        self.fund_record.append(self.strategy.broker.getvalue()) # 每一个交易日会执行一次next

    def get_analysis(self): # 最后用于计算综合结果
        fund_record_arr = np.array(self.fund_record)
        daily_return = np.diff(fund_record_arr) / fund_record_arr[0]
        return daily_return

Analyzer同样可以覆写如下的函数:

  • notify_cashvalue(cash, value):每过一个next()都会触发,通知资金情况
  • notify_fund(cash, value, fundvalue, shares):每过一个next()都会触发,通知资金情况
  • notify_order(order):订单状态变化时会触发这个函数,order为当前订单,每一个新订单或订单状态变化都会触发这个函数
  • notify_trade(trade):交易状态变化时会触发这个函数

完整示例代码

from datetime import datetime
import backtrader
import pandas as pd
import efinance
from backtrader import Analyzer
import numpy as np


def get_k_data(stock_code, begin: datetime, end: datetime) -> pd.DataFrame:
    """
    根据efinance工具包获取股票数据
    :param stock_code:股票代码
    :param begin: 开始日期
    :param end: 结束日期
    :return:
    """
    # stock_code = '600519'  # 股票代码,茅台
    k_dataframe: pd.DataFrame = efinance.stock.get_quote_history(
        stock_code, beg=begin.strftime("%Y%m%d"), end=end.strftime("%Y%m%d"))
    k_dataframe = k_dataframe.iloc[:, :9]
    k_dataframe.columns = ['name', 'code', 'date', 'open', 'close', 'high', 'low', 'volume', 'turnover']
    k_dataframe.index = pd.to_datetime(k_dataframe.date)
    k_dataframe.drop(['name', 'code', 'date'], axis=1, inplace=True)
    return k_dataframe


class MyStrategy1(backtrader.Strategy):  # 策略
    def __init__(self):
        # 初始化交易指令、买卖价格和手续费
        self.close_price = self.datas[0].close  # 这里加一个数据引用,方便后续操作
        self.sma = backtrader.indicators.SimpleMovingAverage(self.datas[0], period=5)  # 借用这个策略,计算5日的均线

    def next(self):  # 固定的函数,框架执行过程中会不断循环next(),过一个K线,执行一次next()
        if self.close_price[0] > self.sma[0]:
            self.buy(size=500, price=self.data.close[0])
        if self.position:
            if self.close_price[0] < self.sma[0]:  # 执行卖出条件已有持仓,且收盘价格跌破5日均线,则卖出
                self.sell(size=500, price=self.data.close[0])


class DailyReturnAnalyzer(Analyzer):
    def __init__(self):
        super(DailyReturnAnalyzer, self).__init__()
        self.fund_record = []

    def next(self):
        self.fund_record.append(self.strategy.broker.getvalue())

    def get_analysis(self):
        fund_record_arr = np.array(self.fund_record)
        daily_return = np.diff(fund_record_arr) / fund_record_arr[0]
        return daily_return


def main():
    # 获取数据
    start_time = datetime(2020, 1, 1)
    end_time = datetime(2021, 1, 1)
    dataframe = get_k_data('600519', begin=start_time, end=end_time)
    # =============== 为系统注入数据 =================
    data = backtrader.feeds.PandasData(dataname=dataframe, fromdate=start_time, todate=end_time)  # 加载数据
    cerebral_system = backtrader.Cerebro()
    # 将数据传入回测系统
    cerebral_system.adddata(data)
    cerebral_system.addanalyzer(DailyReturnAnalyzer, _name="my_analyzer")
    # 将交易策略加载到回测系统中
    cerebral_system.addstrategy(MyStrategy1)
    # =============== 系统设置 ==================
    start_cash = 1000000
    cerebral_system.broker.setcash(start_cash)
    cerebral_system.broker.setcommission(commission=0.00025)  # 设置手续费 万2.5
    print('初始资金: {} 回测期间:from {} to {}'.format(start_cash, start_time, end_time))
    # 运行回测系统
    cerebral_result = cerebral_system.run()
    # 根据analyzer获得日收益率
    analyze_result = cerebral_result[0].analyzers[0].get_analysis()
    print(analyze_result)


if __name__ == '__main__':
    main()
  • 2
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

呆萌的代Ma

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值