Eine Strategie mit mehreren Zeitrahmen, die lineare Regressionskanäle für M1-, M5- und H1-Kerzen kombiniert. Die Regressionssteigung des H1-Kanals definiert den vorherrschenden Trend, während die M5- und M1-Kanäle präzise Einstiegspunkte in der Nähe von Unterstützung und Widerstand bieten.
Indikatoren: Jeder Feed wird von einem linearen Regressionskanal konfigurierbarer Länge verarbeitet. Der Kanal bietet eine Mittellinie und symmetrische obere/untere Bänder basierend auf der maximalen Abweichung der letzten Schlusskurse.
Trendfilter: Die Strategie berücksichtigt nur Short-Trades, wenn die Steigung des H1-Kanals negativ ist, und Long-Trades, wenn sie positiv ist.
Eintrag:
Kurzfristig – das jüngste M5-Hoch und M1-Hoch durchdringen beide ihre oberen Kanalbänder, während die H1-Steigung negativ ist.
Long – das jüngste M5-Tief und das M1-Tief erreichen beide ihre unteren Kanalbänder, während die H1-Steigung positiv ist.
Auftragsabwicklung: Eingaben werden mit Marktaufträgen unter Verwendung des konfigurierten Volumens ausgeführt. Stop-Loss- und Take-Profit-Ziele werden aus der Halbwertsbreite bzw. Mittellinie des M5-Kanals abgeleitet.
Ausstieg: Positionen auf den M1-Kerzen werden geschlossen, wenn der Preis den Schutzstopp oder das Mittellinienziel erreicht.
Positionsverwaltung: Es ist immer maximal eine Marktposition offen.
Parameter
Name
Beschreibung
EnableTrading
Ermöglicht der Strategie, Bestellungen aufzugeben, wenn sie aktiviert ist.
BarsToCount
Anzahl der in jedem Regressionskanal verwendeten Balken (Standard: 50).
Volume
Market-Order-Volumen in Lots.
Notizen
Längere Regressionsfenster sorgen für glattere Kanalsteigungen, aber langsamere Reaktionen.
Die Multi-Timeframe-Steigungsanzeige ist nützlich für die Überwachung der Ausrichtung über höhere Intervalle hinweg, auch wenn nur die H1-Steigung Einträge abschließt.
Die Schutzstufen werden jedes Mal neu berechnet, wenn sich eine neue M5-Kerze bildet. Durch häufige Neukalibrierung bleibt das Risiko eng an die aktuelle Kanalgeometrie gekoppelt.
using System;
using StockSharp.Algo.Indicators;
using StockSharp.Algo.Strategies;
using StockSharp.BusinessEntities;
using StockSharp.Messages;
namespace StockSharp.Samples.Strategies;
/// <summary>
/// Linear regression channel strategy.
/// Uses LinearReg as the center line with Highest/Lowest to form a channel.
/// Sells at upper channel, buys at lower channel, with trend filter from regression slope.
/// </summary>
public class MultiTimeFrameRegressionStrategy : Strategy
{
private readonly StrategyParam<DataType> _candleType;
private readonly StrategyParam<int> _regressionLength;
private readonly StrategyParam<int> _channelLength;
private decimal _prevLrValue;
private bool _hasPrev;
public MultiTimeFrameRegressionStrategy()
{
_candleType = Param(nameof(CandleType), TimeSpan.FromMinutes(5).TimeFrame())
.SetDisplay("Candle Type", "Timeframe for analysis.", "General");
_regressionLength = Param(nameof(RegressionLength), 20)
.SetDisplay("Regression Length", "Period for linear regression.", "Indicators");
_channelLength = Param(nameof(ChannelLength), 20)
.SetDisplay("Channel Length", "Period for highest/lowest channel.", "Indicators");
}
public DataType CandleType
{
get => _candleType.Value;
set => _candleType.Value = value;
}
public int RegressionLength
{
get => _regressionLength.Value;
set => _regressionLength.Value = value;
}
public int ChannelLength
{
get => _channelLength.Value;
set => _channelLength.Value = value;
}
/// <inheritdoc />
/// <inheritdoc />
protected override void OnReseted()
{
base.OnReseted();
_prevLrValue = 0;
_hasPrev = false;
}
protected override void OnStarted2(DateTime time)
{
base.OnStarted2(time);
_prevLrValue = 0;
_hasPrev = false;
var lr = new LinearReg { Length = RegressionLength };
var highest = new Highest { Length = ChannelLength };
var lowest = new Lowest { Length = ChannelLength };
var subscription = SubscribeCandles(CandleType);
subscription
.Bind(lr, highest, lowest, ProcessCandle)
.Start();
var area = CreateChartArea();
if (area != null)
{
DrawCandles(area, subscription);
DrawIndicator(area, lr);
DrawOwnTrades(area);
}
}
private void ProcessCandle(ICandleMessage candle, decimal lrValue, decimal highestValue, decimal lowestValue)
{
if (candle.State != CandleStates.Finished)
return;
var close = candle.ClosePrice;
// Determine slope direction from regression
var slope = _hasPrev ? lrValue - _prevLrValue : 0m;
// Channel boundaries
var channelMid = (highestValue + lowestValue) / 2m;
var channelWidth = highestValue - lowestValue;
if (channelWidth <= 0)
{
_prevLrValue = lrValue;
_hasPrev = true;
return;
}
// Upper/lower thresholds
var upperThreshold = channelMid + channelWidth * 0.4m;
var lowerThreshold = channelMid - channelWidth * 0.4m;
// Exit conditions
if (Position > 0 && (close >= upperThreshold || slope < 0))
{
SellMarket();
}
else if (Position < 0 && (close <= lowerThreshold || slope > 0))
{
BuyMarket();
}
// Entry conditions
if (Position == 0)
{
if (close <= lowerThreshold && slope >= 0)
{
// Price near lower channel with flat/rising regression
BuyMarket();
}
else if (close >= upperThreshold && slope <= 0)
{
// Price near upper channel with flat/falling regression
SellMarket();
}
}
_prevLrValue = lrValue;
_hasPrev = true;
}
}
import clr
clr.AddReference("StockSharp.Messages")
clr.AddReference("StockSharp.Algo")
clr.AddReference("StockSharp.Algo.Indicators")
clr.AddReference("StockSharp.Algo.Strategies")
from System import TimeSpan
from StockSharp.Messages import DataType, CandleStates
from StockSharp.Algo.Indicators import LinearReg, Highest, Lowest
from StockSharp.Algo.Strategies import Strategy
class multi_time_frame_regression_strategy(Strategy):
"""
Multi Time Frame Regression: linear regression channel with highest/lowest boundaries.
"""
def __init__(self):
super(multi_time_frame_regression_strategy, self).__init__()
self._regression_length = self.Param("RegressionLength", 20).SetDisplay("Regression", "LinReg period", "Indicators")
self._channel_length = self.Param("ChannelLength", 20).SetDisplay("Channel", "Channel period", "Indicators")
self._candle_type = self.Param("CandleType", DataType.TimeFrame(TimeSpan.FromMinutes(5))).SetDisplay("Candle Type", "Candles", "General")
self._prev_lr = 0.0
self._has_prev = False
@property
def candle_type(self):
return self._candle_type.Value
def OnReseted(self):
super(multi_time_frame_regression_strategy, self).OnReseted()
self._prev_lr = 0.0
self._has_prev = False
def OnStarted2(self, time):
super(multi_time_frame_regression_strategy, self).OnStarted2(time)
lr = LinearReg()
lr.Length = self._regression_length.Value
highest = Highest()
highest.Length = self._channel_length.Value
lowest = Lowest()
lowest.Length = self._channel_length.Value
subscription = self.SubscribeCandles(self.candle_type)
subscription.Bind(lr, highest, lowest, self._process_candle).Start()
area = self.CreateChartArea()
if area is not None:
self.DrawCandles(area, subscription)
self.DrawIndicator(area, lr)
self.DrawOwnTrades(area)
def _process_candle(self, candle, lr_val, high_val, low_val):
if candle.State != CandleStates.Finished:
return
lr = float(lr_val)
h = float(high_val)
l = float(low_val)
close = float(candle.ClosePrice)
slope = lr - self._prev_lr if self._has_prev else 0.0
ch_mid = (h + l) / 2.0
ch_width = h - l
if ch_width <= 0:
self._prev_lr = lr
self._has_prev = True
return
upper = ch_mid + ch_width * 0.4
lower = ch_mid - ch_width * 0.4
if self.Position > 0 and (close >= upper or slope < 0):
self.SellMarket()
elif self.Position < 0 and (close <= lower or slope > 0):
self.BuyMarket()
if self.Position == 0:
if close <= lower and slope >= 0:
self.BuyMarket()
elif close >= upper and slope <= 0:
self.SellMarket()
self._prev_lr = lr
self._has_prev = True
def CreateClone(self):
return multi_time_frame_regression_strategy()