| Overall Statistics |
|
Total Trades 146 Average Win 2.42% Average Loss -1.92% Compounding Annual Return 16.161% Drawdown 13.800% Expectancy 0.682 Net Profit 71.407% Sharpe Ratio 1.384 Probabilistic Sharpe Ratio 67.727% Loss Rate 26% Win Rate 74% Profit-Loss Ratio 1.26 Alpha 0.139 Beta 0.152 Annual Standard Deviation 0.124 Annual Variance 0.015 Information Ratio -0.176 Tracking Error 0.217 Treynor Ratio 1.129 Total Fees $1380.50 Estimated Strategy Capacity $600000.00 Lowest Capacity Asset SVXY V0H08FY38ZFP |
# Go long SVXY (short volatility) for a short term hold expecting volatility to drop.
# Uses 3 entries, the first entry signal doesn't create a position, the second does.
# Use a SMA 4 and SMA13 on SVXY, and SPY adx. If the SMA4<SMA13, and the OHLC of SVXY is above SMA4 and SPY adx<30 then go long SVXY.
# When the SMA4>SMA13 and the SVXY OHLC goes above the SMA4 then exit.
class ShortVolwithSVXY(QCAlgorithm):
def Initialize(self):
self.SetStartDate(2018, 2, 5) # (2018,2,5) is the date of the deleveraging to 0.5x
#self.SetEndDate(2018, 2, 1)
self.SetCash(100000)
self.svxy = self.AddEquity("SVXY", Resolution.Minute)
self.spy = self.AddEquity("SPY", Resolution.Minute)
self.AddEquity("IEF", Resolution.Minute)
self.AddEquity("UST", Resolution.Minute)
self.svxy.SetDataNormalizationMode(DataNormalizationMode.Raw)
self.smaFast = self.SMA("SVXY", 4, Resolution.Daily)
self.smaSlow = self.SMA("SVXY", 13, Resolution.Daily)
self.adx = self.ADX("SPY", 30, Resolution.Daily)
self.SetWarmUp(30) # warm up the indicator
self.Schedule.On(self.DateRules.EveryDay("SVXY"), self.TimeRules.BeforeMarketClose("SVXY", 15), self.Rebalance)
self.targets = {0:0, 1:0.15, 2:0.25, 3:1} # dictionary to hold our target position sizes {position count: % allocation}
self.counter = 0 # counts what target position we are at, start at zero for first position
self.SetRiskManagement(MaximumDrawdownPercentPerSecurity(0.12))
def OnData(self, data):
if data.ContainsKey("SVXY") == False: return
self.OHLC = (self.Securities["SVXY"].Open+self.Securities["SVXY"].High+self.Securities["SVXY"].Low+self.Securities["SVXY"].Price)/4
def Rebalance(self):
if self.adx.Current.Value<30 and self.OHLC > self.smaFast.Current.Value and self.smaFast.Current.Value<self.smaSlow.Current.Value:
# if we add 1 to our current position count and it is greater than our 100% allocation, then we do nothing
if self.counter + 1 not in self.targets:
return
# since this is a new buy signal, we look at our current position counter and go up to the next allocation amount
self.counter += 1
#self.SetHoldings("IEF", 0, True) # just testing what would be a good sideline security while waiting for the next SVXY trade
self.SetHoldings("SVXY", self.targets[self.counter])
self.Debug("Buy SVXY")
if self.OHLC>self.smaFast.Current.Value and self.smaFast.Current.Value>self.smaSlow.Current.Value:
self.SetHoldings("SVXY", 0)
#self.SetHoldings("IEF", 1)
self.counter = 0
self.Debug("Sell SVXY")
else:
pass