はじめに
記事の目的とわかるようになること
- 目的
1 分足スキャルピングに特化した「Rapid Fire」EA を MQL5 で実装し、誰でも再現できる形で公開する。 - わかるようになること
- パラボリックSARと60SMAを合わせた転換+方向フィルタの設計思想
- およそ140行で完結する実装コード(日本語コメント付き)
- ストラテジーテスター最適化とウォークフォワード検証の具体手順
- スプレッド管理やVPS選定など実運用で陥りやすい罠
1 戦略コンセプト

1-1 高速取引(Rapid Fire)とは
平均保有時間が数分〜数十分、利幅は10-15 pips 程度に設定し、勝率×取引回数で総利益を積み上げる超短期戦略である。頻繁な発注を支えるためプログラム化は必須となる。MQL5
1-2 指標の役割分担
インジケーター | 主機能 | 本戦略での担当 |
---|---|---|
パラボリックSAR | ドットがローソク足を跨ぐ瞬間でトレンド転換を検知 | 転換点トリガ |
60期間SMA | 価格を平滑化し大局方向を示す | 方向フィルタ |
SAR の素早さと SMA の信頼性を掛け合わせることで、ダマシを抑えつつ早期シグナルを確保する。MQL5
1-3 売買シグナル要件
- Buy
- SAR ドットが直近安値を下回る(転換)
- 前バーでは SAR が高値上(転換確認)
- 価格が 60SMA より上
- Sell は上記の反対条件
1 バーにつき 1 トレードのみを許容し、オーバートレードを防止する。MQL5
2 EA 実装ガイド(7ブロック構成)
以下のコードは元記事を改変せず、日本語コメントのみを追加。
2-1 メタデータ & インクルード
#property version "1.00"
#include <Trade/Trade.mqh> // 標準トレードライブラリ
CTrade obj_Trade; // 発注クラス
ポイントCTrade
により OrderSend()
を直接書く必要がなくなり、コードが簡潔になる。
2-2 グローバル変数 & input
int handleSMA = INVALID_HANDLE, handleSAR = INVALID_HANDLE; // インジケーターハンドル
double sma_data[], sar_data[];
input int sl_points = 150; // StopLoss
input int tp_points = 100; // TakeProfit
input
はストラテジーテスターで最適化対象にできる。
2-3 OnInit ― ハンドル生成
int OnInit(){
handleSMA = iMA (_Symbol,PERIOD_M1,60,0,MODE_SMA,PRICE_CLOSE);
handleSAR = iSAR(_Symbol,PERIOD_M1,0.02,0.2);
if(handleSMA==INVALID_HANDLE || handleSAR==INVALID_HANDLE)
return(INIT_FAILED);
ArraySetAsSeries(sma_data,true);
ArraySetAsSeries(sar_data,true);
return(INIT_SUCCEEDED);
}
デフォルト係数 0.02/0.2 は記事の推奨値。MQL5
2-4 OnDeinit ― 後片付け
void OnDeinit(const int reason){
IndicatorRelease(handleSMA);
IndicatorRelease(handleSAR);
}
VPS 常駐でもリソースリークを起こさないための定番処理。
2-5 OnTick 前半 ― データ取得
double Ask = NormalizeDouble(SymbolInfoDouble(_Symbol,SYMBOL_ASK),_Digits);
double Bid = NormalizeDouble(SymbolInfoDouble(_Symbol,SYMBOL_BID),_Digits);
if(CopyBuffer(handleSMA,0,0,3,sma_data)<3) return;
if(CopyBuffer(handleSAR,0,0,3,sar_data)<3) return;
取得本数を最小限に抑え、毎ティック負荷を軽量化。
2-6 OnTick 後半 ― シグナル判定 & 発注
double low0 = iLow (_Symbol,PERIOD_M1,0), low1 = iLow (_Symbol,PERIOD_M1,1);
double high0 = iHigh(_Symbol,PERIOD_M1,0), high1 = iHigh(_Symbol,PERIOD_M1,1);
static datetime signalTime = 0;
datetime currTime = iTime(_Symbol,PERIOD_M1,0);
// Buy
if(sar_data[0]<low0 && sar_data[1]>high1 &&
sma_data[0]<Ask && PositionsTotal()==0 && signalTime!=currTime){
obj_Trade.Buy(0.01,_Symbol,Ask,
Ask-sl_points*_Point, Ask+tp_points*_Point);
signalTime = currTime;
}
// Sell
else if(sar_data[0]>high0 && sar_data[1]<low1 &&
sma_data[0]>Bid && PositionsTotal()==0 && signalTime!=currTime){
obj_Trade.Sell(0.01,_Symbol,Bid,
Bid+sl_points*_Point, Bid-tp_points*_Point);
signalTime = currTime;
}
1 バー内重複エントリーを signalTime
で抑制。
3 バックテスト & 最適化
3-1 テスト設定
パラメータ | 推奨値 | 理由 |
---|---|---|
モデリング | 毎ティック | 1 分足戦略ではヒストリカル精度が最重要 |
期間 | 2-3 年 | 高ボラ期・低ボラ期を両方含める |
可視化 | ON | シグナルと約定の挙動を目視確認 |
3-2 SL/TP チューニング
sl_points
と tp_points
を ±20 % 幅でレンジ最適化し、プロフィットファクター > 1.5 & 最大 DD < 10 % をターゲットに選定する。ウォークフォワード検証で過剰最適化を排除。MQL5

デフォルト値はTPSLが広くてスキャルピングに向きませんので最適化して使用してください。
4 実運用での注意点
4-1 取引コスト
平均利幅が小さいため、スプレッド+手数料が利幅の 20 % 以下になる口座を選択する。
4-2 レイテンシ
Ping ≦ 5 ms のブローカー直結 VPS を推奨。数十 ms の遅延でも約定価格がずれ、PF が一気に悪化する。
4-3 資金管理
固定 0.01 lot は学習用。実運用では口座残高×Risk% でロットを自動調整し、連敗時のドローダウンを抑える。
5 完全コード(コピー用)
//+------------------------------------------------------------------+
#property version "1.00"
#include <Trade/Trade.mqh>
CTrade obj_Trade;
int handleSMA = INVALID_HANDLE, handleSAR = INVALID_HANDLE;
double sma_data[], sar_data[];
input int sl_points = 150;
input int tp_points = 100;
int OnInit(){
handleSMA = iMA(_Symbol,PERIOD_M1,60,0,MODE_SMA,PRICE_CLOSE);
handleSAR = iSAR(_Symbol,PERIOD_M1,0.02,0.2);
if(handleSMA==INVALID_HANDLE || handleSAR==INVALID_HANDLE) return(INIT_FAILED);
ArraySetAsSeries(sma_data,true); ArraySetAsSeries(sar_data,true);
return(INIT_SUCCEEDED);
}
void OnDeinit(const int reason){
IndicatorRelease(handleSMA); IndicatorRelease(handleSAR);
}
void OnTick(){
double Ask = NormalizeDouble(SymbolInfoDouble(_Symbol,SYMBOL_ASK),_Digits);
double Bid = NormalizeDouble(SymbolInfoDouble(_Symbol,SYMBOL_BID),_Digits);
if(CopyBuffer(handleSMA,0,0,3,sma_data)<3) return;
if(CopyBuffer(handleSAR,0,0,3,sar_data)<3) return;
double low0=iLow(_Symbol,PERIOD_M1,0), low1=iLow(_Symbol,PERIOD_M1,1);
double high0=iHigh(_Symbol,PERIOD_M1,0), high1=iHigh(_Symbol,PERIOD_M1,1);
static datetime signalTime=0; datetime currTime=iTime(_Symbol,PERIOD_M1,0);
if(sar_data[0]<low0 && sar_data[1]>high1 &&
sma_data[0]<Ask && PositionsTotal()==0 && signalTime!=currTime){
obj_Trade.Buy(0.01,_Symbol,Ask,
Ask-sl_points*_Point, Ask+tp_points*_Point);
signalTime=currTime;
}else if(sar_data[0]>high0 && sar_data[1]<low1 &&
sma_data[0]>Bid && PositionsTotal()==0 && signalTime!=currTime){
obj_Trade.Sell(0.01,_Symbol,Bid,
Bid+sl_points*_Point, Bid-tp_points*_Point);
signalTime=currTime;
}
}
//+------------------------------------------------------------------+
まとめ
- パラボリックSARで 転換点の速さ、60SMAで 方向の確度 を両立。
- 約140行で書ける軽量 EA。
input
によりテスター最適化が容易。 - 実運用では コスト・レイテンシ・リスク管理 の 3 点が成否を決める。
まずはデモ口座で 2 週間のウォークフォワード検証を行い、安定性を確認してからリアル取引へ進めると良い。MQL5
オンラインコミュニティ
こちらのコミュニティで、AIや機械学習をトレードに活かすために日々探求しています。
興味のある方は覗いてみてください。
参考記事
