Overall Statistics |
Total Trades 216 Average Win 0.16% Average Loss -0.14% Compounding Annual Return 5.511% Drawdown 1.400% Expectancy 0.062 Net Profit 0.915% Sharpe Ratio 1.051 Loss Rate 51% Win Rate 49% Profit-Loss Ratio 1.16 Alpha 0.258 Beta -13.549 Annual Standard Deviation 0.041 Annual Variance 0.002 Information Ratio 0.666 Tracking Error 0.041 Treynor Ratio -0.003 Total Fees $466.72 |
from clr import AddReference AddReference("System") AddReference("QuantConnect.Common") AddReference("QuantConnect.Indicators") AddReference("QuantConnect.Algorithm.Framework") from QuantConnect.Data.UniverseSelection import * from QuantConnect.Indicators import ExponentialMovingAverage from Selection.FundamentalUniverseSelectionModel import FundamentalUniverseSelectionModel import decimal as d class UniverseSelectionModel(FundamentalUniverseSelectionModel): def __init__(self, universeCount = 20, universeSettings = None, securityInitializer = None): super().__init__(False, universeSettings, securityInitializer) self.universeCount = universeCount self.averages = {} def SelectCoarse(self, algorithm, coarse): # We are going to use a dictionary to refer the object that will keep the moving averages for cf in coarse: if cf.Symbol not in self.averages: self.averages[cf.Symbol] = SymbolData(cf.Symbol) # Updates the SymbolData object with price and volume avg = self.averages[cf.Symbol] avg.update(cf.EndTime, cf.Price, cf.Volume) # Filter the values of the dict based on criteria # In this case, we only want up-trending securities filtered_values = list(filter(lambda x: x.is_uptrend, self.averages.values())) # Sort the values of the dict: we want those with greater DollarVolume sorted_values = sorted(filtered_values, key = lambda x: x.volume, reverse = True) return [ x.symbol for x in sorted_values[:self.universeCount] ] # class used to improve readability of the coarse selection function class SymbolData: def __init__(self, symbol): self.symbol = symbol self.priceSMA = SimpleMovingAverage(10) self.volSMA = SimpleMovingAverage(20) self.priceWin = RollingWindow[float](5) self.is_uptrend = False def update(self, time, price, volume): self.price = price self.volume = volume self.priceWin.Add(price) self.priceSMA.Update(time, price) self.volSMA.Update(time, volume) if self.priceSMA.IsReady and self.volSMA.IsReady and self.priceWin.IsReady: MAprice = self.priceSMA.Current.Value MAvol = self.volSMA.Current.Value # Here we can add the criteria for our universe # current price > 10-days moving average price # current volume > 10-days moving average volume # current price > yesterday's close # current price > 10-days maximum price self.is_uptrend = price > 20 and price > MAprice and volume > MAvol and price > self.priceWin[1] and price > max(self.priceWin)
from UniverseSelection import UniverseSelectionModel from AlphaModel import ConstantAlphaModel from Portfolio.EqualWeightingPortfolioConstructionModel import EqualWeightingPortfolioConstructionModel from Execution.ImmediateExecutionModel import ImmediateExecutionModel from Risk.NullRiskManagementModel import NullRiskManagementModel class BasicTemplateFrameworkAlgorithm(QCAlgorithmFramework): def Initialize(self): # Set requested data resolution self.UniverseSettings.Resolution = Resolution.Minute self.SetStartDate(2018, 6, 1) # Set Start Date self.SetEndDate(2018, 8, 1) # Set End Date self.SetCash(100000) # Set Strategy Cash self.AddEquity("SPY") self.Schedule.On(self.DateRules.EveryDay("SPY"), self.TimeRules.BeforeMarketClose("SPY", 10), self.rebalance) count = 5 self.SetUniverseSelection(UniverseSelectionModel(universeCount = count)) self.SetAlpha(ConstantAlphaModel()) self.SetPortfolioConstruction(EqualWeightingPortfolioConstructionModel()) self.SetExecution(ImmediateExecutionModel()) self.SetRiskManagement(NullRiskManagementModel()) # def OnOrderEvent(self, orderEvent): # if orderEvent.Status == OrderStatus.Filled: # self.Debug("Purchased Stock: {0}".format(orderEvent.Symbol)) def rebalance(self): self.Liquidate() # def OnEndOfDay(self): # for i in self.Securities.Keys: # self.Liquidate(i)
from clr import AddReference AddReference("QuantConnect.Common") AddReference("QuantConnect.Algorithm") AddReference("QuantConnect.Algorithm.Framework") from QuantConnect import * from QuantConnect.Algorithm import * from QuantConnect.Algorithm.Framework import * from datetime import timedelta from QuantConnect.Algorithm.Framework.Alphas import AlphaModel, Insight, InsightType, InsightDirection class ConstantAlphaModel(AlphaModel): def __init__(self): self.period = timedelta(hours=6) self.securities = [] self.insightsTimeBySymbol = {} self.ShouldEmitInsight = True self.Name = 'ConstantAlphaModel' def Update(self, algorithm, data): insights = [] if self.ShouldEmitInsight: for security in self.securities: if security.Symbol.Value != "SPY": insights.append(Insight.Price(security.Symbol, timedelta(hours=6), InsightDirection.Up)) self.ShouldEmitInsight = False # if self.removedSecurities: # for i in self.removedSecurities: # insights.append(Insight.Price(i.Symbol, timedelta(minutes=10), InsightDirection.Flat)) return insights def OnSecuritiesChanged(self, algorithm, changes): self.removedSecurities = [] for added in changes.AddedSecurities: self.securities.append(added) self.ShouldEmitInsight = True # this will allow the insight to be re-sent when the security re-joins the universe for removed in changes.RemovedSecurities: self.removedSecurities.append(removed) self.ShouldEmitInsight = True if removed in self.securities: self.securities.remove(removed) if removed.Symbol in self.insightsTimeBySymbol: self.insightsTimeBySymbol.pop(removed.Symbol)