| Overall Statistics |
|
Total Orders 107 Average Win 1.12% Average Loss 0% Compounding Annual Return 30.404% Drawdown 11.900% Expectancy 0 Start Equity 2000000 End Equity 2939817.32 Net Profit 46.991% Sharpe Ratio 1.043 Sortino Ratio 1.414 Probabilistic Sharpe Ratio 64.111% Loss Rate 0% Win Rate 100% Profit-Loss Ratio 0 Alpha 0.081 Beta 0.378 Annual Standard Deviation 0.157 Annual Variance 0.025 Information Ratio -0.324 Tracking Error 0.173 Treynor Ratio 0.433 Total Fees $8712.47 Estimated Strategy Capacity $0 Lowest Capacity Asset SLW TA31J6K2Q2CL Portfolio Turnover 1.81% |
# region imports
from AlgorithmImports import *
# endregion
class BuyHoldMoneyMarket(QCAlgorithm):
def Initialize(self):
# Phase 1: Initial buy-and-hold strategy
self.SetStartDate(2022, 12, 12)
self.SetCash(2000000)
self.AddEquity("VUSB", Resolution.Minute)
self.AddEquity("VMFXX", Resolution.Minute)
# Schedule liquidation and transition to the new strategy
self.Schedule.On(self.DateRules.Today, self.TimeRules.AfterMarketOpen("VUSB", 1), self.LiquidateAndTransition)
# Flag to track the strategy phase
self.transitioned = False
# Set the benchmark during initialization
self.SetBenchmark("QQQ")
def OnData(self, data: Slice):
if not self.transitioned:
# Phase 1: Buy and hold logic
if not self.Portfolio.Invested:
self.SetHoldings("VUSB", 1)
self.SetHoldings("VMFXX", 0)
else:
# Phase 2: New trading strategy logic
self.ExecuteNewStrategy(data)
def LiquidateAndTransition(self):
# Liquidate positions in VUSB and VMFXX
self.Liquidate("VUSB")
self.Liquidate("VMFXX")
self.Debug("Liquidated VUSB and VMFXX positions")
# Transition to the new strategy
self.TransitionToNewStrategy()
def TransitionToNewStrategy(self):
# Phase 2: Initialize stocks and indicators for the new strategy
self.Equities = ['WPM', 'GFI', 'AGI', 'HMY', 'EGO', 'AMLP', 'TSLA', 'LMT', 'GD']
self.symbol_objs = {}
# Initialize indicators and rolling windows for each symbol
self.smaLong = {}
self.smaMid = {}
self._atr = {}
self.high50 = {}
self.low50 = {}
for symbol in self.Equities:
symbol_obj = self.AddEquity(symbol, Resolution.Daily).Symbol
self.symbol_objs[symbol] = symbol_obj
self.smaLong[symbol] = SimpleMovingAverage(100)
self.smaMid[symbol] = SimpleMovingAverage(50)
self._atr[symbol] = AverageTrueRange(symbol, 100, MovingAverageType.EXPONENTIAL)
self.high50[symbol] = Maximum(50)
self.low50[symbol] = Minimum(50)
# Schedule daily trades based on the new strategy
self.Schedule.On(self.DateRules.EveryDay(), self.TimeRules.At(12, 17), Action(self.TradeOnMACDSignal))
# Mark that the transition to the new strategy is complete
self.transitioned = True
def ExecuteNewStrategy(self, data: Slice):
for symbol in self.Equities:
if self._atr[symbol].Current.Value != 0:
price = self.Securities[symbol].Close
holdings = self.Portfolio[symbol].Quantity
# Realize profits if UnrealizedProfitPercent > 10%
if self.Portfolio[symbol].UnrealizedProfitPercent > 0.10:
self.Liquidate(symbol)
self.Log(f"Sold {symbol} at {self.Securities[symbol].Price} to realize gains.")
continue
if holdings == 0:
if self.smaMid[symbol].Current.Value > self.smaLong[symbol].Current.Value:
if price >= self.high50[symbol].Current.Value:
self.SetHoldings(self.symbol_objs[symbol], 1 / len(self.Equities))
self.Log("1BUY " + str(symbol) + " @" + str(price))
elif self.smaMid[symbol].Current.Value < self.smaLong[symbol].Current.Value:
if price <= self.low50[symbol].Current.Value:
self.SetHoldings(self.symbol_objs[symbol], 1 / len(self.Equities))
self.Log("2Short " + str(symbol) + " @" + str(price))
elif holdings > 0:
if price <= self.Securities[symbol].Price - 3 * self._atr[symbol].Current.Value:
self.Liquidate(symbol)
self.Log("close long " + str(symbol) + " @" + str(price))
elif holdings < 0:
if price >= self.Securities[symbol].Price + 3 * self._atr[symbol].Current.Value:
self.Liquidate(symbol)
self.Log("close short " + str(symbol) + " @" + str(price))
def TradeOnMACDSignal(self):
self.Debug("TradeOnMACDSignal")
self.ExecuteNewStrategy(None)
def OnData(self, data: Slice):
if self.transitioned:
# Update indicators in OnData after transitioning to the new strategy
for symbol in self.Equities:
history = self.History[TradeBar](symbol, 120, Resolution.Minute)
for bar in history:
self.smaLong[symbol].Update(bar.EndTime, bar.Close)
self.smaMid[symbol].Update(bar.EndTime, bar.Close)
self._atr[symbol].Update(bar)
self.low50[symbol].Update(bar.EndTime, bar.Close)
self.high50[symbol].Update(bar.EndTime, bar.Close)