Обучение языку MQL4 под MetaTrader 4📌

От xbms, 13 апреля, 2013 в Уголок Программиста

#6126
5 минут назад, Just Trader сказал:

к сожалению с этим советник вообще не закрывает((

Ну значит где то я в коде ошибку допустил, я же не проверял в тестере. Добавь принтов, посмотри, где не срабатывает. 

Вот эта конструкция в тестере вполне работает:

datetime time_curr = 0;
bool close_me = false;
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
  {

   if(close_me && TimeCurrent()-time_curr >= 5) {
      close_me = false;
      
      Print("2 "+TimeCurrent());
   }
      
   if (!close_me)
   {
      time_curr = TimeCurrent();
      Print("1 "+TimeCurrent());
      close_me = true;
   } 

}
//+------------------------------------------------------------------+

 

#6127
В 18.12.2020 в 10:56, Rever27 сказал:

Ну значит где то я в коде ошибку допустил, я же не проверял в тестере. Добавь принтов, посмотри, где не срабатывает. 

Вот эта конструкция в тестере вполне работает:

 

Спасибо большое за помощь, вот что я получаю в эксперте.

 

2020.12.22 18:54:41.897    Setka GBPUSD,M5: 1 1608656080

2020.12.22 18:54:56.291    Setka GBPUSD,M5: 2 1608656095

 

 

 

 

#6128
2 часа назад, Just Trader сказал:

Спасибо большое за помощь, вот что я получаю в эксперте

ну тут задержка получилась 15 секунд, наверное, потому что в тестере прогнал ты. Если поставить на реал, то должна быть 5 секунд минимум и может еще пару секунд, пока новый тик не придет.

#6129
13 часов назад, Rever27 сказал:

ну тут задержка получилась 15 секунд, наверное, потому что в тестере прогнал ты. Если поставить на реал, то должна быть 5 секунд минимум и может еще пару секунд, пока новый тик не придет.

я все время на демо аккаунте делаю, поэтому так поздно отвечаю так как жду результатов.

 

в целом такой код получается?

 

  if(close_me && TimeCurrent()-time_curr >= 15) 
  {
      close_me = false;
      Print("2 "+IntegerToString(TimeCurrent()));
      CloseAll();
      SendNotification("Close Metatrader1");
      Sleep(360*60000);
      SendNotification("Close Metatrader2");
      Sleep(60*60000);
   }
   
   
   double op = CalculateProfit();
          
   if (op >= Profit && !close_me)
     {
      time_curr = TimeCurrent();
      Print("1 "+IntegerToString(TimeCurrent()));
      close_me = true;
      }

 

Изменено 23 декабря, 2020 пользователем Just Trader

#6130
8 часов назад, Just Trader сказал:

в целом такой код получается?

В этой версии будет закрытие через 15 секунд.

При том не нужно вводить функцию Sleep, она тут уже не нужна.

#6131
23 часа назад, Rever27 сказал:

В этой версии будет закрытие через 15 секунд.

При том не нужно вводить функцию Sleep, она тут уже не нужна.

для чего я слип делаю после закрытия, чтобы успеть зайти и закрыть терминал и потом на след день снова запустить.

#6132

Доброго времени суток, Господа! Просьба есть следующая... Прошу привести пример кода, рисующего стрелки в заданном месте терминала. Спасибо)

#6133
5 часов назад, Gamakiv сказал:

Прошу привести пример кода, рисующего стрелки в заданном месте терминала.

https://docs.mql4.com/ru/constants/objectconstants/enum_object/obj_arrow

#6134

Люди добрые подскажите, если ограничении на кол-во условии в мгл4? Вот если сделать столько условии могут быть какие то проблемы?

 

  if (CountBuy() + CountSell () == 0 && Bid <maprice && Time_cur > Time_S && Time_cur < Time_E && DayOfWeek() != 5 && totalhistory <1)

 

 

#6135

@Just Trader Ограничений нет. Проблем не будет.

#6136
В 25.12.2020 в 14:07, Rever27 сказал:

Да. Это конечно круто, но через чур заморочено. Все должно быть просто. Чем проще тем лучше. Просто как в кино xD
 

Спойлер

//+------------------------------------------------------------------+
//|                                                      Strelka.mq4 |
//|                                          Copyright 2020, GamaKiv |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2020, GamaKiv"
#property link      "https://www.mql5.com"
#property version   "1.00"
#property strict
//+------------------------------------------------------------------+
//| Script program start function                                    |
//+------------------------------------------------------------------+

#property description "Скрипт рисует значки Buy | Sell в заданом месте графика графика."

void OnStart()
  {
//---
   ObjectCreate("Strelka_Sell",OBJ_LABEL,0,0,0,0,0);
   
   //установить угол привязки
   ObjectSet("Strelka_Sell",OBJPROP_CORNER, CORNER_RIGHT_UPPER);
   
   //установка в определенное место
   ObjectSet("Strelka_Sell",OBJPROP_XDISTANCE,175);
   ObjectSet("Strelka_Sell",OBJPROP_YDISTANCE,17);
 
   // используем значки из шрифта Wingdings - 16 = размер
   ObjectSetText("Strelka_Sell",CharToStr(236),16,"Wingdings",DodgerBlue);

   
  }
//+------------------------------------------------------------------+

 

 

#6137
54 минуты назад, Gamakiv сказал:

Да. Это конечно круто, но через чур заморочено. Все должно быть просто. Чем проще тем лучше. Просто как в кино xD
 

  Скрыть контент

//+------------------------------------------------------------------+
//|                                                      Strelka.mq4 |
//|                                          Copyright 2020, GamaKiv |
//|                                             https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2020, GamaKiv"
#property link      "https://www.mql5.com"
#property version   "1.00"
#property strict
//+------------------------------------------------------------------+
//| Script program start function                                    |
//+------------------------------------------------------------------+

#property description "Скрипт рисует значки Buy | Sell в заданом месте графика графика."

void OnStart()
  {
//---
   ObjectCreate("Strelka_Sell",OBJ_LABEL,0,0,0,0,0);
   
   //установить угол привязки
   ObjectSet("Strelka_Sell",OBJPROP_CORNER, CORNER_RIGHT_UPPER);
   
   //установка в определенное место
   ObjectSet("Strelka_Sell",OBJPROP_XDISTANCE,175);
   ObjectSet("Strelka_Sell",OBJPROP_YDISTANCE,17);
 
   // используем значки из шрифта Wingdings - 16 = размер
   ObjectSetText("Strelka_Sell",CharToStr(236),16,"Wingdings",DodgerBlue);

   
  }
//+------------------------------------------------------------------+

 

 

Если как в кино, то достаточно одной строчки

ObjectCreate(chart_ID,name,OBJ_ARROW,sub_window,time,price)

#6138

в эту функцию как добавить задержку на 10 сек перед тем как все тут исполнится?

 

void CloseAll()
{ 
         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) 
                  {
                   if (!OrderClose(OrderTicket(), OrderLots(), Bid,Slippage))
                   Print("Ne udalos zakrit order na pokupku!");
                   }
                  
                  if (OrderType() == OP_SELL)
                  {
                   if (!OrderClose(OrderTicket(), OrderLots(), Ask,Slippage))
                   Print ("Ne udalost zakrit order na prodaju!");
                   }
            }
            
            }
         }}

 

#6139
4 часа назад, Just Trader сказал:

в эту функцию как добавить задержку на 10 сек перед тем как все тут исполнится?

 


void CloseAll()
{ 
         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) 
                  {
                   if (!OrderClose(OrderTicket(), OrderLots(), Bid,Slippage))
                   Print("Ne udalos zakrit order na pokupku!");
                   }
                  
                  if (OrderType() == OP_SELL)
                  {
                   if (!OrderClose(OrderTicket(), OrderLots(), Ask,Slippage))
                   Print ("Ne udalost zakrit order na prodaju!");
                   }
            }
            
            }
         }}

 

Можно использовать sleep(milliseconds)

А зачем добавлять задержку на 10 секунд?!

#6140
20 часов назад, Rigal сказал:

Можно использовать sleep(milliseconds)

А зачем добавлять задержку на 10 секунд?!

Тогда слип разве не попадет в цикл?

Чтобы не сразу закрывать сделки по достижению профита, а чуток подождать.

#6141
1 час назад, Just Trader сказал:

Тогда слип разве не попадет в цикл?

Чтобы не сразу закрывать сделки по достижению профита, а чуток подождать.

Вам нужно подождать 10 сек перед закрытием ВСЕХ ордеров? Тогда Sleep() перед вызовом функции CloseAll()...
Если нужно подождать 10 сек перед закрытием каждого отдельного ордера, тогда Sleep() внутри цикла...
Но Rigal резонно спросил- нафига все это надо? За таймаут у Вас ордера лехко уйдут в минус..

#6142
1 час назад, usver73 сказал:

Вам нужно подождать 10 сек перед закрытием ВСЕХ ордеров? Тогда Sleep() перед вызовом функции CloseAll()...
Если нужно подождать 10 сек перед закрытием каждого отдельного ордера, тогда Sleep() внутри цикла...
Но Rigal резонно спросил- нафига все это надо? За таймаут у Вас ордера лехко уйдут в минус..

перед закрытием всех ордеров, то есть до вызова функции Клоузолл. Просто я часто видел как цена за пару секунд летела. Если не получается ничего оставлю как есть.

#6143

Здравствуйте. Хочу попросить, сделайте пожалуйста видео урок, как построить трендовую линию по зигзагу на mql4. Спасибо

Изменено 11 января, 2021 пользователем Vsegut

#6144

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

на графике 1 мин и 5 мин. Например для 5 мин графика datetime v = TimeCurrent() +  ( кол-во свечей ) * 5 *60;

советник работает нормально открывает ордера, а если мы задаем параметр для 1 мин графика 

datetime v = TimeCurrent() +  ( кол-во свечей ) * 1 *60;  то советник перестает открывать ордера ,в чем может быть дело ?

#6145
23 минуты назад, Roman 13 сказал:

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

на графике 1 мин и 5 мин

Не должно быть разницы.

Напишите что то типа

if(!OrderSend(.....) Print(GetLastError());

Если ордер не открылся, то будет ошибка в журнале.  От неё и пляшите

#6146

Здравствуйте уважаемые господа программисты!

3 месяца назад начал изучение mql4.

Уже 2 недели не могу найти решение проблемы, пожалуйста помогите с кодом.

Вообщем проблема заключается в следующем, нужно найти ценовые значение фракталов и сохранить их в динамический массив, чтобы размер массива всегда

менялся в зависимости от количества элементов фракталов. И чтобы цены фракталов записывались с нуля. Например mas[0] – 1.21200, mas[1] – 1.21500, mas[2] – 122200 итд.

Сколько не пробовал получается лишь сохранять в массив статический например на 100 элементов, но тогда элементы массива сохраняются не с нуля а просто на тех барах на которых был найден фрактал например mas[9] – 1.20400, mas[12] – 1.23500 итд. И если пробую изменить размер динамического размер то получается out of range.

Вот в одном из тестов сохраняет одну и туже цену с нуля и записывает её в весь массив.

void fSignal()
{
    int cnt = 0;
    int size = 0;
    double mas[];
    double fCounter = 0.0;
    for(int i=0;i<100;i++)
      {
         fCounter = iFractals(_Symbol, _Period, MODE_LOWER, i);
         if (fCounter)
         cnt++;
         size = ArrayResize(mas,cnt-1); 
      
          for(int j=0;j<size;j++)
            {
              if(fCounter != 0.0)
              {
                mas[j] = fCounter;
                Print ("Array ", "\t","[",j,"]", mas[j]);
              }
            }
       } 
          
      Print ("Array New Size ", ArraySize(mas)," ", mas[0], " ", mas[1]);
}

 

 

#6147
2 часа назад, Alexfm2000 сказал:

Вообщем проблема заключается в следующем, нужно найти ценовые значение фракталов и сохранить их в динамический массив, чтобы размер массива всегда

менялся в зависимости от количества элементов фракталов.

Если по шагам, то мне видится разбить задачу на несколько этапов:
1. Предполагаю, что fSignal() вызывается не каждый тик, а 1 раз на каждой свече.
2. Вы хотите записывать сигнал индикатора и Вверх и Вниз в одну кучу или все таки разделять их? Если разделять, то массив mas[] должен быть двумерным, типа mas[Price][Direct]. Тогда нужно вызывать два экземпляра индикатора (MODE_LOWER и 
MODE_UPPER)

3. Массив нужно объявлять ВНЕ функции его заполнения, т.е. на глобальном уровне, иначе он будет обнуляться на каждом вызове функции fSignal().
4. Далее ищем на какой свече (и в каком направлении) был сигнал от индикатора. 
Вы правильно делаете цикл по свечам. Но количество итераций должно быть в пределах разумного (100- явно излишне). Пусть будет 20.
5. Допустим, нашли фрактал на третей свече. Пусть это будет UP сигнал. Записываем цену фрактала и его направление в массив.
Индекс массива, куда пишем, считается примерно:
 
int x = ArraySize(mas);
mas[x+1][0] = fCounter;

где [0]- это направление сигнала.
Тогда на следующей свече нам нужно исключить чтение значения на этой свече (она уже будет четвертой).
Мне видится два варианта:
5.1. Если найден сигнал, то запоминать время свечи, на которой он был найден. Переменная для хранения времени объявляется вне функции на глобальном уровне;
5.2. Ввести счетчик (типа Вашего cnt), в котором считать номер свеч во время поиска сигнальных свеч. Но, ИМХО, это сложнее, т.к. нужно его периодически обнулять и вообще...
6. Если сигнал получен и записан в массив, то прерываем цикл по свечам и выходим из функции.

Попробуйте самостоятельно закодить...

#6148
2 часа назад, usver73 сказал:

Если по шагам, то мне видится разбить задачу на несколько этапов:
 

Спасибо большое за обширный ответ!  

Вы уже пошли намного дальше придумав возможные варианты функции которую я всё ещё пытаюсь доделать.

1. добавил функцию IsNewCandle() вызов функции происходит из функции OnTick().

2. Изначально просто для реализации функции поиска фракталов и сохранения планировал сохранять верхние (MODE_UPPER) и нижние (MODE_LOWER) по отдельности. С двухмерным массивом никогда не пробовал работать, но так как вы подали такую идею вот попробовал реализовать.

3. массив mas[][2]; объявил на глобальном уровне.

4. поиск фракталов по заданному направлению в цикле for. Количество свечей изменил на 20.

5. запись найденного фрактала в массив mas[x+1][0], но вот при вызове массива элементов массиве не видно.

5.1 пока что не пробовал реализовать, я так понимаю нужно создать динамический массив datetime time[] а вот как туда далее сохранить даты пока что не знаю...

5.2 по поводу счетчика другого варианта подсчёта пока что не знаю.

6. прерываем цикл else if (fCounter == 0.0) return;

 

void fSignal(int dir=2)
{
    int cnt = 0;
    int x = ArraySize(mas);
    int res = 0;
    
    if (dir == EMPTY_VALUE) dir = 2; //direction 1. MODE_UPPER / 2. MODE_LOWER
    
    
    double fCounter = 0.0;
    
   
    
    for(int i=0;i<20;i++)
      {
         fCounter = iFractals(_Symbol, _Period,(dir==1)?MODE_UPPER:(dir==2)?MODE_LOWER:2, i);
         if (fCounter)
         cnt++;
         res = ArrayResize(mas,cnt-1);
         //ArrayResize(time,cnt-1); новый размер массива time
        
          for(int j=0;j<x;j++)
            {
              if(fCounter != 0.0)
              {
                mas[x+1][(dir==1)?0:1] = fCounter;
                //time[x]=fCounter; как сохранять время? 
                Print ("Array ", "\t","[",j,"]", mas[j][1]);
                Print ("Array ", "\t","[",j,"]", mas[j][0]);
                
              } else if (fCounter == 0.0) return; // прерываем цикл
            }
        } 
     
       
          Print ("Array New Size ", ArraySize(mas)," ", mas[0][0], " ", mas[1][1]);   
}

 

 

#6149
8 часов назад, Alexfm2000 сказал:

 

Вот накидал с комментариями
 

Спойлер


double arrFractals[][2];
datetime TimeLastFr = 0;
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
{
   ArrayResize(arrFractals,1);
   ArrayInitialize(arrFractals,0.0);
   return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
   for(int i = 1; i < ArrayRange(arrFractals,0); i++)   // пишем в журнал записанные значения из массива
   {
      Print("Index ",i," , Volume ",arrFractals[i][0],"     ", arrFractals[i][1]);
   }
}
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
{
   if(IsNewBar())
   {
      fSignal();
   } 
}
//+------------------------------------------------------------------+
void fSignal()
{
   int    dir = -1;    // направление найденного фрактала
   double vol = 0.0;   // значение найденного фрактала
   int    arrSize = 0; // размер массива
   
   for(int i=1; i<15; i++)
   {
      double Signal_up = iFractals(_Symbol, PERIOD_CURRENT, 1, i);
      double Signal_low = iFractals(_Symbol, PERIOD_CURRENT, 2, i);
      
      if(Signal_up >0 || Signal_low > 0)//если нашли фрактал,
      {
         if(iTime(_Symbol,PERIOD_CURRENT,i) > TimeLastFr) // то проверяем его время
         {
            if(Signal_up >0)
            {
               dir = 0;
               vol = Signal_up;
            } 
            else if(Signal_low > 0)
            {
               dir = 1;
               vol = Signal_low;
            }
            
            arrSize = ArrayRange(arrFractals,0);  // считаем, сколько элементов в 0-м измерении массива. ArraySize вернет удвоенный размер, поэтому используем ArrayRange
            arrFractals[arrSize-1][dir] = vol;    // запишем значение и направление фрактала
            ArrayResize(arrFractals,arrSize + 1); // увеличиваем размер массива для следующего фрактала
                                                  // в нулевом индексе массива всегда будет пустое значение
            TimeLastFr = iTime(_Symbol,PERIOD_CURRENT,i); // запишем время найденного фрактала в глобальную переменную
         }
         else break; // прерываем цикл, если найденый фрактал уже записан в массив
      }
      else continue;
   }

   return;
}
//+------------------------------------------------------------------+
datetime prevTime=0;

bool IsNewBar()
{
   datetime arr[1] ;
   CopyTime(_Symbol,PERIOD_CURRENT,0,1,arr);
   
   if(arr[0] != prevTime)
   {
      prevTime = arr[0];
      return(true);
   }
   
   return(false);

 

В данной реализации может оказаться неудобным то, что значения фракталов разбросаны по разным индексам массива. Вот результат работы:

0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 1 , Volume 0.0     1.07962
0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 2 , Volume 1.08198     0.0
0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 3 , Volume 0.0     1.07745
0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 4 , Volume 1.08158     0.0
0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 5 , Volume 0.0     1.07797
0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 6 , Volume 1.08068     0.0
0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 7 , Volume 1.08075     0.0
0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 8 , Volume 0.0     1.0799
0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 9 , Volume 0.0     1.0798
0	11:49:22.133	2020.05.20 15:02:32  test_fractal EURUSD,H1: Index 10 , Volume 0.0     1.07929

Если нужно, чтобы значения шли подряд, то можно объявить два одномерных массива- первый для значений фрактала, второй- для записи направления:
 

Спойлер


double arrFractals[];
int    arrDir[];
datetime TimeLastFr = 0;
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
{
   ArrayResize(arrFractals,1);
   ArrayResize(arrDir,1);
   ArrayInitialize(arrFractals,0.0);
   ArrayInitialize(arrDir,0);
   
   return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
   for(int i = 1; i < ArraySize(arrFractals); i++)   // пишем в журнал записанные значения из массива
   {
      Print("Index ",i," , Volume ",arrFractals[i],"    Direction ", arrDir[i]);
   }
}
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
{
   if(IsNewBar())
   {
      fSignal();
   } 
}
//+------------------------------------------------------------------+
void fSignal()
{
   int    dir = 0;    // направление найденного фрактала
   double vol = 0.0;  // значение найденного фрактала
   int    Size = 0;   // размер массива
   
   for(int i=1; i<15; i++)
   {
      double Signal_up = iFractals(_Symbol, PERIOD_CURRENT, 1, i);
      double Signal_low = iFractals(_Symbol, PERIOD_CURRENT, 2, i);
      
      if(Signal_up >0 || Signal_low > 0)//если нашли фрактал,
      {
         if(iTime(_Symbol,PERIOD_CURRENT,i) > TimeLastFr) // то проверяем его время
         {
            if(Signal_up >0)
            {
               dir = 1;
               vol = Signal_up;
            } 
            else if(Signal_low > 0)
            {
               dir = 2;
               vol = Signal_low;
            }
            
            Size = ArraySize(arrFractals);     // считаем, сколько элементов в  массиве
            arrFractals[Size-1] = vol;         // запишем значение фрактала
            arrDir[Size-1] = dir;              // запишем направление фрактала
            ArrayResize(arrFractals,Size + 1); // увеличиваем размер массива для следующего фрактала
                                                  // в нулевом индексе массива всегда будет пустое значение
            ArrayResize(arrDir,Size + 1);                                      
            TimeLastFr = iTime(_Symbol,PERIOD_CURRENT,i); // запишем время найденного фрактала в глобальную переменную
         }
         else break; // прерываем цикл, если найденый фрактал уже записан в массив
      }
      else continue;
   }

   return;
}
//+------------------------------------------------------------------+
datetime prevTime=0;

bool IsNewBar()
{
   datetime arr[1] ;
   CopyTime(_Symbol,PERIOD_CURRENT,0,1,arr);
   
   if(arr[0] != prevTime)
   {
      prevTime = arr[0];
      return(true);
   }
   
   return(false);
}

 

Результат:
 

0	12:04:46.718	2020.05.19 14:20:00  test_fractal_2 EURUSD,H1: Index 1 , Volume 1.07962    Direction 2
0	12:04:46.718	2020.05.19 14:20:00  test_fractal_2 EURUSD,H1: Index 2 , Volume 1.08198    Direction 1
0	12:04:46.718	2020.05.19 14:20:00  test_fractal_2 EURUSD,H1: Index 3 , Volume 1.07745    Direction 2
0	12:04:46.718	2020.05.19 14:20:00  test_fractal_2 EURUSD,H1: Index 4 , Volume 1.08158    Direction 1
0	12:04:46.718	2020.05.19 14:20:00  test_fractal_2 EURUSD,H1: Index 5 , Volume 1.07797    Direction 2
0	12:04:46.718	2020.05.19 14:20:00  test_fractal_2 EURUSD,H1: Index 6 , Volume 1.08068    Direction 1
0	12:04:46.718	2020.05.19 14:20:00  test_fractal_2 EURUSD,H1: Index 7 , Volume 1.08075    Direction 1
0	12:04:46.718	2020.05.19 14:20:00  test_fractal_2 EURUSD,H1: Index 8 , Volume 1.0799    Direction 2
0	12:04:46.718	2020.05.19 14:20:00  test_fractal_2 EURUSD,H1: Index 9 , Volume 1.0798    Direction 2

test_fractal_2.mq47 скач.

test_fractal.mq46 скач.

Изменено 16 января, 2021 пользователем usver73

#6150
Только что, usver73 сказал:

В данной реализации может оказаться неудобным то, что значения фракталов разбросаны по разным индексам массива.

Если подумать, то можно в двумерном массиве, но без пропусков:
 

Спойлер

double arrFractals[][2];
datetime TimeLastFr = 0;
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
{
   ArrayResize(arrFractals,1);
   ArrayInitialize(arrFractals,0.0);
   return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
   for(int i = 1; i < ArrayRange(arrFractals,0); i++)   // пишем в журнал записанные значения из массива
   {
      Print("Index ",i," , Volume ",arrFractals[i][0],"  Direction ", arrFractals[i][1]);
   }
}
//+------------------------------------------------------------------+
//| Expert tick function                                             |
//+------------------------------------------------------------------+
void OnTick()
{
   if(IsNewBar())
   {
      fSignal();
   } 
}
//+------------------------------------------------------------------+
void fSignal()
{
   int    dir = 0;     // направление найденного фрактала
   double vol = 0.0;   // значение найденного фрактала
   int    arrSize = 0; // размер массива
   
   for(int i=1; i<15; i++)
   {
      double Signal_up = iFractals(_Symbol, PERIOD_CURRENT, 1, i);
      double Signal_low = iFractals(_Symbol, PERIOD_CURRENT, 2, i);
      
      if(Signal_up >0 || Signal_low > 0)//если нашли фрактал,
      {
         if(iTime(_Symbol,PERIOD_CURRENT,i) > TimeLastFr) // то проверяем его время
         {
            if(Signal_up >0)
            {
               dir = 1;
               vol = Signal_up;
            } 
            else if(Signal_low > 0)
            {
               dir = 2;
               vol = Signal_low;
            }
            
            arrSize = ArrayRange(arrFractals,0);  // считаем, сколько элементов в 0-м измерении массива. ArraySize вернет удвоенный размер, поэтому используем ArrayRange
            arrFractals[arrSize-1][0] = vol;    // запишем значение  фрактала
            arrFractals[arrSize-1][1] = dir;    // запишем направление  фрактала
            ArrayResize(arrFractals,arrSize + 1); // увеличиваем размер массива для следующего фрактала
                                                  // в нулевом индексе массива всегда будет пустое значение
            TimeLastFr = iTime(_Symbol,PERIOD_CURRENT,i); // запишем время найденного фрактала в глобальную переменную
         }
         else break; // прерываем цикл, если найденый фрактал уже записан в массив
      }
      else continue;
   }

   return;
}
//+------------------------------------------------------------------+
datetime prevTime=0;

bool IsNewBar()
{
   datetime arr[1] ;
   CopyTime(_Symbol,PERIOD_CURRENT,0,1,arr);
   
   if(arr[0] != prevTime)
   {
      prevTime = arr[0];
      return(true);
   }
   
   return(false);

 

результат:
 

0	12:17:14.614	2020.05.20 15:10:06  test_fractal_3 EURUSD,H1: Index 1 , Volume 1.07962  Direction 2.0
0	12:17:14.614	2020.05.20 15:10:06  test_fractal_3 EURUSD,H1: Index 2 , Volume 1.08198  Direction 1.0
0	12:17:14.614	2020.05.20 15:10:06  test_fractal_3 EURUSD,H1: Index 3 , Volume 1.07745  Direction 2.0
0	12:17:14.614	2020.05.20 15:10:06  test_fractal_3 EURUSD,H1: Index 4 , Volume 1.08158  Direction 1.0
0	12:17:14.614	2020.05.20 15:10:06  test_fractal_3 EURUSD,H1: Index 5 , Volume 1.07797  Direction 2.0
0	12:17:14.614	2020.05.20 15:10:06  test_fractal_3 EURUSD,H1: Index 6 , Volume 1.08068  Direction 1.0
0	12:17:14.614	2020.05.20 15:10:06  test_fractal_3 EURUSD,H1: Index 7 , Volume 1.08075  Direction 1.0

 

Для публикации сообщений создайте учётную запись или авторизуйтесь

Перейти к списку тем
Форум · 2.0.20260627.0025