点此获取扫地僧backtrader技术教程
======================================
多股组合操作的核心是在每个再平衡日确定各个股票的权重(即资金分配比率)。这属于组合(portfolio)优化的范畴,最经典的是采用马科维茨均值方差理论进行组合优化。
还有一种确定权重的方法叫等波动率权重法,equal volatility weighted portfolio,基本上就是收益率的波动率越大的股票权重越小,波动率越小的权重越大。
有人用backtrader实现了这个策略,见这里,代码如下:
import numpy as np
import pandas as pd
from . import BaseStrategy as base
class EqualVolatility(base.Strategy):
"""
Given a set of equities, balance volatilities monthly.
"""
params = {
'rebalance_days': 21,
'target_percent': 0.95,
'lookback': 21
}
def __init__(self):
base.Strategy.__init__(self)
def rebalance(self):
vols = []
for d in self.datas:
returns = pd.Series(d.close.get(size=self.params.lookback))
returns = np.log(returns).diff().iloc[1:]
vol = returns.std()
vols.append(vol)
vols = np.array(vols)
order_sort = []
weights = []
for v, d in zip(vols, self.datas):
weight = (1.0 / v) / sum(1.0 / vols)
weights.append(weight)
position = self.getposition(d)
position_value = position.size * position.price
order_target = self.params.target_percent * weight * self.broker.get_value()
order_sort.append(order_target - position_value)
for s, d, w in sorted(zip(order_sort, self.datas, weights), key=lambda pair: pair[0]):
self.order_target_percent(d, self.params.target_percent * w)
def next(self):
if self.order:
# Skip if order is pending
return
# Rebalance portfolio
if len(self) % self.params.rebalance_days == 0:
self.rebalance()
# Retry order on next day if rejected
elif self.order_rejected:
self.rebalance()
self.order_rejected = False
这个代码中值得关注的有两点:
1 收益率波动率的计算方法,如下。它将股票收盘价序列先转换成pandas series,后面利用普通的pandas功能和numpy进行操作,有借鉴意义。当然,其实也可以用backtader内置的指标来计算收益率和波动率,读者可以去查backtrader指标文档。
def rebalance(self):
vols = []
for d in self.datas:
returns = pd.Series(d.close.get(size=self.params.lookback))
returns = np.log(returns).diff().iloc[1:]
vol = returns.std()
vols.append(vol)
vols = np.array(vols)2 等波动率权重的计算,程序中是weight = (1.0 / v) / sum(1.0 / vols)。
计算原理公式如下
![]() |
|