GitHub で見る

BrainTrend2 + AbsolutelyNoLagLWMA MMRec 戦略

概要

この戦略は、MetaTraderエキスパート Exp_BrainTrend2_AbsolutelyNoLagLwma_MMRec を2つの独立したシグナルブロックを組み合わせて再現します:トレンドフォローエンジンBrainTrend2と適応フィルターAbsolutelyNoLagLWMAです。各ブロックは独自の権限に従ってトレードを開くことも閉じることもでき、元のMMRecテンプレートのマネーマネジメントスイッチを模倣しています。注文はStockSharpの高レベルAPIを使用して成行執行と設定可能なデフォルトボリュームで実行されます。

取引ロジック

BrainTrend2ブロック

  • ATRに似た加重トゥルーレンジに基づいた動的トレーリングレベルを構築します。
  • ローソク足がトレーリングバッファーを0.7 * ATR以上突き破ると方向(river)が切り替わります。
  • 上昇リバー内の上昇ローソク足はロングエントリーをトリガーし(有効な場合)、ショートポジションを閉じます。
  • 下落リバー内の下落ローソク足はショートエントリーをトリガーし(有効な場合)、ロングポジションを閉じます。
  • シグナルはBrain Signal Shiftパラメーターによって古いバーで動作するように遅延させることができます。

AbsolutelyNoLagLWMAブロック

  • 選択した価格ソースに2段階の線形加重移動平均を適用します。
  • 2重LWMAが上昇すると色が**上昇(2)に、下落すると下落(0)に、それ以外は中立(1)**になります。
  • 色2への遷移はロングを開き、オプションでショートを閉じます;色0への切り替えはショートを開き、オプションでロングを閉じます。
  • シグナルもユーザー定義の本数分のバーで後ろにシフトできます。

ポジション管理

  • 戦略は単一のネットポジションを運用します。両方のブロックが同じバーでトレードを要求すると、クローズシグナルが新しいエントリーより前に実行されます。
  • ブロックがトレードを開きたいが反対のポジションが開いており対応するクローズ権限が無効な場合、エントリーはスキップされます(単一ネットポートフォリオではヘッジポジションを保持できないことを反映しています)。

パラメーター

グループ 名前 説明
BrainTrend2 Brain Candle BrainTrend2インジケーターに使用するローソク足タイプ。
BrainTrend2 Brain ATR BrainTrend2の内部計算に使用するATR期間。
BrainTrend2 Brain Signal Shift BrainTrend2シグナルを遅延させるバー数。
BrainTrend2 Brain Buy / Sell BrainTrend2がロング/ショートトレードを開くことを許可する。
BrainTrend2 Brain Close Buys / Close Sells BrainTrend2シグナルが既存ポジションを閉じることを許可する。
AbsolutelyNoLag Abs Candle LWMAインジケーターに使用するローソク足タイプ。
AbsolutelyNoLag Abs Length LWMAの期間。
AbsolutelyNoLag Abs Price LWMAに使用する適用価格。MQLのApplied_price_enumに対応します。
AbsolutelyNoLag Abs Signal Shift LWMAシグナルを遅延させるバー数。
AbsolutelyNoLag Abs Buy / Sell LWMAブロックがロング/ショートトレードを開くことを許可する。
AbsolutelyNoLag Abs Close Buys / Close Sells LWMAブロックがポジションを閉じることを許可する。
AbsolutelyNoLag Abs Shift LWMA出力に定数価格オフセットを追加する。
General Order Volume デフォルトの成行注文ボリューム。

注意事項

  • ATRとLWMAの計算はMQLの元の実装に従っており、三角ATR重み付けと広範な適用価格リストが含まれています。
  • スプレッド情報はStockSharpのローソク足では利用できないため、トゥルーレンジはローソク足価格のみを使用します。これはスプレッドがゼロの場合のインジケーターの動作を反映しています。
  • 異なるマジックナンバーを持つ複数の同時ポジションは単一のネットポジションに統合されます。これはStockSharp戦略の標準です。
using System;
using System.Collections.Generic;

using Ecng.Common;

using StockSharp.Algo.Indicators;
using StockSharp.Algo.Strategies;
using StockSharp.BusinessEntities;
using StockSharp.Messages;

namespace StockSharp.Samples.Strategies;

/// <summary>
/// BrainTrend2 AbsolutelyNoLag LWMA MMRec strategy (simplified).
/// Uses RSI + EMA for trend detection with position recovery logic.
/// </summary>
public class BrainTrend2AbsolutelyNoLagLwmaMmrecStrategy : Strategy
{
	private readonly StrategyParam<DataType> _candleType;
	private readonly StrategyParam<int> _rsiLength;
	private readonly StrategyParam<int> _emaLength;

	public DataType CandleType
	{
		get => _candleType.Value;
		set => _candleType.Value = value;
	}

	public int RsiLength
	{
		get => _rsiLength.Value;
		set => _rsiLength.Value = value;
	}

	public int EmaLength
	{
		get => _emaLength.Value;
		set => _emaLength.Value = value;
	}

	public BrainTrend2AbsolutelyNoLagLwmaMmrecStrategy()
	{
		_candleType = Param(nameof(CandleType), TimeSpan.FromHours(1).TimeFrame())
			.SetDisplay("Candle Type", "Candles", "General");

		_rsiLength = Param(nameof(RsiLength), 14)
			.SetGreaterThanZero()
			.SetDisplay("RSI Length", "RSI period", "Indicators");

		_emaLength = Param(nameof(EmaLength), 20)
			.SetGreaterThanZero()
			.SetDisplay("EMA Length", "EMA period", "Indicators");
	}

	protected override void OnStarted2(DateTime time)
	{
		base.OnStarted2(time);

		var rsi = new RelativeStrengthIndex { Length = RsiLength };
		var ema = new ExponentialMovingAverage { Length = EmaLength };

		var subscription = SubscribeCandles(CandleType);
		subscription
			.Bind(rsi, ema, (ICandleMessage candle, decimal rsiVal, decimal emaVal) =>
			{
				if (candle.State != CandleStates.Finished)
					return;

				if (!IsFormedAndOnlineAndAllowTrading())
					return;

				var close = candle.ClosePrice;

				// Bullish: RSI above 55 and close above EMA
				if (rsiVal > 55 && close > emaVal && Position <= 0)
					BuyMarket();
				// Bearish: RSI below 45 and close below EMA
				else if (rsiVal < 45 && close < emaVal && Position >= 0)
					SellMarket();
			})
			.Start();

		var area = CreateChartArea();
		if (area != null)
		{
			DrawCandles(area, subscription);
			DrawIndicator(area, ema);
			DrawOwnTrades(area);
		}
	}
}