使用python计算最大回撤

使用python计算最大回撤

1. 单期简单收益率

Rt=PtPt1Pt1R_{t}=\dfrac {P _{t}-P_{t-1}}{P_{t-1}}
说明:

  1. RtR_t 为单期简单收益率
  2. PtP_t 为t期的价格
  3. Pt1P_{t-1} 为t-1期的价格
import datetime
import pandas as pd
pd.core.common.is_list_like = pd.api.types.is_list_like
price = pd.Series([3.42,3.51,3.68,3.43,3.56,3.67], index=[datetime.date(2015,7,x) for x in range(3,9)])
price
2015-07-03    3.42
2015-07-04    3.51
2015-07-05    3.68
2015-07-06    3.43
2015-07-07    3.56
2015-07-08    3.67
dtype: float64

利用ffn库计算单期简单收益

import ffn
r = ffn.to_returns(price)
r
2015-07-03         NaN
2015-07-04    0.026316
2015-07-05    0.048433
2015-07-06   -0.067935
2015-07-07    0.037901
2015-07-08    0.030899
dtype: float64

2. 最大回撤

最大回撤(Maximum Drawdown, MDD) 用来衡量投资(特别是基金)的表现,

2.1 回撤:某资产在时刻T的回撤是指资产在(0,T)的最高峰值与现在价值PTP_T之间的回落值,用数学公式表达为:

D(T)=max{0,maxt(0,T)PtPT}D\left( T\right) =\max \left\{ 0,\max _{t\in (0,T)}P_t-P_{T}\right\}

2.2 对应的回撤率为:

d(T)=D(T)maxt(0,T)ptd\left(T\right) = \dfrac {D\left( T\right) }{\max _{t\in \left( 0,T\right) }p_{t}}

知道回撤的含义之后,最大回撤就比较容易理解了,资产在T时刻的最大回撤MDD(T),就是资产在时段(0,T)内回撤的最大值,对应的数学公式为:

MDD(T)=maxτ(0,T)D(τ)=maxτ(0,T)[maxt(0,τ)PtPτ]MDD\left(T\right) = {\max _{\tau \in \left(0,T\right)}} D\left(\tau\right) = {\max _{\tau \in \left(0,T\right)}} \begin{aligned} \left[ \max _{t\in \left( 0,\tau \right) }P_{t}-P_{\tau}\right] \end{aligned}

相应的最大回撤率为:
mdd(T)=maxτ(0,T)d(τ)MDD(T)maxt(0,T)Ptmdd\left(T\right) = {\max _{\tau \in \left(0,T\right)}} d\left(\tau \right) \dfrac {MDD\left(T\right)}{\max _{t \in \left(0,T\right)}P_t}

直观的讲,MDD(T)对应的是在(0,T)时段内资产价值从最高峰回落到最低谷的幅度。最大回撤常用来描述投资者在持有资产是可能面临的最大亏损。

2.3 利用收益率计算最大回撤

如果某资产的收益率序列为R1,R2,…,RT,在初始时刻0时,我们投资1元在该资产上并一直持有到T时刻,则初始值为1元的资产价值就会随时间变化为:(1+R1),(1+R1)(1+R2),(1+R1)(1+R2)(1+R3),…,k=1T(1+Rk)\prod _{k=1}^{T}\left( 1+R_{k}\right)

时刻T对应的回撤值为:
D(T)=max{0,maxt(0,T)k=1t(1+Rk)k=1T(1+Rk)}D(T) = \max \left\{ 0, \max _{t \in (0,T)} \prod _{k=1}^{t}\left( 1+R_{k}\right) - \prod _{k=1}^{T}\left( 1+R_{k}\right) \right\}

相应的回撤率为:
d(T)=D(T)maxt(0,T)k=1t(1+Rk)d(T) = \dfrac {D\left( T\right) }{\max _{t\in \left( 0,T\right) }\prod _{k=1}^{t}\left( 1+R_{k}\right) }

最大回撤为:
MDD(T)=maxτ(0,T)D(τ)=maxτ(0,T)[maxt(0,τ)k=1t(1+Rk)k=1τ(1+Rk)]MDD(T) = \max _{\tau \in \left( 0,T\right) }D\left( \tau \right) = \max _{\tau \in \left( 0,T\right) } \begin{aligned} \left[\max _{t\in \left( 0,\tau \right) }\prod _{k=1}^{t}\left( 1+R_{k}\right) - \prod _{k=1}^{\tau}\left( 1+R_{k}\right) \right]\end{aligned}

相应的最大回撤率为:
mdd(T)=maxτ(0,T)d(τ)=MDD(T)maxt(0,T)k=1t(1+Rk)mdd(T) = \max _{\tau \in \left( 0,T\right) }d(\tau) = \dfrac {MDD(T)}{\max _{t \in \left( 0,T\right) }\prod _{k=1}^{t}\left( 1+R_{k}\right)}

value = (1 + r).cumprod()
value
2015-07-03         NaN
2015-07-04    1.026316
2015-07-05    1.076023
2015-07-06    1.002924
2015-07-07    1.040936
2015-07-08    1.073099
dtype: float64
D = value.cummax() - value
D
2015-07-03         NaN
2015-07-04    0.000000
2015-07-05    0.000000
2015-07-06    0.073099
2015-07-07    0.035088
2015-07-08    0.002924
dtype: float64
d = D / (D + value)
d
2015-07-03         NaN
2015-07-04    0.000000
2015-07-05    0.000000
2015-07-06    0.067935
2015-07-07    0.032609
2015-07-08    0.002717
dtype: float64
MDD = D.max()
MDD
0.07309941520467844
mdd =d.max()
mdd
# 对应的最大回撤率值为
0.06793478260869572
# 采用ffn库计算收益率累积最大回撤
ffn.calc_max_drawdown(value)
-0.06793478260869568
from empyrical import max_drawdown
# 使用 empyrical 计算收益率序列最大回撤
max_drawdown(r)
-0.06793478260869572
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章