Overall Statistics |
Total Trades 1 Average Win 0% Average Loss 0% Compounding Annual Return 15.566% Drawdown 9.600% Expectancy 0 Net Profit 0% Sharpe Ratio 1.257 Loss Rate 0% Win Rate 0% Profit-Loss Ratio 0 Alpha 0.016 Beta 0.984 Annual Standard Deviation 0.12 Annual Variance 0.014 Information Ratio 0.886 Tracking Error 0.016 Treynor Ratio 0.153 Total Fees $2.55 |
namespace QuantConnect { public class MultiTimeFrameRollingWindowIndicatorAlgorithm : QCAlgorithm { private int _period = 30; private Dictionary<int, RollingWindow<IndicatorSuiteState>> _window = new Dictionary<int, RollingWindow<IndicatorSuiteState>>(); public override void Initialize() { SetStartDate(2016, 1, 1); AddEquity("SPY", Resolution.Minute); foreach (var minute in new int[] { 5, 10, 15, 20, 30 }) { // Create Consolidator var consolidator = new TradeBarConsolidator(TimeSpan.FromMinutes(minute)); // Create indicators var suite = new IndicatorSuite(minute.ToString(), 14, 14, 10, 20); // Add new rolling window to the _window dictionary _window.Add(minute, new RollingWindow<IndicatorSuiteState>(_period)); // Register indicators to the consolidator to be updated at its frequency RegisterIndicator("SPY", suite, consolidator); // Updates the rolling window using an anonymous method consolidator.DataConsolidated += (s, bar) => { if (!suite.IsReady) return; // Uses a wrapper to save only the state of the indicator suite _window[bar.Period.Minutes].Add(new IndicatorSuiteState(suite)); }; // Add the consolidator to the subscription manager to get updated with data from security SubscriptionManager.AddConsolidator("SPY", consolidator); } } public override void OnData(Slice data) { if (!Portfolio.HoldStock) SetHoldings("SPY", 1); } // At end of day, plot the indicators for visual sanity check public override void OnEndOfDay() { if (!_window[30].IsReady) return; // Last IndicatorSuite (index 0) of the 30 min consolidator var suite = _window[30][0]; Plot("Indicators", "ADX", suite.ADX.Current); Plot("Indicators", "RSI", suite.RSI.Current); Plot("Indicators", "Fast SMA", suite.FastSMA.Current); Plot("Indicators", "Slow SMA", suite.SlowSMA.Current); } } public class IndicatorSuite : BarIndicator { public AverageDirectionalIndex ADX; public RelativeStrengthIndex RSI; public SimpleMovingAverage FastSMA; public SimpleMovingAverage SlowSMA; public override bool IsReady { get { return ADX.IsReady && RSI.IsReady && FastSMA.IsReady && SlowSMA.IsReady; } } public IndicatorSuite(string name, int adxPeriod, int rsiPeriod, int fastSmaPeriod, int slowSmaPeriod) : base(name) { ADX = new AverageDirectionalIndex("", adxPeriod); RSI = new RelativeStrengthIndex(rsiPeriod); FastSMA = new SimpleMovingAverage(fastSmaPeriod); SlowSMA = new SimpleMovingAverage(slowSmaPeriod); } protected override decimal ComputeNextValue(IBaseDataBar input) { ADX.Update(input); RSI.Update(input.EndTime, input.Value); FastSMA.Update(input.EndTime, input.Value); SlowSMA.Update(input.EndTime, input.Value); return 0; } } public class IndicatorSuiteState { public AverageDirectionalIndexState ADX; public RelativeStrengthIndexState RSI; public SimpleMovingAverageState FastSMA; public SimpleMovingAverageState SlowSMA; public IndicatorSuiteState(IndicatorSuite suite) { ADX = new AverageDirectionalIndexState(suite.ADX); RSI = new RelativeStrengthIndexState(suite.RSI); FastSMA = new SimpleMovingAverageState(suite.FastSMA); SlowSMA = new SimpleMovingAverageState(suite.SlowSMA); } public class AverageDirectionalIndexState { public readonly string Name; public readonly IndicatorDataPoint Current; public readonly IndicatorBase<IndicatorDataPoint> NegativeDirectionalIndex; public readonly IndicatorBase<IndicatorDataPoint> PositiveDirectionalIndex; public AverageDirectionalIndexState(AverageDirectionalIndex adx) { Name = adx.Name; Current = adx.Current; NegativeDirectionalIndex = adx.NegativeDirectionalIndex; PositiveDirectionalIndex = adx.PositiveDirectionalIndex; } public override string ToString() { return Name + ":" + Current; } } public class RelativeStrengthIndexState { public readonly string Name; public readonly IndicatorDataPoint Current; public RelativeStrengthIndexState(RelativeStrengthIndex rsi) { Name = rsi.Name; Current = rsi.Current; } public override string ToString() { return Name + ":" + Current; } } public class SimpleMovingAverageState { public readonly string Name; public readonly IndicatorDataPoint Current; public SimpleMovingAverageState(SimpleMovingAverage sma) { Name = sma.Name; Current = sma.Current; } public override string ToString() { return Name + ":" + Current; } } } }