| Overall Statistics |
|
Total Trades 1 Average Win 0% Average Loss 0% Compounding Annual Return 2037255753670440000000000% Drawdown 11.700% Expectancy 0 Net Profit 52.532% Sharpe Ratio 81407470.15 Probabilistic Sharpe Ratio 0% Loss Rate 0% Win Rate 0% Profit-Loss Ratio 0 Alpha 99648490.313 Beta 51.035 Annual Standard Deviation 1.224 Annual Variance 1.498 Information Ratio 82603443.263 Tracking Error 1.206 Treynor Ratio 1952534.258 Total Fees $183.15 |
class BreakOutExample(QCAlgorithm):
def Initialize(self):
self.SetStartDate(2020, 12, 1) # Set Start Date
self.SetEndDate(2020, 12, 3) # Set End Date
self.SetCash(1000000) # Set Strategy Cash
# Subscribe and set our expiry filter for the futures chain
future = self.AddFuture(Futures.Metals.Gold) #(Futures.Indices.SP500EMini)
future.SetFilter(timedelta(0), timedelta(182))
self.symbol_data_by_symbol = {}
def OnData(self, data):
if self.Portfolio.Invested:
return
for chain in data.FutureChains:
contracts = [contract for contract in chain.Value if self.symbol_data_by_symbol[contract.Symbol].IsReady]
if len(contracts) == 0:
continue
# Sort contracts
# Select contract
contract = contracts[0]
symbol = contract.Symbol
price = self.Securities[symbol].Close
symbol_data = self.symbol_data_by_symbol[contract.Symbol]
if price >= symbol_data.max.Current.Value:
self.SetHoldings(symbol, 1)
if price <= symbol_data.min.Current.Value:
self.SetHoldings(symbol,-1)
def OnSecuritiesChanged(self, changes):
for security in changes.AddedSecurities:
symbol = security.Symbol
self.symbol_data_by_symbol[symbol] = SymbolData(symbol, self)
for security in changes.RemovedSecurities:
symbol = security.Symbol
symbol_data = self.symbol_data_by_symbol.pop(symbol, None)
if symbol_data:
symbol_data.dispose()
class SymbolData:
def __init__(self, symbol, algorithm):
self.symbol = symbol
self.algorithm = algorithm
self.min = Minimum(3)
self.max = Maximum(3)
self.consolidator = algorithm.Consolidate(symbol, timedelta(minutes=60), self.OnDataConsolidated)
def OnDataConsolidated(self, bar):
self.algorithm.Log(f"OnDataConsolidated at {bar.EndTime} for {bar.Symbol}")
self.min.Update(bar.EndTime, bar.Low)
self.max.Update(bar.EndTime, bar.High)
def dispose(self):
self.SubscriptionManager.RemoveConsolidator(self.symbol, self.consolidator)
@property
def IsReady(self):
return self.min.IsReady and self.max.IsReady