Overall Statistics |
Total Trades 3 Average Win 0% Average Loss 0% Compounding Annual Return 0.465% Drawdown 19.700% Expectancy 0 Net Profit 0.698% Sharpe Ratio 0.083 Probabilistic Sharpe Ratio 8.848% Loss Rate 0% Win Rate 0% Profit-Loss Ratio 0 Alpha 0.003 Beta 0.769 Annual Standard Deviation 0.145 Annual Variance 0.021 Information Ratio 0.013 Tracking Error 0.063 Treynor Ratio 0.016 Total Fees $4.05 Estimated Strategy Capacity $7600000.00 Lowest Capacity Asset BND TRO5ZARLX6JP Portfolio Turnover 0.18% |
# region imports from AlgorithmImports import * # endregion class DancingApricotCamel(QCAlgorithm): def Initialize(self): self.SetStartDate(2022, 1, 14) # Set Start Date self.SetCash(100000) # Set Strategy Cash self.AddEquity("SPY", Resolution.Minute) self.AddEquity("BND", Resolution.Minute) self.AddEquity("AAPL", Resolution.Minute) def OnData(self, data: Slice): if not self.Portfolio.Invested: self.SetHoldings("SPY", 0.33) self.SetHoldings("BND", 0.33) self.SetHoldings("AAPL", 0.33)
#region imports from AlgorithmImports import * from datetime import timedelta import datetime as dt #endregion def getOIHist(qb, contract_symbol, startDate=datetime(2023, 2, 10), endDate=datetime(2023, 2, 10)): history = qb.History(OpenInterest, contract_symbol, startDate, endDate) if not history.empty: history.index = history.index.droplevel([0, 1, 2]) oi_df = history['openinterest'].droplevel(level=0) oi_df.index = oi_df.index.date return oi_df else: return pd.DataFrame() def GetNearestSymbols(qb, symbol, dDate, up, nearness=8): contract_symbols = qb.OptionChainProvider.GetOptionContractList(symbol, dDate) # Get nearest 20 strikes on both sides of underlying price at start date allStrikes = sorted(set([x.ID.StrikePrice for x in contract_symbols]),key=lambda x: abs(up-x)) nearStrikes = allStrikes[:nearness] nearExpiries = set([x.ID.Date for x in contract_symbols if x.ID.Date.date() <= dDate+dt.timedelta(days=180)]) nearSymbols = [s for s in contract_symbols if s.ID.StrikePrice in nearStrikes and s.ID.Date in nearExpiries] # print(f'Filtered {len(nearSymbols)} near ones out of total {len(contract_symbols)} contracts') return nearSymbols def getGreeksForAll(qb): all_slices = qb.History(timedelta(days=180),Resolution.Daily) df = pd.DataFrame() for slice in all_slices: underlying_price = None underlying_volatility = None # Update the security with QuoteBar information for bar in slice.QuoteBars.Values: qb.Securities[bar.Symbol].SetMarketPrice(bar) # Update the security with TradeBar information for bar in slice.Bars.Values: symbol = bar.Symbol security = qb.Securities[symbol] security.SetMarketPrice(bar) if security.Type == SecurityType.Equity: underlying_volatility = security.VolatilityModel.Volatility underlying_price = security.Price continue # Create the Option contract contract = OptionContract.Create(symbol, symbol.Underlying, bar.EndTime, security, underlying_price) contract.LastPrice = bar.Close # Evaluate the price model to get the IV, Greeks, and theoretical price result = security.PriceModel.Evaluate(security, None, contract) greeks = result.Greeks # Append the data to the DataFrame data = { # "IV" : result.ImpliedVolatility, "Delta": greeks.Delta, "Gamma": greeks.Gamma, # "Vega": greeks.Vega, # "Rho": greeks.Rho, # "Theta": greeks.Theta, # "LastPrice": contract.LastPrice, # "Close": security.Close, # "theoreticalPrice" : result.TheoreticalPrice, "underlyingPrice": underlying_price, # "underlyingVolatility": underlying_volatility } right = "Put" if symbol.ID.OptionRight == 1 else "Call" index = pd.MultiIndex.from_tuples([(symbol.ID.Date, symbol.ID.StrikePrice, right, symbol.Value, bar.EndTime)], names=["expiry", "strike", "type", "symbol", "endTime"]) df = pd.concat([df, pd.DataFrame(data, index=index)]) # df.reset_index(level=[0,1,2]) return df