欢迎光临
专业期货策略平台

Pyfolio一行代码实现专业量化回测图表

引言

量化回测是量化投资中不可或缺的步骤,是构建、评价和优化策略的重要手段。策略回测归根结底是对历史资金曲线的回测,不管是中低频(日、周、月等)还是高频(时、分、秒)交易策略,只要我们根据既定的交易策略获得该交易频率下的历史收益率,便可以对策略进行量化评价,常见的评价指标包括年化收益、累计收益、最大回撤、夏普比率等等。那么有没现成的量化模块库既可以实现计算量化评价指标,还可以输出专业级的量化图表呢?答案是pyfolio

pyfolio 是全球最大量化网站Quantopian开发的量化“三剑客”之一,另外两个分别是alphalens(用于多因子分析)和zipline(类似backtrader的回测框架)。pyfolio非常适合用于金融投资组合性能和风险分析,包括与Zipline和alphalens结合,输出专业的量化指标和图表分析结果。关于alphalens的应用参照推文《如何对选股因子进行量化回测?》。pyfolio和alphalens直接使用pip即可安装,而zipline由于各种原因一直未安装成功。

pyfolio的核心是一种所谓的tears表,由各种独立的量化回测结果组成,提供交易算法性能的综合图表。下面通过一个简单的例子为大家展示pyfolio的用法。

pyfolio回测实例

下面使用tushare获取个股和指数交易数据,以简单的买入持有作为交易策略进行简单回测,实际上其他交易策略和投资组合均可以以类似方式进行回测,关键是得到策略的资金曲线(即某交易策略或组合的最终收益率时间序列)。

import pandas as pd
import tushare as ts
import pyfolio as pf

获取数据

def get_return(code):
    df=ts.get_k_data(code,start='2010-01-01')
    df.index=pd.to_datetime(df.date)
    return df.close.pct_change().fillna(0).tz_localize('UTC')
ret=get_return('600519')
benchmark_ret=get_return('sh')
#假设前面是模拟盘,2017年开始实盘买入600519并一直持有
date='2017-01-03'

pyfolio一行代码进行回测

pyfolio的create_full_tear_sheet函数可以实现一行代码输出所有量化回测结果和图表,具体参数包括:

其中,returns就是我们要输入的收益率时间序列数据(pd.Series),其他默认参数均为可选项,如benchmark_rets(pd.DataFrame)是策略或组合的基准收益率,用于对比分析,live_start_date是指定个时间开始进行实盘交易分析。如果要单独输出某个量化结果图表,可以通过输入pf.create_xxx_tear_sheet (returns),如输出收益相关量化结果图表,则xxx为returns,具体可参考pyfolio源代码中的tears.py,该文件提供了各种图表的输出函数和详细的参数说明。

pf.create_full_tear_sheet(returns=ret,benchmark_rets=benchmark_ret,live_start_date=date)

量化回测基本统计指标

Pyfolio一行代码实现专业量化回测图表
Pyfolio一行代码实现专业量化回测图表

结果显示,量化回测开始日期为2010年1月4日,结束日期为2021年5月28日。由于设定了实盘起始日期为2017年1月3日,pyfolio将数据分为样本内(in-sample,2010.1.4-2017.1.3)和样本外(out of sample,2017.1.4-2021.5.28)进行回测。Annual return是年化收益率,从样本外回测看,如果你在2017年1月3日后买入贵州茅台一直持有,年化收益率达到57%,累计收益率(Cumulative returns)为587%,年化波动率31.6%,夏普比率(Sharpe ratio)为1.59,最大回撤为-33.5%,关于这些指标的定义和计算可参照推文:《【手把手教你】Python量化策略风险指标》。

最大回撤率与持续期间

Pyfolio一行代码实现专业量化回测图表

事件分析(event study)

pyfolio还提供了事件分析的量化结果,如欧债危机、2010年5月的闪电暴跌(FlashCrash)事件期间该策略的收益率情况。

Pyfolio一行代码实现专业量化回测图表

下面输出的的累计收益率(含基准对比)、波动率、滚动夏普比率、最大回撤、月度收益率等的量化结果的可视化图。

Pyfolio一行代码实现专业量化回测图表

极端事件期间的收益率分析

与backtrader相结合

此外,pyfolio还可以为backtrader的回测结果提供图表分析。关于backtrader的应用可参考公众号系列图文:【手把手教你】入门量化回测最强神器backtrader(一)、【手把手教你】入门量化回测最强神器backtrader(二) 、【手把手教你】入门量化回测最强神器backtrader(三)、backtrader如何加载股票因子数据?以换手率、市盈率为例进行回测【附Python代码】、 如何用backtrader对股票组合进行量化回测?、【手把手教你】用backtrader量化回测海龟交易策略、backtrader股票技术指标自定义与量化回测。

import backtrader as bt
from datetime import datetime

class MyStrategy(bt.Strategy):
    pass(略)
#假设数据为df
data = bt.feeds.PandasData(dataname=df)
# 初始化cerebro回测系统设置                           
cerebro = bt.Cerebro()  
# 加载数据
cerebro.adddata(data) 
# 将交易策略加载到回测系统中
cerebro.addstrategy(MyStrategy) 
# 设置初始资本为10,000
cerebro.broker.setcash(100000.0) 
#每次固定交易数量
cerebro.addsizer(bt.sizers.FixedSize, stake=1000) 
#手续费
cerebro.broker.setcommission(commission=0.001) 
#运行回测系统
cerebro.addanalyzer(bt.analyzers.PyFolio, _name='pyfolio')
results = cerebro.run()
strat = results[0]
pyfoliozer = strat.analyzers.getbyname('pyfolio')
returns, positions, transactions, gross_lev = pyfoliozer.get_pf_items()
# pyfolio showtime
import pyfolio as pf
pf.create_full_tear_sheet(returns)

从上述代码不难看出,应用在backtrader回测框架中,关键是在analyzer模块中使用PyFolio获取相应的数据,即只要获取returns收益系列数据,就能使用pyfolio输出专业化的量化回测结果图表。实际上backtrader能提供收益、头寸、交易费用、杠杆等更多数据,这些结果都可以作为输入项在pyfolio作进一步分析。

结语

本文以一个简单例子介绍了pyfolio在量化回测中的应用,要想更深入的研究和使用该模块的相关函数,最好的方法是分析安装包的源代码。目前随着量化的流行和python等编程语言的普及,国内外呈现出大量的量化在线平台和开源回测框架,参见推文【推荐收藏】倾心整理的Python量化资源大合集。量化在线平台为我们学习和研究策略提供了大量资源,但是量化投资中策略永远是核心,真正赚钱的策略一般是不公开的,因此量化回测单机才是王道,这也是本人一直不习惯在某平台上进行回测的原因(平台与平台之间代码不能很好的移植)。从单机回测来看,pyfolio的应用是很广泛的,类似于pandas之于数据处理。

资料来源:

Quantopian Github: https://github.com/quantopian

Pyfolio:https://github.com/quantopian/pyfolio

0 0 vote
Article Rating
Click to rate this post!
[Total: 0 Average: 0]
赞(5) 打赏
未经允许不得转载:A期客 » Pyfolio一行代码实现专业量化回测图表
订阅
提醒
guest
1 评论
Oldest
Newest Most Voted
Inline Feedbacks
View all comments
QQ1171513819
QQ1171513819
1 年 之前

ATFX黄金外汇平台诚招代理商

觉得文章有用就打赏一下文章作者

非常感谢你的打赏,我们将继续给力更多优质内容,让我们一起创建更加美好的网络世界!

支付宝扫一扫打赏

微信扫一扫打赏

1
0
Would love your thoughts, please comment.x
()
x