EAにマーチンゲール法を取り入れてみた結果(サンプルソース)

記事内に商品プロモーションを含む場合があります
スポンサーリンク

今回は、MT4のEAサンプルソース(FX用)公開、及びマーチンゲール法についてを解説しています。

マーチンゲール法はトレードというより、ギャンブルの手法みたいなところですが、一体どんなトレードになるのか確認していきましょう!

はじめに

ギャンブルの世界では有名なマーチンゲール法ですが、FXでも度々話を聞きます。自分が作ったEAにマーチンゲール法を取り入れたらどうなるのか?という好奇心から自分のEAに導入してみました。

まずはマーチンゲール法とは何か?を確認した後、それをEAにどうやって導入していくかのサンプルソースを公開しています。

マーチンゲール法とは?

マーチンゲール法とは、トレードに連敗した分だけLot数を倍にして次のトレードを行う、いわば倍掛け法とも呼ばています。理論上は絶対に負けない方法です。

まずはマーチンゲール法をわかりやすいよう表にしてみます。トレードの勝率は50%で、利益が出た場合も損失が出た場合も同額という事が前提です。

連敗数123456789
Lot数1248163264128256
連敗する確立1/21/41/81/161/321/641/1281/2561/512

このように、連敗する毎にLot数を倍にするという非常に危険なトレードをする事で、勝ちエントリーが発生すれば負債がチャラになって資金が増えるというトレード方法です。

マーチンゲール法の例

表の通りのLot数でエントリー(1Lotで負けた場合1万円負けと仮定)していき1エントリー目は負けて1万円の負債が発生します。2戦目も負けて2万円の負債(1戦目とあわせて3万円の負債)が発生。3戦目も負けて4万円の負債が発生(1,2戦目とあわせて7万円の負債)し3連敗したとします。

次の4戦目で勝った場合、8万円の利益を得ます。この利益をもって3連敗した分の負債7万円を帳消しにし、さらに利益1万円も得られるといった仕組みです。

勝つまでが1サイクルという考え方で、Lot数を管理しながらエントリーしていく事で何連敗しようがどこかで勝てば最終的に1万円が利益となります。(1戦目で勝っても10戦目で勝っても)
※資金が無限にあり、無限にLot数を増やせるのが前提

確かに理論的に負けない一見夢のあるトレード方法にも見えますね!!とりあえず、 この手法をEAに取り入れてみると果たしてどうなるんでしょうか。

私が作ったボリンジャーバンドEAがちょうど勝率50%で利益・損失も似たような感じなので、今回のテストにはピッタリなのでそれを使います。

早速マーチンゲール法を入れてバックテストしてみた結果がこちら。

スポンサーリンク

EAレポート結果

最後にもの凄い損失が出ている箇所は、12連敗しています。Lot数の制限が最大10(100万通貨)だったので次の勝ちトレードで負けを取り返す事ができていません。ただ、それまでは負けながらも順調な右肩上がりのグラフになりました。

ちなみに、マーチンゲール法を行わなかった場合のグラフが以下です。

こちらは0.01Lotではなく1Lot固定での取引なので、利益は大きめになっています。

マーチンゲール法を入れるとここまで変わるんですね。全く同じロジックのEAとは思えない結果です。

ダウンロード

上記のEAファイルになります。

“マーチンゲールEA” をダウンロード 16_Martingale.ex4 – 3673 回のダウンロード – 7.93 KB

ソースコード

以下サンプルソースコードになります。

//+------------------------------------------------------------------+
//|                                                    BB_Sample.mq4 |
//|                                    Copyright 2020, mef Software. |
//|                                             https://fx-prog.com/ |
//+------------------------------------------------------------------+
#property copyright "Copyright 2020, mef Software."
#property link      "https://fx-prog.com/"
#property version   "1.00"
#property strict
double waitBB,maisuu=0.01;
datetime prevtime;
       
       
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int init()
  {
//---
           
//---
   return(INIT_SUCCEEDED);
  }
        
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
int start()
{
int orderPtn=0; //0:何もしない 1:買い 2:売り
int total=0;
        
int errorcode;               // エラーコード
int ea_ticket_No,ea_order_entry_Type=0,ea_order_MagicNo;  // チケットNo,エントリタイプ,マジックNo.
double ea_order_stop_price=0,ea_order_good_price=0,ea_order_entry_price=0; //ストップロスレート,利確レート,エントリーレート
        
//---
        
        
        
   //ボリンジャーバンドの値を取得
   double BB3UP = iBands(NULL,0,20,3,0,PRICE_CLOSE,MODE_UPPER,0); //3σの上側
   double BB3LO = iBands(NULL,0,20,3,0,PRICE_CLOSE,MODE_LOWER,0); //3σの下側
        
   double BB2UP = iBands(NULL,0,20,2,0,PRICE_CLOSE,MODE_UPPER,0); //2σの上側
   double BB2LO = iBands(NULL,0,20,2,0,PRICE_CLOSE,MODE_LOWER,0); //2σの下側
        
        
//***売買判断箇所***//
        
   //Askがボリンジャーバンドの上3σタッチで買いサイン
   if(BB3UP < Ask) 
   {
      orderPtn=1;
   }
   //Bidがボリンジャーバンドの下3σタッチで売りサイン
   else if(BB3LO > Bid)
   {
      orderPtn=2;
   }
   //それ以外は何もしない
   else
   {
      orderPtn=0;
   }
           
           
   //買いの場合 または 買い待ちの場合
   if((orderPtn==1) || waitBB>0 )
   {
      //2σ内で買いエントリー
      if((BB2UP > Ask && BB2LO < Bid ))
      {
         orderPtn=1;
         waitBB=0;
      }else{
         orderPtn=0;
         waitBB=1;  
      }
   }
   //売りの場合 または 売り待ちの場合
   if((orderPtn==2) || waitBB<0 )
   {
      //2σ内で売りエントリー   
      if((BB2LO < Bid && BB2UP > Ask ))
      {
         orderPtn=2;
         waitBB=0;
      }else{
         orderPtn=0;
         waitBB=-1;  
      }
   }   
//***売買判断箇所***//
        
   total=OrdersTotal();
           
   if(total == 1){
      //既に建玉を保有していたら何もしない
      waitBB=0; 
   }
        
//***エントリー箇所***//
   else if(total == 0 && orderPtn > 0)
   {
          
      //★★★★★マーチンゲール法★★★★★
      if(OrderSelect(OrdersHistoryTotal()-1,SELECT_BY_POS,MODE_HISTORY) == true)
      {
         //前回マイナスだった場合はLot数を倍
         if(OrderProfit() < 0){
            maisuu =  maisuu * 2;
         //前回イーブンだった場合はLot数を保留            
         }else if(OrderProfit() == 0){
            maisuu =  maisuu;
         //前回プラスだった場合はLot数を戻す
         }else{
            maisuu =  0.01;
         }
             
         //枚数が最大の10を超えた場合、取引できなくなるので10にする
         if(maisuu>10){
               maisuu=10;
         }
      }
      //★★★★★マーチンゲール法★★★★★
   
          
      if(orderPtn == 1)
      {
         ea_order_entry_price = Ask;               // 現在の買値でエントリー
         ea_order_entry_Type = OP_BUY;             //OP_BUY
         ea_order_stop_price = Ask - 220 * Point;  //損切りポイント(-22銭)
         ea_order_good_price = Ask + 220 * Point;  //利喰いポイント(+22銭)  
      }
      else if(orderPtn == 2)
      {
         ea_order_entry_price = Bid;               // 現在の売値でエントリー
         ea_order_entry_Type = OP_SELL;            //OP_SELL      
         ea_order_stop_price = Bid + 220 * Point;  //損切りポイント(-22銭)
         ea_order_good_price = Bid - 220 * Point;  //利喰いポイント(+22銭)  
      }
              
      ea_order_MagicNo=0000;  //マジックナンバーは0000固定とする
        
      ea_ticket_No = OrderSend(   // 新規エントリー注文
            NULL,                     // 通貨ペア
            ea_order_entry_Type,      // オーダータイプ[OP_BUY / OP_SELL]
            maisuu,                   // ロット(0.01単位,FXTFは1=10Lot)
            ea_order_entry_price,     // オーダープライスレート
            20,                       // スリップ上限
            ea_order_stop_price,      // ストップレート
            ea_order_good_price,      // リミットレート
            "テストオーダー",             // オーダーコメント
            ea_order_MagicNo,         // マジックナンバー(識別用)
            0,                        // オーダーリミット時間
            clrRed                    // オーダーアイコンカラー
          );
                
      if ( ea_ticket_No == -1)           // オーダーエラー
      {
         errorcode = GetLastError();      // エラーコード取得
         if( errorcode != ERR_NO_ERROR)   // エラー発生
         {
             printf("エラー");
         }
      }
      else {    // 注文約定
         Print("新規注文約定。 チケットNo=",ea_ticket_No);
      }
   }
        
        
   return(0);
}
//***エントリー箇所***//
        
//+------------------------------------------------------------------+

//★★★★★マーチンゲール法★★★★★のとろこが当該処理になります。

変数のmaisuuを用意し、Lot数を制御する処理を入れて、OrderSend()関数でそのmaisuuでエントリーするようにしています。

スポンサーリンク

主な構文

マーチンゲール法は、前述した通り特に難しい手法ではなく前回の勝敗によってLot数を増減するだけなので、まずはOrderSelect(OrdersHistoryTotal()-1,・・・)を使って、一つ前の取引結果を確認します。

そして、前回トレードが負けているようならLot数を倍に増やし、逆に勝っているようならLot数を最初の値(0.01)に戻します。

あと、私が使っているMT4のブローカーは10Lot以上はエントリーできないので、もしLot数を倍にした際に10Lotを超えてしまうようなら10Lotでエントリーします。

おまけ(ココモ法)

マーチンゲール法ではマイナスに終わってしまったので、似た形式のココモ法を使って確認してみました。

マーチンゲール法は前回から倍に掛け算していましたが、ココモ法は前々回のLot数+前回のLot数という形で足し算ですので、マーチンゲール法よりマイルドな結果になります。

ココモ法の表

連敗数123456789
Lot数1235813213455
連敗する確立1/21/41/81/161/321/641/1281/2561/512

ココモ法のEAレポート結果

12連敗するため、1回目のLot数を0.05で確認しました。

少しプラスになりましたが、まだ微妙な感じですね。やはり、連敗数を減らさないといけない感じです。

おまけ(調整)

マーチンゲール法でも、ココモ法でも微妙な結果だったので少しロジックを調整しました。

調整内容は6連敗以上したら、逆方向にエントリーしてみるといった何とも大胆な調整です。
完全にカーブフィッティングの典型例ですね!

さいごに

マーチンゲール法を利用すれば、右肩上がりのバックテスト結果が作れてしまいます。

意図的に右肩上がりのグラフを作ることができてしまう
※EAの良い悪いの判断が難しくなる

もしもEA購入を検討されている場合、綺麗な右肩上がりになっているグラフはマーチンゲール法を使っている可能性もあるため確認が必要ですね。不測の連敗をしてしまった場合、損失が大変なことになります。

私がおまけ(調整)でやっているように大連敗した部分のトレード内容を修正し、大連敗しないようにすればプラス収支に終わらせることも可能です。ほぼ根拠無しのトレードですが右肩上がりの結果を作っています。

こういった修正はカーブフィッティングに繋がります。



※ カーブフィッティングについてはこちら


※ EAのサンプルソースを一覧表にまとめました

※オンラインレッスンやってます


コメント

  1. すーや より:

    はじめましてすーやと申します。

    私は現在、EAつくーるweb版を利用しています。いろいろと試行錯誤していますが、ひとつ思うように出来ない部分があり、プログラミングについて探している中、りょうさんのブログへと辿り着きました。

    そこで、一つお聞きしたいのですが、マーチンゲール法を使用した際に、りょうさんのように掛け金と利確/損切り幅を連動させるにはどうしたらよいでしょうか。

    例えば利確30pips損切り10pipsに設定していたとします。1Lotで始めた場合、利確30pips損切り10pips(利益30pips損10pips)になるかと思います。ここで負けて、次はマーチンゲール法により2Lotでエントリーします。この時、利確30pips損切り10pips(利益60pips損20pips)にしたいのですが、やり方わかりません。
    EAつくーるの場合ですと2Lotの場合、利確15pips損切り5pips(利益30pips損10pips)となってしまいます。
    収益でのpips数ではなく、価格幅で30pipsと10pipsにしたいのですが、どうしたらよいでしょうか。

    文章がわかりにくい上、ぶしつけな質問申し訳ございません。

    • りょう りょう より:

      はじめまして、すーやさん。

      すみません、現在EAつくーるは解約してしまったので詳しい事はわからないのですがやりたい内容は理解できました!
      上記の内容でゴゴジャンラボに投稿すればゴゴジャンから回答が返ってくる内容だと思いますよ。
      https://labo.gogojungle.co.jp/category/1/31

      • すーや より:

        りょうさん即レス感謝いたします。
        書き忘れていましたが、ゴゴジャンのQ&Aでは現在EAつくーるではその機能がないとのことでした。なので、一部自身でプログラミングを書き換えようと思って探していたところりょうさんのブログを見つけました。

        りょうさんの設定条件を見ると自分がやりたかった掛け数に応じての利確/損切り幅の連動がされているようでしたので質問しました。

        • りょう りょう より:

          なるほど、できないんですね。

          EAつくーるのマーチンゲールのソースコードで、利確15pips損切り5pipsとしている所を無理やり書き換えるのが手っ取り早いと思います。

          が、私のソースコードとEAつくーるのソースコードでは結構違う作りなので探して書き換えるのは難しいかもしれません。

          マーチンゲール機能をOFFにした時のソースコードとONにした時のソースコードを比較して調査する感じでしょうか。

          • すーや より:

            レポート結果の詳細を見ると、そもそもマーチンゲールが機能していませんでした。また別の問題が発覚しました(汗

            Q&Aでは同じ現象が起きている人がいて、早急になんとかしてほしいものです。

            わざわざ返信ありがとうございました。