GitHub で見る
Ronz Auto SLTP 戦略
概要
Ronz Auto SLTP 戦略 は、MetaTrader 5 ユーティリティ Ronz Auto SLTP の直接 C# ポートです。これは、保護的なストップロスとテイクプロフィットレベルを自動的に設定し、利益ロックを適用し、すべてのオープンポジションに対してトレーリングルールをアクティブにするトレードマネージャーとして機能します。変換は高レベルの StockSharp API に依存しており、アカウント全体の監視と単一シンボルのデプロイメントの両方をサポートします。
主な機能:
UseServerStops フラグに応じて、サーバー側または仮想 (クライアント側) 保護を適用します。
- MetaTrader スタイルのピップ測定を使用して、最初のストップロスとテイクプロフィットの距離を設定します。
- 取引が設定可能なしきい値に達した後、固定額の利益を固定します。
- 元のアドバイザーを反映した 3 つのトレーリング ストップ バリエーション (クラシック、ステップ距離、ステップバイステップ) を実行します。
- 接続されたポートフォリオ内のすべての証券を監視するか、管理を戦略証券のみに制限します。
- 仮想ストップまたはテイクプロフィットがポジションを決済するたびに、オプションのログ通知を発行します。
パラメーター
| パラメータ |
デフォルト |
説明 |
ManageAllSecurities |
true |
ポートフォリオ内のすべてのオープンポジションを監視します。戦略セキュリティのみを管理するには無効にします。 |
TakeProfitPips |
550 |
MetaTrader ピップ単位の距離が利食いターゲットのエントリー価格に追加されます (ブローカーの最小停止距離を含む)。 |
StopLossPips |
350 |
ストップロスレベルのエントリー価格から差し引かれた距離(ブローカーの最小ストップ距離を含む)(MetaTrader ピップ)。 |
UseServerStops |
true |
有効にすると、ストップ注文と指値注文をブローカーに送信します。無効にすると、しきい値に達すると仮想的にポジションを閉じます。 |
EnableLockProfit |
true |
しきい値に達した後にストップをエントリー価格の上下に移動するプロフィットロックロジックを有効にします。 |
LockProfitAfterPips |
100 |
ロック ロジックがアクティブになる前に達成する必要がある利益 (ピップ単位)。ゼロに設定すると、ロック ステージをスキップしてすぐに追跡します。 |
ProfitLockPips |
60 |
ロックがかかると利益は確保されます。ストップはエントリー価格にこの距離をプラス/マイナスした値に移動します。 |
TrailingStopMode |
Classic |
ロックしきい値の後に使用されるトレーリング アルゴリズム。オプション: None、Classic、StepDistance、StepByStep。 |
TrailingStopPips |
50 |
ピップ単位のトレーリング距離。クラシック モードとステップベースのトレーリング モードの両方のメイン バッファとして機能します。 |
TrailingStepPips |
10 |
ステップベースのトレーリング モードで使用される増分。従来の末尾のバリアントでは無視されます。 |
EnableAlerts |
false |
true の場合、仮想ストップまたはテイクプロフィットが注文を閉じるたびにログ メッセージを書き込みます。 |
動作の詳細
初期保護
- 新しいポジションが検出されると、ストラテジーはエントリー価格を基準にしてストップロスとテイクプロフィットのターゲットを計算します。
- ブローカー定義の最小停止距離は、レベル 1 更新から停止/フリーズ レベル フィールドを読み取り、必要に応じて要求された距離を拡張することによって尊重されます。
利益のロック
- 現在の利益が
LockProfitAfterPips を超えると、ストップが引き上げられ (ショートの場合は引き下げられ)、ProfitLockPips 相当の利益が固定されます。
- ロックが無効になっている場合、ストラテジーはこのステージをスキップし、後続の条件を待ちます。
トレーリングストップ
Classic: 現在の価格まで一定の距離 (TrailingStopPips) を保ちます。
StepDistance: 価格が十分に有利に推移すると、距離を TrailingStepPips だけ短縮します。これは、MetaTrader の「ステップキープディスタンス」の実装とほぼ一致します。
StepByStep: 価格が設定されたトレーリング距離だけ前進すると、ストップを離散的な TrailingStepPips 増分で前進させます。
LockProfitAfterPips がゼロになるとすぐにトレーリングが始まります。それ以外の場合は、利益が LockProfitAfterPips + TrailingStopPips を超えると有効になります。
仮想モード
UseServerStops が false の場合、ストラテジーはストップ注文/指値注文を登録しません。代わりに、計算されたストップロスまたはテイクプロフィットを突破するとすぐに、成行注文を通じてオープンポジションをクローズします。
- アラートを有効にして、これらの仮想クロージャをログに記録できます。
マルチセキュリティのサポート
ManageAllSecurities = true を使用すると、戦略は、選択したポートフォリオにオープン ポジションを持つすべての証券のレベル 1 データをサブスクライブします。
- 各証券は独自のストップ、テイクプロフィット、トレーリング状態を維持するため、ロングとショートの取引は独立して監視されます。
使用のヒント
- 戦略をポートフォリオに添付し、監視が必要な金融商品が 1 つだけの場合は、オプションでデフォルトの証券を割り当てます。
- pip 計算の正確性を維持するために、レベル 1 データ (最良の買値/売値) がすべての管理シンボルで利用可能であることを確認します。
- ブローカーのストップレベル制限を確認します。この戦略ではすでに要求された距離が拡張されていますが、非常に狭い構成は依然として取引会場によって拒否される可能性があります。
- 仮想モードは、保護注文をサポートしていないブローカーやバックテスト シナリオ中に役立ちます。
オリジナルエキスパートとの違い
- StockSharp は証券ごとにポジションを集計し、MetaTrader ヘッジ モードは個々のチケットを追跡します。したがって、ポートは機器ごとにネットポジションを管理します。
- MQ5 スクリプトのテスト注文機能 (テスターでダミー取引を開く) は意図的に省略されました。
- アラートは、画面上のポップアップではなく、StockSharp ログ サブシステムを通じて配信されます。
namespace StockSharp.Samples.Strategies;
using System;
using Ecng.Common;
using StockSharp.Algo.Indicators;
using StockSharp.Algo.Strategies;
using StockSharp.Messages;
/// <summary>
/// Ronz Auto SLTP strategy: SMA crossover with ATR-based risk management.
/// Buys when fast SMA crosses above slow SMA, sells on cross below.
/// </summary>
public class RonzAutoSltpStrategy : Strategy
{
private readonly StrategyParam<DataType> _candleType;
private readonly StrategyParam<int> _fastPeriod;
private readonly StrategyParam<int> _slowPeriod;
private decimal _prevFast;
private decimal _prevSlow;
private bool _hasPrev;
public DataType CandleType { get => _candleType.Value; set => _candleType.Value = value; }
public int FastPeriod { get => _fastPeriod.Value; set => _fastPeriod.Value = value; }
public int SlowPeriod { get => _slowPeriod.Value; set => _slowPeriod.Value = value; }
public RonzAutoSltpStrategy()
{
_candleType = Param(nameof(CandleType), TimeSpan.FromMinutes(60).TimeFrame())
.SetDisplay("Candle Type", "Candle timeframe", "General");
_fastPeriod = Param(nameof(FastPeriod), 10)
.SetGreaterThanZero()
.SetDisplay("Fast SMA", "Fast SMA period", "Indicators");
_slowPeriod = Param(nameof(SlowPeriod), 30)
.SetGreaterThanZero()
.SetDisplay("Slow SMA", "Slow SMA period", "Indicators");
}
/// <inheritdoc />
protected override void OnReseted()
{
base.OnReseted();
_prevFast = 0;
_prevSlow = 0;
_hasPrev = false;
}
/// <inheritdoc />
protected override void OnStarted2(DateTime time)
{
base.OnStarted2(time);
_prevFast = 0;
_prevSlow = 0;
_hasPrev = false;
var fast = new ExponentialMovingAverage { Length = FastPeriod };
var slow = new ExponentialMovingAverage { Length = SlowPeriod };
var subscription = SubscribeCandles(CandleType);
subscription.Bind(fast, slow, ProcessCandle).Start();
}
private void ProcessCandle(ICandleMessage candle, decimal fastValue, decimal slowValue)
{
if (candle.State != CandleStates.Finished) return;
if (_hasPrev)
{
if (_prevFast <= _prevSlow && fastValue > slowValue && Position <= 0)
BuyMarket();
else if (_prevFast >= _prevSlow && fastValue < slowValue && Position >= 0)
SellMarket();
}
else
{
if (fastValue > slowValue && Position <= 0)
BuyMarket();
else if (fastValue < slowValue && Position >= 0)
SellMarket();
}
_prevFast = fastValue;
_prevSlow = slowValue;
_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 ExponentialMovingAverage
from StockSharp.Algo.Strategies import Strategy
class ronz_auto_sltp_strategy(Strategy):
def __init__(self):
super(ronz_auto_sltp_strategy, self).__init__()
self._candle_type = self.Param("CandleType", DataType.TimeFrame(TimeSpan.FromMinutes(60)))
self._fast_period = self.Param("FastPeriod", 10)
self._slow_period = self.Param("SlowPeriod", 30)
self._prev_fast = 0.0
self._prev_slow = 0.0
self._has_prev = False
@property
def CandleType(self):
return self._candle_type.Value
@CandleType.setter
def CandleType(self, value):
self._candle_type.Value = value
@property
def FastPeriod(self):
return self._fast_period.Value
@FastPeriod.setter
def FastPeriod(self, value):
self._fast_period.Value = value
@property
def SlowPeriod(self):
return self._slow_period.Value
@SlowPeriod.setter
def SlowPeriod(self, value):
self._slow_period.Value = value
def OnReseted(self):
super(ronz_auto_sltp_strategy, self).OnReseted()
self._prev_fast = 0.0
self._prev_slow = 0.0
self._has_prev = False
def OnStarted2(self, time):
super(ronz_auto_sltp_strategy, self).OnStarted2(time)
self._prev_fast = 0.0
self._prev_slow = 0.0
self._has_prev = False
fast = ExponentialMovingAverage()
fast.Length = self.FastPeriod
slow = ExponentialMovingAverage()
slow.Length = self.SlowPeriod
subscription = self.SubscribeCandles(self.CandleType)
subscription.Bind(fast, slow, self._process_candle).Start()
def _process_candle(self, candle, fast_value, slow_value):
if candle.State != CandleStates.Finished:
return
fast_val = float(fast_value)
slow_val = float(slow_value)
if self._has_prev:
if self._prev_fast <= self._prev_slow and fast_val > slow_val and self.Position <= 0:
self.BuyMarket()
elif self._prev_fast >= self._prev_slow and fast_val < slow_val and self.Position >= 0:
self.SellMarket()
else:
if fast_val > slow_val and self.Position <= 0:
self.BuyMarket()
elif fast_val < slow_val and self.Position >= 0:
self.SellMarket()
self._prev_fast = fast_val
self._prev_slow = slow_val
self._has_prev = True
def CreateClone(self):
return ronz_auto_sltp_strategy()