Stochastic Three Periods
The Stochastic Three Periods strategy aligns fast stochastic signals with confirmation from two higher timeframes. Trades are opened when the fast oscillator crosses while both higher timeframes agree.
Details
- Entry Criteria: Fast %K crosses %D with opposite reading
ShiftEntrancebars ago; both higher timeframe stochastics show %K above %D; close price must move in signal direction. - Long/Short: Both.
- Exit Criteria: Opposite fast stochastic cross measured on previous candle.
- Stops: Fixed stop-loss and take-profit in points via
StartProtection. - Default Values:
CandleType1= 5mCandleType2= 15mCandleType3= 30mKPeriod1= 5KPeriod2= 5KPeriod3= 5KExitPeriod= 5ShiftEntrance= 3TakeProfitPoints= 30StopLossPoints= 10
- Filters:
- Category: Oscillator
- Direction: Both
- Indicators: Stochastic
- Stops: Yes
- Complexity: Intermediate
- Timeframe: Intraday
- Seasonality: No
- Neural Networks: No
- Divergence: No
- Risk Level: Medium
using System;
using System.Linq;
using System.Collections.Generic;
using Ecng.Common;
using Ecng.Collections;
using Ecng.Serialization;
using StockSharp.Algo.Indicators;
using StockSharp.Algo.Strategies;
using StockSharp.BusinessEntities;
using StockSharp.Messages;
namespace StockSharp.Samples.Strategies;
/// <summary>
/// Stochastic alignment strategy using fast and slow stochastic oscillators.
/// Enters when both stochastics agree on direction.
/// </summary>
public class StochasticThreePeriodsStrategy : Strategy
{
private readonly StrategyParam<int> _fastPeriod;
private readonly StrategyParam<int> _slowPeriod;
private readonly StrategyParam<DataType> _candleType;
private RelativeStrengthIndex _slowRsi;
private decimal _prevSlow;
private int _lastSignal;
public int FastPeriod { get => _fastPeriod.Value; set => _fastPeriod.Value = value; }
public int SlowPeriod { get => _slowPeriod.Value; set => _slowPeriod.Value = value; }
public DataType CandleType { get => _candleType.Value; set => _candleType.Value = value; }
public StochasticThreePeriodsStrategy()
{
_fastPeriod = Param(nameof(FastPeriod), 5)
.SetGreaterThanZero()
.SetDisplay("Fast K", "Fast stochastic K period", "Parameters");
_slowPeriod = Param(nameof(SlowPeriod), 14)
.SetGreaterThanZero()
.SetDisplay("Slow K", "Slow stochastic K period", "Parameters");
_candleType = Param(nameof(CandleType), TimeSpan.FromHours(1).TimeFrame())
.SetDisplay("Candle Type", "Working timeframe", "General");
}
public override IEnumerable<(Security sec, DataType dt)> GetWorkingSecurities()
{
return [(Security, CandleType)];
}
/// <inheritdoc />
protected override void OnReseted()
{
base.OnReseted();
_prevSlow = 0m;
_lastSignal = 0;
}
protected override void OnStarted2(DateTime time)
{
base.OnStarted2(time);
var fastRsi = new RelativeStrengthIndex { Length = FastPeriod };
_slowRsi = new RelativeStrengthIndex { Length = SlowPeriod };
_prevSlow = 0m;
var subscription = SubscribeCandles(CandleType);
subscription
.Bind(fastRsi, (candle, fastValue) =>
{
if (candle.State != CandleStates.Finished)
return;
var slowResult = _slowRsi.Process(candle.ClosePrice, candle.CloseTime, true);
if (!_slowRsi.IsFormed || slowResult.IsEmpty)
return;
var slowValue = slowResult.ToDecimal();
if (fastValue > slowValue && fastValue > 55m && slowValue > 50m && slowValue > _prevSlow && _lastSignal != 1 && Position <= 0)
{
BuyMarket();
_lastSignal = 1;
}
else if (fastValue < slowValue && fastValue < 45m && slowValue < 50m && slowValue < _prevSlow && _lastSignal != -1 && Position >= 0)
{
SellMarket();
_lastSignal = -1;
}
_prevSlow = slowValue;
})
.Start();
StartProtection(
new Unit(2000m, UnitTypes.Absolute),
new Unit(1000m, UnitTypes.Absolute));
}
}
import clr
clr.AddReference("StockSharp.Messages")
clr.AddReference("StockSharp.BusinessEntities")
clr.AddReference("StockSharp.Algo")
clr.AddReference("StockSharp.Algo.Indicators")
clr.AddReference("StockSharp.Algo.Strategies")
from System import TimeSpan
from StockSharp.Messages import DataType, CandleStates, Unit, UnitTypes
from StockSharp.Algo.Indicators import RelativeStrengthIndex
from StockSharp.Algo.Strategies import Strategy
from indicator_extensions import *
class stochastic_three_periods_strategy(Strategy):
"""Fast/slow RSI alignment with StartProtection."""
def __init__(self):
super(stochastic_three_periods_strategy, self).__init__()
self._fast_period = self.Param("FastPeriod", 5).SetGreaterThanZero().SetDisplay("Fast K", "Fast RSI period", "Parameters")
self._slow_period = self.Param("SlowPeriod", 14).SetGreaterThanZero().SetDisplay("Slow K", "Slow RSI period", "Parameters")
self._candle_type = self.Param("CandleType", DataType.TimeFrame(TimeSpan.FromHours(1))).SetDisplay("Candle Type", "Working timeframe", "General")
@property
def CandleType(self): return self._candle_type.Value
@CandleType.setter
def CandleType(self, value): self._candle_type.Value = value
def OnReseted(self):
super(stochastic_three_periods_strategy, self).OnReseted()
self._prev_slow = 0
self._last_signal = 0
def OnStarted2(self, time):
super(stochastic_three_periods_strategy, self).OnStarted2(time)
self._prev_slow = 0
self._last_signal = 0
self._fast_rsi = RelativeStrengthIndex()
self._fast_rsi.Length = self._fast_period.Value
self._slow_rsi = RelativeStrengthIndex()
self._slow_rsi.Length = self._slow_period.Value
sub = self.SubscribeCandles(self.CandleType)
sub.Bind(self._fast_rsi, self.OnProcess).Start()
area = self.CreateChartArea()
if area is not None:
self.DrawCandles(area, sub)
self.DrawIndicator(area, self._fast_rsi)
self.DrawOwnTrades(area)
self.StartProtection(
Unit(2000, UnitTypes.Absolute),
Unit(1000, UnitTypes.Absolute))
def OnProcess(self, candle, fast_value):
if candle.State != CandleStates.Finished:
return
slow_result = process_float(self._slow_rsi, candle.ClosePrice, candle.OpenTime, True)
if not self._slow_rsi.IsFormed or slow_result.IsEmpty:
return
slow_value = float(slow_result)
fast_value = float(fast_value)
if fast_value > slow_value and fast_value > 55 and slow_value > 50 and slow_value > self._prev_slow and self._last_signal != 1 and self.Position <= 0:
self.BuyMarket()
self._last_signal = 1
elif fast_value < slow_value and fast_value < 45 and slow_value < 50 and slow_value < self._prev_slow and self._last_signal != -1 and self.Position >= 0:
self.SellMarket()
self._last_signal = -1
self._prev_slow = slow_value
def CreateClone(self):
return stochastic_three_periods_strategy()