既刊のiAC(Accelerator/Decelerator Oscillator)インジケーターの記事では、
ゼロラインクロスと、2本連続の色変化という2つの判定を解説しました。
この記事ではあえてゼロラインクロスを使わず、
Bill Williamsが考案した「Two in a Row」だけを、
エントリー条件にするEAを作ります。
・「Two in a Row」とゼロラインクロスの判定の違い
・既刊クロス判定EA群(MACD/Force Index/RVI等)との仕組みの違い
・確定済みバーだけで連続性を確認する書き方
・実際に動くEAのコード全体
なぜゼロラインクロスではなく「Two in a Row」を使うのか
まず、2つの判定方法の違いを整理します。
「Two in a Row」とは何か
Two in a Rowは、ACがゼロラインより上にある状態で、
2本連続で値が増えていれば買いシグナル、
ゼロラインより下にある状態で2本連続で値が減っていれば売りシグナルとする、
Bill Williams考案のルールです。
既刊のクロス判定EA群との違い
このサイトには、ライン交差や符号反転を発注条件にするEAが、
既にいくつも存在します。
| EA | 判定方法 | 見ているもの |
|---|---|---|
| 既刊MACD/StochasticクロスEA | 2本のラインの交差 | ラインの位置関係 |
| 既刊Force Index/Momentum/RVIクロスEA | ゼロライン・基準線クロス | 値の符号反転の瞬間 |
| 本記事(iAC Two in a Row EA) | ゼロラインの外側での2本連続同方向変化 | 勢いの変化が続いているかどうか |
本記事は、符号が反転した「瞬間」ではなく、
同じ方向への変化が「続いている」ことを確認する、
既刊群とは別の判定の仕組みに属します。
Two in a Rowを使う設計思想
・ゼロラインクロスは符号が変わった瞬間に反応する
・Two in a Rowはゼロラインを跨いだ後、勢いが続くかを1本待って確認する
・反応はクロスより遅れるが、単発のノイズに反応しにくい
ゼロラインクロスは反応が早い分、
1本だけの変化で反転したように見えても、
すぐ元に戻ってしまう「ノイズ」を拾いやすい設計です。
Two in a Rowは1本多く待つことで、
その変化が続いているかどうかを確認してからエントリーします。
iAC関数のシグネチャ(既刊記事で確認済み)
既刊iac-mt4.mdで確認済みの引数構成を再掲します。
3つの引数の意味
double iAC( string symbol, // 通貨ペア名(NULLで現在のチャート) int timeframe, // 時間足(0で現在の時間足) int shift // 何本前のバーの値を取得するか );
本EAでは、確定済みの直近3本(shift1〜3)を比較に使います。
形成中の最新バー(shift0)は判定に使いません。
2本連続同方向変化の判定ロジック
double ac1 = iAC(_Symbol, 0, 1); double ac2 = iAC(_Symbol, 0, 2); double ac3 = iAC(_Symbol, 0, 3); bool risingTwice = (ac1 > ac2 && ac2 > ac3); bool fallingTwice = (ac1 < ac2 && ac2 < ac3);
直近3本を比較し、2回続けて同じ方向に動いているかを確認します。
ゼロラインより外側にあるかの確認
bool buySignal = (ac1 > 0 && risingTwice); bool sellSignal = (ac1 < 0 && fallingTwice);
risingTwice/fallingTwiceだけでは、
ゼロライン付近での小さな上下動にも反応してしまうため、
ac1がゼロラインの外側にあることも合わせて確認します。
発注条件・損切り・ポジション重複の防止
判定だけでは発注にならないため、安全策を組み込みます。
買い・売りの発注条件
if(buySignal)
{
double sl = Bid - InpStopLossPips * point;
double tp = Ask + InpTakeProfitPips * point;
OrderSend(_Symbol, OP_BUY, InpLots, Ask, 3, sl, tp, "AcTwoInRow", InpMagic, 0, clrBlue);
}
else if(sellSignal)
{
double sl = Ask + InpStopLossPips * point;
double tp = Bid - InpTakeProfitPips * point;
OrderSend(_Symbol, OP_SELL, InpLots, Bid, 3, sl, tp, "AcTwoInRow", InpMagic, 0, clrRed);
}
Two in a Rowが成立した方向に、
そのまま順張りで発注する単純な条件にしています。
損切り・利確を必ず指定する
`sl`(損切り)・`tp`(利確)は発注時点で必ず計算し、
未設定のまま放置しません。
ポジション重複を防ぐチェック
bool HasOpenPosition()
{
for(int i = 0; i < OrdersTotal(); i++)
{
if(OrderSelect(i, SELECT_BY_POS, MODE_TRADES) &&
OrderSymbol() == _Symbol && OrderMagicNumber() == InpMagic)
return(true);
}
return(false);
}
同じマジックナンバー・同じ通貨ペアでポジションが既にあるかを確認し、
あれば新規エントリーをスキップします。
実際に動くコード全体
ここまでの要素をまとめた、EAの全体です。
//+------------------------------------------------------------------+
//| AcTwoInRowEA.mq4 |
//| Copyright 2026, FX-EA System Project Creator |
//| https://creator.fx-ea-system-project.com/ |
//+------------------------------------------------------------------+
#property copyright "Copyright 2026, FX-EA System Project Creator"
#property link "https://creator.fx-ea-system-project.com/"
#property version "1.00"
#property strict
input double InpLots = 0.1; //発注ロット数
input int InpStopLossPips = 300; //損切り(pips)
input int InpTakeProfitPips = 600; //利確(pips)
input int InpMagic = 20261106; //マジックナンバー
datetime lastBarTime = 0;
bool HasOpenPosition()
{
for(int i = 0; i < OrdersTotal(); i++)
{
if(OrderSelect(i, SELECT_BY_POS, MODE_TRADES) &&
OrderSymbol() == _Symbol && OrderMagicNumber() == InpMagic)
return(true);
}
return(false);
}
void OnTick()
{
if(Time[0] == lastBarTime)
return;
lastBarTime = Time[0];
int needed = 45;
if(Bars < needed)
return;
double ac1 = iAC(_Symbol, 0, 1);
double ac2 = iAC(_Symbol, 0, 2);
double ac3 = iAC(_Symbol, 0, 3);
bool risingTwice = (ac1 > ac2 && ac2 > ac3);
bool fallingTwice = (ac1 < ac2 && ac2 < ac3);
bool buySignal = (ac1 > 0 && risingTwice);
bool sellSignal = (ac1 < 0 && fallingTwice);
if(HasOpenPosition())
return;
double point = _Point;
if(_Digits == 3 || _Digits == 5)
point *= 10;
if(buySignal)
{
double sl = Bid - InpStopLossPips * point;
double tp = Ask + InpTakeProfitPips * point;
int ticket = OrderSend(_Symbol, OP_BUY, InpLots, Ask, 3, sl, tp,
"AcTwoInRow", InpMagic, 0, clrBlue);
if(ticket < 0)
Print("買い発注に失敗しました。エラーコード: ", GetLastError());
}
else if(sellSignal)
{
double sl = Ask + InpStopLossPips * point;
double tp = Bid - InpTakeProfitPips * point;
int ticket = OrderSend(_Symbol, OP_SELL, InpLots, Bid, 3, sl, tp,
"AcTwoInRow", InpMagic, 0, clrRed);
if(ticket < 0)
Print("売り発注に失敗しました。エラーコード: ", GetLastError());
}
}
Two in a Rowが成立した瞬間だけ、新規エントリーが発生します。
MetaEditorでのコンパイル・バックテスト手順
実際に動かすまでの手順です。
- MetaEditorで新規Expert Advisor「AcTwoInRowEA」を作成し、上のコードを貼り付ける
- F7キー(またはコンパイルボタン)でコンパイルし、「0 error(s), 0 warning(s)」になることを確認する
- ストラテジーテスターでこのEAを選択し、任意の通貨ペア・期間でバックテストを実行する
- 「結果」タブで、ACが2本連続で同方向に変化した直後にエントリーが発生していることを確認する
- 既刊のiACインジケーターを同時に表示し、エントリーのタイミングがヒストグラムのどの位置にあたるかを目視で確認する
よくあるエラーと注意点
実際に運用する前に、確認しておきたい点です。
needed本数が足りない
・iACは内部でAOの5期間SMAまで遡って計算する
・さらに3本分の比較が必要なため余裕を持った本数にする
・ヒストリーが少ない通貨ペアでは必ず確認する
ゼロラインクロスのEAと混同する
既刊のゼロラインクロス系EA(Force Index/Momentum/RVI)は、
符号が変わった瞬間にエントリーしますが、
本EAは符号が変わった後、2本連続で同方向に変化するまで待ちます。
同じAC系の指標でも、トリガーのタイミングは別です。
コンパイルエラーになる
`&&`の優先順位に注意し、
条件式を括弧で明示的に区切ることをおすすめします。
よくある質問
iACのTwo in a Row EAについて、よく検索される疑問に回答します。
・既刊iACインジケーターを併用すれば、ヒストグラムの推移を目視でも確認できる
・既刊ゼロラインクロス系EAと同時運用する場合は、
マジックナンバーを分けて区別する
・損切り幅(InpStopLossPips)は通貨ペア・時間足に応じて調整する
既刊のゼロラインクロスEA群と何が違いますか?
判定のタイミングが違います。
既刊のForce Index/Momentum/RVIのクロスEAは、
符号が反転した瞬間に反応しますが、
本記事は符号が反転した後、2本連続で同方向に変化するまで待ちます。
本来のBill Williamsのルールと完全に同じですか?
本記事は確定済みのバー(shift1〜3)だけで判定しており、
形成中の最新バーまで含めて判定する運用もあるとされていますが、
本記事ではリペイントを避けるため確定バーのみを使っています。
ゼロラインクロスのEAと併用できますか?
マジックナンバーを分ければ併用できます。
ただし、同じiACを元にした判定のため、
シグナルが近いタイミングで重なることがある点は把握しておいてください。
【MQL4】iACの「2本連続同方向変化(Two in a Row)」をエントリー条件にするEAの作り方(既刊クロス判定EA群とは違う設計):まとめ
この記事では、既刊iACインジケーターのゼロラインクロスではなく、
Bill Williams考案の「Two in a Row」を、
発注条件にするEAを解説しました。
既刊MACD/Stochastic(ライン交差)・既刊Force Index、
Momentum/RVI(ゼロライン・基準線クロス)とは、
判定の仕組みそのものを変え、
「変化が続いているか」を確認する設計で差別化しています。
損切り必須・ポジション重複防止という最低限の安全策を備えた上で、
確定済みバーのみで判定することでリペイントを避ける構成にしています。
コメント