Overall Statistics |
Total Trades 11 Average Win 9.92% Average Loss -2.25% Compounding Annual Return 7.539% Drawdown 8.900% Expectancy 2.245 Net Profit 71.510% Sharpe Ratio 0.97 Probabilistic Sharpe Ratio 43.054% Loss Rate 40% Win Rate 60% Profit-Loss Ratio 4.41 Alpha 0.066 Beta -0.018 Annual Standard Deviation 0.066 Annual Variance 0.004 Information Ratio -0.36 Tracking Error 0.173 Treynor Ratio -3.512 Total Fees $147.74 Estimated Strategy Capacity $3300000000.00 Lowest Capacity Asset SPY R735QTJ8XC9X |
class SmoothOrangeWhale(QCAlgorithm): def Initialize(self): self.SetStartDate(2014, 1, 1) # Set Start Date self.SetCash(1000000) # Set Strategy Cash self.SetBrokerageModel(BrokerageName.AlphaStreams) self.spy = self.AddEquity("SPY",Resolution.Daily).Symbol self.zzhl = ZigZagHighLow(self,"custom",100,0.1,0.5) self.RegisterIndicator(self.spy,self.zzhl,Resolution.Daily) self.SetWarmUp(100) def OnData(self, data): if not self.zzhl.IsReady: return if self.zzhl.Value>0 and not self.Portfolio.Invested: self.SetHoldings(self.spy,0.5) else: if self.zzhl.Value<0 and self.Portfolio.Invested: self.Liquidate() class ZigZagHighLow(PythonIndicator): def __init__(self,algorithm,symbol,length = 100 ,percent_change = 0.02 ,atr_reversal = 0 ): self.algorithm = algorithm self.name = symbol self.high_index = 0 self.low_index = 0 self.dir = False self.Value = 0 self.Period = length self.percent_change = percent_change self.atr_reversal = atr_reversal self.high_window = RollingWindow[float](length) self.low_window = RollingWindow[float](length) self.atr = AverageTrueRange(10,MovingAverageType.Simple) def Update(self,bar): self.high_window.Add(bar.High) self.low_window.Add(bar.Low) self.high_index = max(0,min(self.high_index+1,self.high_window.Count-1)) self.low_index = max(0,min(self.low_index+1,self.low_window.Count-1)) self.atr.Update(bar) if not self.dir: if(bar.Low<((self.getHigh()*(1-self.percent_change))-(self.atr.Current.Value*self.atr_reversal))): self.dir = True self.low_index = 0 else: if(bar.High>((self.getLow()*(1+self.percent_change))+(self.atr.Current.Value*self.atr_reversal))): self.dir = False self.high_index = 0 IsReady = self.high_window.IsReady and self.low_window.IsReady and self.atr.IsReady if IsReady: if self.low_index>self.high_index: self.Value = 1 elif self.low_index==self.high_index: self.Value = 0 else: self.Value = -1 return IsReady def getHigh(self): high = self.high_window[self.high_index] for i in range(self.high_index,-1,-1): if self.high_window[i]>high: high = self.high_window[i] self.high_index = i return high def getLow(self): low = self.low_window[self.low_index] for i in range(self.low_index,-1,-1): if self.low_window[i]<low: low = self.low_window[i] self.low_index = i return low