https://s3-us-west-2.amazonaws.com/secure.notion-static.com/5fc153b0-66c9-40d4-965b-8a3837aa8f8e/chart3.png

RSIのレベルによる仕掛けシグナルに対して、ATRを使ったフィルタをかけ、シグナルを選別します。

ATRは各バーの値幅の平均をとったものなので、通貨ペアによってその値は異なります。そこで、短期ATRと長期ATRを比較して、短期ATRの方が大きいときにボラティリティが大きく、短期ATRの方が小さいときにボラティリティが小さいと判断します。

ここでの仕掛けはRSIを使った逆張りシグナルなので、大きなトレンドにならないボラティリティが小さい相場で有効であると仮定します。そこで、短期ATRが長期ATRよりも小さいときに仕掛けシグナルを採用するフィルタとします。

ボラティリティの大小でシグナルを採用する「ボラティリティフィルタ」となっています。

仕掛けフィルタ

<aside> 💡 売買シグナルの採用条件:1本前の短期ATRが長期ATRより小さい場合

</aside>

コード

//共通ライブラリ
#include "LibEA.mqh"

sinput double Lots = 0.1; //売買ロット数

//ティック時実行関数
void Tick()
{
   int sig_entry = EntrySignal(); //仕掛けシグナル
   int sig_filter = FilterSignal(sig_entry); //ボラティリティフィルタ
   //成行売買
   MyOrderSendMarket(sig_filter, sig_entry, Lots);
}

input int RSIPeriod = 10; //RSIの期間

//仕掛けシグナル関数
int EntrySignal()
{
   //1本前のRSI
   double RSI1 = iRSI(_Symbol, 0, RSIPeriod, PRICE_CLOSE, 1);

   int ret = 0; //シグナルの初期化

   //買いシグナル
   if(RSI1 < 30) ret = 1;
   //売りシグナル
   if(RSI1 > 70) ret = -1;

   return ret; //シグナルの出力
}

input int FastATRPeriod = 20; //短期ATRの期間
input int SlowATRPeriod = 200; //長期ATRの期間

//フィルタ関数
int FilterSignal(int signal)
{
   //1本前のATR
   double FastATR1 = iATR(_Symbol, 0, FastATRPeriod, 1);
   double SlowATR1 = iATR(_Symbol, 0, SlowATRPeriod, 1);

   int ret = 0; //シグナルの初期化

   //売買シグナルのフィルタ
   if(FastATR1 < SlowATR1) ret = signal;

   return ret; //シグナルの出力
}

説明

ATRは、[iATR()](<https://toyolab-fx.notion.site/iATR-ATR-e386551768a04235b6bb3b790e338fe2>)というテクニカル指標関数で求められます。

短期ATRの期間、長期ATRの期間として、別途宣言したFastATRPeriodSlowATRPeriodをそれぞれ引数periodに代入します。

1本前の短期ATRFastATR1と長期ATRSlowATR1の大小関係よりフィルタの条件を判定します。