| Overall Statistics |
|
Total Trades 65 Average Win 26.45% Average Loss -1.80% Compounding Annual Return 171.109% Drawdown 52.800% Expectancy 1.940 Net Profit 133.944% Sharpe Ratio 2.536 Probabilistic Sharpe Ratio 63.225% Loss Rate 81% Win Rate 19% Profit-Loss Ratio 14.68 Alpha 2.498 Beta -1.023 Annual Standard Deviation 0.922 Annual Variance 0.85 Information Ratio 2.02 Tracking Error 1.08 Treynor Ratio -2.286 Total Fees $24183.20 |
# Ray Dalio's portfolio idea with futures with monthly rebalancing.
class FuturePortfolio(QCAlgorithm):
def Initialize(self):
self.SetStartDate(2020,1,1) #Set Start Date - earliest for futures can be (2009,6,1)
#self.SetEndDate(2020,1,1) #Set End Date
self.SetCash(1000000) # $1M used since futures can have large requirements per contract.
self.qqq = self.AddEquity("QQQ", Resolution.Minute).Symbol
self.futureNQ = self.AddFuture(Futures.Indices.NASDAQ100EMini)
self.futureNQ .SetFilter(30, 120) # Get contracts from 30 days to 120 days out
self.futureZB = self.AddFuture(Futures.Financials.Y30TreasuryBond)
self.futureZB .SetFilter(30, 120)
self.futureZN = self.AddFuture(Futures.Financials.Y10TreasuryNote)
self.futureZN .SetFilter(30, 120)
self.futureVX = self.AddFuture(Futures.Indices.VIX)
self.futureVX .SetFilter(30, 120)
self.rebalance = True # Flag to initate trades
self.Schedule.On(self.DateRules.MonthStart("QQQ"), self.TimeRules.AfterMarketOpen("QQQ", 30), self.Rebalance)
self.contract = None
self.SetWarmUp(200)
def OnData(self, data):
if not (data.ContainsKey(self.qqq) and data[self.qqq] is not None and self.rebalance):
return
self.Liquidate() # close all contracts at the start of each month, this way we avoid having to roll as expiration nears.
for contracts in data.FutureChains.Values:
sorted_contracts = sorted(contracts, key=lambda c: c.Expiry, reverse = True)
if len(sorted_contracts) == 0 or \
(self.contract is not None and sorted_contracts[0].Symbol == self.contract.Symbol):
continue
self.contract = sorted_contracts[0]
if self.contract.Symbol.ID.Symbol == Futures.Indices.NASDAQ100EMini:
self.SetHoldings(sorted_contracts[0].Symbol, 0.35)
if self.contract.Symbol.ID.Symbol == Futures.Financials.Y30TreasuryBond:
self.SetHoldings(sorted_contracts[0].Symbol, 0.35)
if self.contract.Symbol.ID.Symbol == Futures.Financials.Y10TreasuryNote:
self.SetHoldings(sorted_contracts[0].Symbol, 0.2)
else:
self.SetHoldings(sorted_contracts[0].Symbol, 0.0) # Use this for /VX
self.rebalance = False # Reset rebalance timer
def Rebalance(self):
self.rebalance = True