Here's my winning algo that dropped below $90K today and was stopped, per the contest rules, by Quantopian. --Grant

Clone Algorithm

1736

Loading...

There was an error loading this backtest.

Backtest from
to
with
initial capital

Cumulative performance:

Algorithm
Benchmark

Custom data:

Total Returns

--

Alpha

--

Beta

--

Sharpe

--

Sortino

--

Max Drawdown

--

Benchmark Returns

--

Volatility

--

Returns | 1 Month | 3 Month | 6 Month | 12 Month |

Alpha | 1 Month | 3 Month | 6 Month | 12 Month |

Beta | 1 Month | 3 Month | 6 Month | 12 Month |

Sharpe | 1 Month | 3 Month | 6 Month | 12 Month |

Sortino | 1 Month | 3 Month | 6 Month | 12 Month |

Volatility | 1 Month | 3 Month | 6 Month | 12 Month |

Max Drawdown | 1 Month | 3 Month | 6 Month | 12 Month |

import numpy as np import pandas as pd def initialize(context): context.stocks = [ sid(7792), sid(3951), sid(3496), sid(5328), sid(2190), sid(3149), sid(4922), sid(7041), sid(2119), sid(24), sid(5061), sid(26578), sid(6295), sid(3212), sid(368), sid(1900), sid(16841), sid(1637) ] context.m = len(context.stocks) context.eps = 1.0028 # change epsilon here context.b_t = np.ones(context.m) / context.m schedule_function(trade, date_rules.every_day(), time_rules.market_open(minutes=60)) def handle_data(context,data): pass def trade(context,data): prices = history(20*390,'1m','price') prices = pd.ewma(prices, span = 390).as_matrix(context.stocks) # skip bar if any orders are open for stock in context.stocks: if bool(get_open_orders(stock)): return sum_weighted_port = np.zeros(context.m) sum_weights = 0 for n in range(0,len(prices[:,0])+1): (weight,weighted_port) = get_weighted_port(data,context,prices,n) sum_weighted_port += weighted_port sum_weights += weight allocation_optimum = sum_weighted_port/sum_weights rebalance_portfolio(context, allocation_optimum) def get_weighted_port(data,context,prices,n): # update portfolio for i, stock in enumerate(context.stocks): context.b_t[i] = context.portfolio.positions[stock].amount*data[stock].price denom = np.sum(context.b_t) # test for divide-by-zero case if denom == 0.0: context.b_t = np.ones(context.m) / context.m else: context.b_t = np.divide(context.b_t,denom) x_tilde = np.zeros(context.m) b = np.zeros(context.m) # find relative moving volume weighted average price for each secuirty for i, stock in enumerate(context.stocks): mean_price = np.mean(prices[-n:,i]) x_tilde[i] = mean_price/prices[-1,i] ########################### # Inside of OLMAR (algo 2) x_bar = x_tilde.mean() # Calculate terms for lambda (lam) dot_prod = np.dot(context.b_t, x_tilde) num = context.eps - dot_prod denom = (np.linalg.norm((x_tilde-x_bar)))**2 # test for divide-by-zero case if denom == 0.0: lam = 0 # no portolio update else: lam = max(0, num/denom) b = context.b_t + lam*(x_tilde-x_bar) b_norm = simplex_projection(b) weight = np.dot(b_norm,x_tilde) return (weight,weight*b_norm) def rebalance_portfolio(context, desired_port): for i, stock in enumerate(context.stocks): order_target_percent(stock, desired_port[i]) def simplex_projection(v, b=1): """Projection vectors to the simplex domain Implemented according to the paper: Efficient projections onto the l1-ball for learning in high dimensions, John Duchi, et al. ICML 2008. Implementation Time: 2011 June 17 by [email protected] AT pmail.ntu.edu.sg Optimization Problem: min_{w}\| w - v \|_{2}^{2} s.t. sum_{i=1}^{m}=z, w_{i}\geq 0 Input: A vector v \in R^{m}, and a scalar z > 0 (default=1) Output: Projection vector w :Example: >>> proj = simplex_projection([.4 ,.3, -.4, .5]) >>> print proj array([ 0.33333333, 0.23333333, 0. , 0.43333333]) >>> print proj.sum() 1.0 Original matlab implementation: John Duchi ([email protected]) Python-port: Copyright 2012 by Thomas Wiecki (thomas.w[email protected]). """ v = np.asarray(v) p = len(v) # Sort v into u in descending order v = (v > 0) * v u = np.sort(v)[::-1] sv = np.cumsum(u) rho = np.where(u > (sv - b) / np.arange(1, p+1))[0][-1] theta = np.max([0, (sv[rho] - b) / (rho+1)]) w = (v - theta) w[w<0] = 0 return w

We have migrated this algorithm to work with a new version of the Quantopian API. The code is different than the original version, but the investment rationale of the algorithm has not changed. We've put everything you need to know here on one page.