AM2
Андрей

 
Уровень 35

  Торгую в компаниях:


Группа "Программирование на MQL"

Рейтинг 280



Добавим функцию Мартингейла к советнику.

Возьмем простейший советник торгующий с фиксированными значениями стопов.


//+------------------------------------------------------------------+
//|                                                        WellX.mq4 |
//|                                            Copyright © 2011, AM2 |
//|                                      http://www.forexsystems.biz |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2011, AM2"
#property link      "http://www.forexsystems.biz"

#define MAGIC 20111010

extern double StopLoss   = 400;
extern double TakeProfit = 800;
extern double ADXPeriod  = 14;
extern double BBPeriod   = 20;
extern double BBDev      = 2;
extern int Level         = 30;
extern double Lots       = 1;

bool b=true, s=true;  

//+------------------------------------------------------------------+
int start()
  {
//---- go trading only for first tiks of new bar
   if(Volume[0]>1) return;  
//----   
   int p=0;    
//---- get Indicatorrs 
   double bbh=iBands(NULL,0,BBPeriod,BBDev,0,PRICE_CLOSE,MODE_UPPER,0);
   double bbl=iBands(NULL,0,BBPeriod,BBDev,0,PRICE_CLOSE,MODE_LOWER,0);
   double adx=iADX(NULL,0,ADXPeriod,PRICE_CLOSE,MODE_MAIN,0);
  
//----

   for (int i=0; i<OrdersTotal(); i++)
   {
     if (OrderSelect(i, SELECT_BY_POS)==true)
      {  
         if (OrderSymbol()!=Symbol() || OrderMagicNumber()!=MAGIC) continue;
         if (OrderType()==OP_BUY || OrderType()==OP_SELL) p++;       
      }   
   }  
//---- buy 
   if(adx<Level && Ask<bbl && b && p<1)  
     {
      OrderSend(Symbol(),OP_BUY,Lots,Ask,30,Ask-StopLoss*Point,Ask+TakeProfit*Point,"",MAGIC,0,Blue);
      b=false;
      s=true;  
     }        
//---- sell   
   if(adx<Level && Bid>bbh && s && p<1)  
     {
      OrderSend(Symbol(),OP_SELL,Lots,Bid,30,Bid+StopLoss*Point,Bid-TakeProfit*Point,"",MAGIC,0,Red );
      b=true; 
      s=false;
     }       
//----
   return(0);
  }
//+------------------------------------------------------------------+



Результат оптимизации эксперта с 2000-го года ниже:



Функция Мартингейла может иметь следующий вид:


//+------------------------------------------------------------------+
int LossCount = 0;
double LotsArray[]={0.1,0.2,0.4,0.8,1.6,3.2};

...

double Lots()
 {
   double Lot = Lots;
   int total = OrdersHistoryTotal();
   for (int i = 0; i < total; i++)
    {
      OrderSelect(i, SELECT_BY_POS, MODE_HISTORY);
      if (OrderSymbol() == Symbol() && OrderMagicNumber() == MAGIC)
       {
         if (OrderProfit() > 0)
          {
            Lot=LotsArray[0];
            LossCount = 0;    
          }         
          else
           {
            Lot=LotsArray[LossCount+1];
            LossCount++;
           }
       }
    }
   return(Lot);
}
//+------------------------------------------------------------------+


Остается только собрать все воедино:


//+------------------------------------------------------------------+
//|                                                        WellX.mq4 |
//|                                            Copyright © 2011, AM2 |
//|                                      http://www.forexsystems.biz |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2011, AM2"
#property link      "http://www.forexsystems.biz"

#define MAGIC 20111010

extern double StopLoss   = 400;
extern double TakeProfit = 800;
extern double ADXPeriod  = 14;
extern double BBPeriod   = 20;
extern double BBDev      = 2;
extern int Level         = 30;
extern double Lots       = 0.1;

int LossCount = 0;
double LotsArray[]={0.1,0.2,0.4,0.8,1.6,3.2};
bool b=true, s=true;

//+------------------------------------------------------------------+
int start()
  {
//---- go trading only for first tiks of new bar
   if(Volume[0]>1) return;  
//----   
   int p=0;    
//---- get Indicatorrs 
   double bbh=iBands(NULL,0,BBPeriod,BBDev,0,PRICE_CLOSE,MODE_UPPER,0);
   double bbl=iBands(NULL,0,BBPeriod,BBDev,0,PRICE_CLOSE,MODE_LOWER,0);
   double adx=iADX(NULL,0,ADXPeriod,PRICE_CLOSE,MODE_MAIN,0);
  
//----

   for (int i=0; i<OrdersTotal(); i++)
   {
     if (OrderSelect(i, SELECT_BY_POS)==true)
      {  
         if (OrderSymbol()!=Symbol() || OrderMagicNumber()!=MAGIC) continue;
         if (OrderType()==OP_BUY || OrderType()==OP_SELL) p++;       
      }   
   }  
//---- buy 
   if(adx<Level && Ask<bbl && b && p<1)  
     {
      OrderSend(Symbol(),OP_BUY,Lots(),Ask,30,Ask-StopLoss*Point,Ask+TakeProfit*Point,"",MAGIC,0,Blue);
      b=false;
      s=true;  
     }        
//---- sell   
   if(adx<Level && Bid>bbh && s && p<1)  
     {
      OrderSend(Symbol(),OP_SELL,Lots(),Bid,30,Bid+StopLoss*Point,Bid-TakeProfit*Point,"",MAGIC,0,Red );
      b=true; 
      s=false;
     }       
//----
   return(0);
  }
//+------------------------------------------------------------------+
double Lots()
 {
   double Lot = Lots;
   int total = OrdersHistoryTotal();
   for (int i = 0; i < total; i++)
    {
      OrderSelect(i, SELECT_BY_POS, MODE_HISTORY);
      if (OrderSymbol() == Symbol() && OrderMagicNumber() == MAGIC)
       {
         if (OrderProfit() > 0)
          {
            Lot=LotsArray[0];
            LossCount = 0;    
          }         
          else
           {
            Lot=LotsArray[LossCount+1];
            LossCount++;
           }
       }
    }
   return(Lot);
}
//+------------------------------------------------------------------+


Прибыль эксперта после оптимизации конечно же куда скромнее, но для наглядности вполне подходит.



Результат с того же 2000-го года.

Дерзайте, юные умы!
  • +3
  • Просмотров: 50827
  • 10 октября 2011, 23:06
  • AM2
Понравилcя материал? Не забудьте поставить плюс и поделиться в социальной сети!

Вступите в группу "Программирование на MQL", чтобы следить за обновлениями
ПРИСОЕДИНИТЬСЯ К ГРУППЕ
присоединиться
Следующая запись в группе  
Пишем усреднитель.
10 октября 2011
24 октября 2011

Брокер для ваших роботов, 15 лет на рынке

Комментарии (25)

+
0
Молоток
avatar

  9  amyrgan145 Сообщений: 428 - Амыр

  • 11 октября 2011, 08:30
+
0
А НЕ ТА-КТО ВСЕ ПРОСТО.
avatar

  15  div15 Сообщений: 71 - div15

  • 4 сентября 2012, 20:24
+
0
все работает. только что гонял.
avatar

  35  AM2 Автор Сообщений: 16419 - Андрей

  • 4 сентября 2012, 20:46
+
0
у меня не получается вставить все это в советник выдает ошибку
avatar

  15  div15 Сообщений: 71 - div15

  • 4 сентября 2012, 20:48
+
+1
кидай советник
avatar

  35  AM2 Автор Сообщений: 16419 - Андрей

  • 4 сентября 2012, 20:50
+
0
отправил на почту
avatar

  15  div15 Сообщений: 71 - div15

  • 4 сентября 2012, 21:04
+
0
А мне вот интересно. Можно ли вынести как-н. значения размеров ордеров для массива?
double LotsArray[]={0.1,0.2,0.4,0.8,1.6,3.2};
Т.е. задать типа: LotsArray[] =(a1,a2,a3,.....a4,a5);
все параметры a1,a2,a3,.....a4,a5 вынести во внешнюю переменную.
avatar

  0  hoz Сообщений: 9

  • 9 сентября 2012, 01:37
+
0
все можно, только это вам домашнее задание :) 
avatar

  35  AM2 Автор Сообщений: 16419 - Андрей

  • 9 сентября 2012, 08:15
+
0
Да я уже..*good* 
avatar

  0  hoz Сообщений: 9

  • 9 сентября 2012, 21:12
+
0
Пробовал добавить мартингейл в простой советник, не получилось.Помогите пожалуиста.
avatar

  0  pepell84 Сообщений: 1

  • 24 января 2013, 09:40
+
0
я пока в санатории :) 
avatar

  35  AM2 Автор Сообщений: 16419 - Андрей

  • 27 января 2013, 14:31
+
0
а как добавить в советник функцию LotExponent =2 тоесть умножение лота на 2 при каждой убыточной сделки
avatar

  15  div15 Сообщений: 71 - div15

  • 12 сентября 2014, 20:07
+
0
extern double LotExponent = 2; //множитель для увеличения следующего лота в случае если сделка будет убыточной

//--------------------------------------------------------------------
//------------ФУНКЦИЯ МАРТИНГЕЙЛА-------------------------------------
//--------------------------------------------------------------------
double Lots()//Lots() ЭТО ВСТАВЛЯЕМ ВМЕСТО ЛОТА
{
double lot = Lots;
int total = OrdersHistoryTotal();
for (int i = 0; i < total; i++)
{
OrderSelect(i, SELECT_BY_POS, MODE_HISTORY);
if (OrderSymbol() == Symbol() && OrderMagicNumber() == Magic)
{
if (OrderProfit() > 0)
{
lot = Lots;
}
else
{
lot = lot * LotExponent;
}
}
}
return(lot);
}
avatar

  15  div15 Сообщений: 71 - div15

  • 16 сентября 2014, 21:28
+
0
прикольная тема. извиняюсь может я не по теме но создал советник засунул в него эту функцию. на одной паре работает без проблем. но на мультивалютке глючит. берет на lotsAray {} 0.1,0.2,0.3,0.4,0.5,0.6. первый лот 0.1 второй. 0.2 идет а третий уже вкладывает 0.5 по порядку. Извиняюсь если вопрос глупый но хотелось бы разобраться.
avatar

  2  laban Сообщений: 16

  • 13 сентября 2015, 00:40
+
0
Разместите тему в столе заказов, может быть помогут :) 
avatar

  35  AM2 Автор Сообщений: 16419 - Андрей

  • 13 сентября 2015, 14:05
+
0
Уважаемый AM2!) я не программист и собирал по конструктору. Мой советник на опционе делает ставки, но не может использовать этот код (он там прописан), не пойму как просто удвоить лот при каждой убыточной сделке. Могли бы вы подсказать, что нужно поменять в этом коде «мартингейл» чтоб он отталкивался исключительно от убыточных сделок. Надеюсь на вашу помощь или подсказку! Заранее спасибо! Могу целиком скинуть советник, если необходимо.
// ---

// ---
double newLotsMartingail(int magic = -1)
{
	int time = 0;
	double lastProfit = 0.0;
	double lastLots = 0.0;
	for (int i = OrdersHistoryTotal() - 1; i >= 0; i--)
	{
		if (!OrderSelect(i, SELECT_BY_POS, MODE_HISTORY))
			continue;
		if ((OrderSymbol() == Symbol())
			&& OrderCloseTime() > time
			&& ((OrderMagicNumber() == magic) || (magic == -1)))
		{
			time = OrderCloseTime();
			lastProfit = OrderProfit();
			lastLots = OrderLots();
		}
	}
	/* Если последняя сделка по текущему символу была убыточна, то возвращаем ёё объём, умноженный на два;
	 иначе возвращаем начальный объём (extern int Lots) */
	double resultLots = 0.0;
	if (lastProfit < 0)
		resultLots = lastLots * 2;
	else
		resultLots = _Lots;
	resultLots = MathRound(resultLots / MarketInfo(Symbol(), MODE_LOTSTEP)) * MarketInfo(Symbol(), MODE_LOTSTEP); // приводим к нужному числу знаков
	resultLots = MathMin(resultLots, MarketInfo(Symbol(), MODE_MAXLOT));	
	resultLots = MathMax(resultLots, MarketInfo(Symbol(), MODE_MINLOT));
	if(resultLots > _MaxLots)
		resultLots = _Lots;
	// ---
	return(resultLots);
}

void get_lots()
{
	// MQL4 | присвоение объёма по входному параметру и мартингейлу при закрытии последней сделки в убытке
	OP_LOTS = newLotsMartingail(_MagicNumber);
}
// ---
// ---
avatar

  0  Designer63rus Сообщений: 3

  • 26 ноября 2015, 17:04
+
0
Такая функция устроит?



//+------------------------------------------------------------------+
   double Lot()
     {
      double lot;
      if(OrdersHistoryTotal()==0)
        {
         lot=Lots;
        }
      if(OrderSelect(OrdersHistoryTotal()-1,SELECT_BY_POS,MODE_HISTORY))
        {
         if(OrderProfit()>0)
           {
            lot=Lots;
           }
         if(OrderProfit()<=0)
           {
            lot=OrderLots()*KLot;
           }
        }
      if(lot>MaxLot)lot=MaxLot;
      return(lot);
     }
//+------------------------------------------------------------------+
avatar

  35  AM2 Автор Сообщений: 16419 - Андрей

  • 26 ноября 2015, 17:10
+
0
Тоже не работает в БО на МТ4(…
avatar

  0  OLEG2017 Сообщений: 4

  • 24 декабря 2017, 18:02
+
0
Спасибо за быстрый ответ! Я попробовал вставить и при проверке получил 6 ошибок. Либо я не правильно вставил, либо не подходит. Может наглядней на полном советнике найти причину? вот ссылка на него: yadi.sk/d/9WX7eF9ckmM37
avatar

  0  Designer63rus Сообщений: 3

  • 26 ноября 2015, 22:00
+
+1
Я попробовал вставить и при проверке получил 6 ошибок. Либо я не правильно вставил, либо не подходит.


Просто нужно понимать что делаешь. У функции есть внешние входные переменные.
avatar

  35  AM2 Автор Сообщений: 16419 - Андрей

  • 27 ноября 2015, 01:46
+
0
extern string Name ="== ExpGalaxyGK.v2.2Night ==";
extern string Nastroiki ="== Настройки советника ==";
extern double Lots = 50;
extern string Expiration = «5»;
extern int Slippage = 5;
extern int Magic = 12345;
extern double LotExponent = 2;
extern double MaxLot = 10000;
extern double KLot = 50;

double lot;
double OPEN1;
double CLOSE1;
double LOW1;
double HIGH1;

double OPEN2;
double CLOSE2;
double LOW2;
double HIGH2;

double OPEN3;
double CLOSE3;
double LOW3;
double HIGH3;

//----------------------------------------
Здесь расчет

//----------------------------------------
double Lot()
{
if(OrdersHistoryTotal()==0)
{
lot=Lots;
}
if(OrderSelect(OrdersHistoryTotal()-1,SELECT_BY_POS,MODE_HISTORY))
{
if(OrderProfit()>0)
{
lot=Lots;
}
if(OrderProfit()<=0)
{
lot=OrderLots()*KLot;
}
}
if(lot>MaxLot)lot=MaxLot;
return(lot);
}
//+------------------------------------------------------------------+
avatar

  1  Petrov210217 Сообщений: 1

  • 14 ноября 2016, 21:27
+
0
Уважаемый АМ2 для БО на вфорекс в вашей сове option.mql4 можно ли поставить сетку мартина?
//--- Inputs
extern double Stavka     = 5;           // ставка в валюте
extern string Expiration = "BO exp:60"; // время истечения в секундах
extern int    Magic      = 111;         // магик
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
  {
   Comment("");
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
  {
   Comment("");
  }
//+------------------------------------------------------------------+
//| Check for open order conditions                                  |
//+------------------------------------------------------------------+
void OpenPos()
  {
   int res;
//--- sell 
   if(High[1]<High[2] && High[3]<High[2])
     {
      res=OrderSend(Symbol(),OP_SELL,Stavka,Bid,3,0,0,Expiration,Magic,0,Red);
      return;
     }
//--- buy 

   if(Low[1]>Low[2] && Low[3]>Low[2])
     {
      res=OrderSend(Symbol(),OP_BUY,Stavka,Bid,3,0,0,Expiration,Magic,0,Blue);
      return;
     }
//---
  }
//+------------------------------------------------------------------+
int CountTrades()
  {
   int count=0;
   for(int i=OrdersTotal()-1;i>=0;i--)
     {
      if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
        {
         if(OrderSymbol()==Symbol() && OrderMagicNumber()==Magic)
           {
            if(OrderType()==OP_BUY || OrderType()==OP_SELL)
               count++;
           }
        }
     }
   return(count);
  }
//+------------------------------------------------------------------+
//| OnTick function                                                  |
//+------------------------------------------------------------------+
void OnTick()
  {
   if(CountTrades()<1) OpenPos();
  }
//+------------------------------------------------------------------+
avatar

  9  maksGruv Сообщений: 340

  • 13 апреля 2017, 14:08
+
0
Ау народ, здесь есть кто. Нужна помощь. Достал советника но что то в нем не так. Открывает сделки и если просадка маленькая то берет пррофит, если просадка нормальная то закрывает сделку не дожидаясь плюса с небольшим минусом. И я не пойму как у него мартин работает, с какой просадкой. Я не программист, может кто поможет.
avatar

  0  Alexws Сообщений: 1

  • 27 февраля 2020, 11:12
+
0
на своей странице в блоге напиши и прикрепи советника
avatar

  16  cerber04 Сообщений: 409

  • 28 февраля 2020, 17:29
+
0
Уважаемые, поставил данный код, а открываются только в SELL и очень много, и оставил лишь только сам этот код и не чего больше, а вообще пытаюсь понять как сделать так чтоб было всего не более пяти ордеров и первый BUY и второй в SELL после подряд три (Step) в BUY и последний открывался с лотом в пять раз больше чем первый, и только пятый в пять раз больше чем первый! И второй ордер вообще по другоному индикатору, таким образом два инщикатора, локирование, усреднение, и Мартин? Вот и собираю коды, можно подсказать?
Редактирован: 6 мая 2020, 01:16
avatar

  1  Sel7 Сообщений: 3

  • 6 мая 2020, 01:15

Зарегистрируйтесь или авторизуйтесь, чтобы оставить комментарий