Jump to content

Общие вопросы по языку MQL


Recommended Posts

torgf
48 минут назад, Pirojoque Project сказал:

Не понимаю проблему. Опишите подробней.

11:15 вчера - это iTime(Symbol(), PERIOD_D1, 1) + 15 * 60 + 11 * 3600

Как полям  структуры типа MqlDateTime, присвоить такие  значения - "11:15 вчера"?

Link to post
Share on other sites
  • Replies 7.6k
  • Created
  • Last Reply

Top Posters In This Topic

  • AntFX

    577

  • sergey1294

    569

  • Ugar68

    517

  • Programmer

    419

Top Posters In This Topic

Popular Posts

Ну, в данном случае мне стоило бы сразу соблюдать простейшие приёмы защитного программирования, то есть проверять, не равна ли нулю переменная, оказавшаяся под знаком деления. Ведь она "чужая", то ест

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

Основной советник выставляет "сигнальный" отложенный ордер далеко от текущей цены и каждую например, минуту модифицирует у него время экспирации: это может быть текущее время плюс 1 час, или плюс 1 су

Posted Images

Pirojoque Project
39 минут назад, torgf сказал:

Как полям  структуры типа MqlDateTime, присвоить такие  значения - "11:15 вчера"?

Вопрос ясен. Очень легко:

MqlDateTime mqltime; // Время-структура
datetime basetime = TimeCurrent(); // Время, от которого будем отсчитывать сдвиг (здесь — текущее время сервера)

TimeToStruct(basetime, mqltime); // Конвертируем базовое время в структуру
mqltime.day--; // Модифицируем структуру (сегодняшний день откручиваем назад на один)
mqltime.hour = 11; // Устанавливаем час
mqltime.min = 15; // Устанавливаем минуту

datetime targettime = StructToTime(mqltime); // Конвертируем время-структуру в искомое время простого формата (вчерашние 11:15)
int n = iBarShift(_Symbol, _Period, targettime); // Получили номер искомого бара (который был вчера в 11:15)

 

  • Upvote 1
Link to post
Share on other sites
torgf
1 час назад, Pirojoque Project сказал:

Вопрос ясен. Очень легко:

 

Спасибо.

Количество баров расчёта ограничиваю так

   int limit=rates_total-prev_calculated;
   if(limit>1000)
     {
      limit=1000;//rates_total-20;
     }
//--- Цикл расчёта индикатора
   for(int i=limit; i>=0; i--)
     {
//
     }

 

Как ограничить расчёт индикатора не в барах, а в днях? Например 4 дня, дальше не считать.

Edited by torgf
Link to post
Share on other sites
Ugar68

4 дня или 4 дневных бара? Из за выходных есть разница.


Пишу советники и индикаторы по вашим алгоритмам. Пишите в личку.
Чужие программы не переделываю.

Link to post
Share on other sites
Pirojoque Project
В 31.07.2018 в 22:50, torgf сказал:

Количество баров расчёта ограничиваю так

Зачем? Полная глубина истории на графике будет посчитана один раз, а затем пересчёт будет производиться только на новых барах (на последнем обычно, если история уже подгружена).

 

В 31.07.2018 в 22:50, torgf сказал:

Как ограничить расчёт индикатора не в барах, а в днях? Например 4 дня, дальше не считать.

С помощью приёма со временем-структурой нужно найти бар, который был 4 дня назад и цикл расчёта индикатора производить от него, а не от limit, как вы это делали.

  • Thanks 1
Link to post
Share on other sites
AntFX
В 31.07.2018 в 22:50, torgf сказал:

Как ограничить расчёт индикатора не в барах, а в днях? Например 4 дня, дальше не считать.

limit=iBarShift(Symbol(), Period(), TimeCurrent() - 86400 * 4);

  • Thanks 1

1

Link to post
Share on other sites
DVargo

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

Почему бы не вынести все в скрипт или советник. И вызывать построение трендовой по мере надобности - раз в сутки, в час и т.д.

Зачем  эти все лимиты?

Link to post
Share on other sites
torgf
11 часов назад, AntFX сказал:

limit=iBarShift(Symbol(), Period(), TimeCurrent() - 86400 * 4);

Не хочет ограничивать, всю историю считает.

//--- Проверка на минимальное колиество баров для расчёта
   if(rates_total<4) return 0;

   int limit=rates_total-prev_calculated;
  
     limit=iBarShift(Symbol(), Period(), TimeCurrent() - 86400 * 4);
//--- Цикл расчёта индикатора
   for(int i=limit; i>=0; i--)
     {
     //
     }

Что не так?

Edited by torgf
Link to post
Share on other sites
AntFX
6 минут назад, torgf сказал:

Не хочет ограничивать, всю историю считает.

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

  • Upvote 1

1

Link to post
Share on other sites
torgf
8 минут назад, AntFX сказал:

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

Изменила т.ф., Ограничивает. Спасибо.

ENUM_TIMEFRAMES tf=PERIOD_D1;
   if(rates_total<4) return 0;

   int limit=rates_total-prev_calculated;
  
     limit=iBarShift(Symbol(), tf, TimeCurrent() - 86400 * (N_-1));
//--- Цикл расчёта индикатора
   for(int i=limit; i>=0; i--)
     {
     //
     }

 

Link to post
Share on other sites
torgf

Как вернуть true, если 4 первых фрактала расположены по возрастанию?

f=iFractals(sy,tf,MODE_UPPER,1);

 

Edited by torgf
Link to post
Share on other sites
Ugar68

Надо в цикле перебирать бары в поисках фракталов. Найденные запоминать и сравнивать со следующим найденным.

  • Thanks 1

Пишу советники и индикаторы по вашим алгоритмам. Пишите в личку.
Чужие программы не переделываю.

Link to post
Share on other sites
torgf
9 часов назад, Ugar68 сказал:

Надо в цикле перебирать бары в поисках фракталов. Найденные запоминать и сравнивать со следующим найденным.

Спасибо. Задача на определённом количестве "dofr" баров посчитать фракталы, прибавить единицу и затем убедиться что они  расположены по возрастанию. Первую часть сделала, как теперь построить цикл сравнения этих  kfr_all+1?

попыталась, но не выходит

//+--------------------------------------------
bool f_UPPER(int dofr,int n_)
  {
   int tf=0;//,
   int kfr_all=0;
   string sy=Symbol();
   double f=0,fn=0,old_f=0;
   int    i,kf;

   for(i=n_; i<n_+dofr; i++)
     {
      f=iFractals(sy,tf,MODE_UPPER,i);
      if(f!=0)
        {
         kfr_all++;
        }
     }
//посчиталa фракталы
//сравниваю,если каждый след. фр. больше то true
   int    n=0,con;
   for(int i=n; i<=kfr_all+1; i++)
     {
      fn=iFractals(sy,tf,MODE_UPPER,1);
      if(fn>0)
         n++;
      if(fn>old_f)
        {
         old_f=fn;
         con++;
        }
     }
   if(con==kfr_all)return(true);

   return(false);
  }
//+------------------------------------------------------

 

Link to post
Share on other sites
Ugar68

Сравнивать надо найденные фракталы. для этого их надо запомнить все в массиве. Но проще всего это сделать в одном цикле. Тогда запоминать надо только прошлый найденный фрактал.

bool f_UPPER(int dofr,int n_)
   {
   int tf=0;
   int kfr_all=0;
   string sy=Symbol();
   double f=0,fn=0,old_f=0;
   int    i;

   for(i=n_; i<n_+dofr; i++)
     {
      f=iFractals(sy,tf,MODE_UPPER,i);
      if(f>0)//Если фрактал найден
        {
         kfr_all++;//счётчик фракталов
         //Сравнение фрактала с прошлым, если не по возрастанию - выйти вернув false
         if(old_f>0 && old_f<f)return(false);
         old_f=f;
        }
     //Если досчитали до 4 фракталов и не вылетели ранее-выйти вернув true
     if(kfr_all==4)return(true);
     }
   return(false);
   }

Как то так.

  • Upvote 1

Пишу советники и индикаторы по вашим алгоритмам. Пишите в личку.
Чужие программы не переделываю.

Link to post
Share on other sites
torgf
8 часов назад, Ugar68 сказал:

Сравнивать надо найденные фракталы. для этого их надо запомнить все в массиве. Но проще всего это сделать в одном цикле. Тогда запоминать надо только прошлый найденный фрактал.

Как то так.

Спасибо.

Вероятно моя формулировка задачи некорректна. Количество баров и фракталов динамически меняется.

Задача глобально:   между первым и вторым нижними фракталами найти все верхние  фракталы плюс 1 фрактал, то есть участвует в сравнении ещё и первый верхний расположенный за вторым нижним.

Если все расположены по возрастанию=true. Приведённым вами примером могу посчитать только верхние фракталы между первым и вторым нижними. Нужно как то добавить ещё один фрактал )

Link to post
Share on other sites
Ugar68

Тогда надо в цикле искать и считать сразу верхние и нижние фракталы. Но критерием для прекращения поиска и возвратом true, будет не досчитал 4 верхних, а досчитал 2 нижних и после 1 верхний.

Критерий прекращения поиска и возврата false - остаётся.

  • Thanks 1

Пишу советники и индикаторы по вашим алгоритмам. Пишите в личку.
Чужие программы не переделываю.

Link to post
Share on other sites
torgf
9 минут назад, Ugar68 сказал:

а досчитал 2 нижних и после 1 верхний.

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

Link to post
Share on other sites
torgf

Не получается, помогите.
Нахожу второй нижний фрактал, запоминаю бар в переменную 1.
От этого бара нахожу первый верхний фрактал, запоминаю бар в переменную 2.
Затем до бара в переменной 2 нахожу верхние фракталы, считаю их количество  и количество возрастающих фракталов. Если их равное количество значит каждый следующий больше, возвращаю true.
Почему всегда true?
 

bool f_UPPER(int n_)
   {
   int tf=0,niznum,verhnum,nbar=0,vbar=0;
   int kfr_all=0,rit_fr=0;
   string sy=Symbol();
   double f=0,fn=0,old_f=0,fl=0,fup=0;
   int    i,k=iBars(sy,tf);
   for(i=n_; i<k; i++)
     {
     fl=iFractals(sy,tf,MODE_LOWER,i);
      if(fl>0)//Если фрактал найден
      {
      nbar++;
      }
      if(nbar==3)//если фрактал второй
        {
        niznum=i;//запомню бар, от него буду искать первы верхний
       //
         break;
        }
     }
     //
   for(i=niznum; i<k; i++)
     {
     fup=iFractals(sy,tf,MODE_UPPER,i);
      if(fup>0)//Если фрактал найден
      {
        verhnum=i;// до этого бара буду искать верхние фракталы
         break;
        }
     }
     
     //
   for(i=n_+2; i<verhnum; i++)
     {
      f=iFractals(sy,tf,MODE_UPPER,i);
      if(f>0)//Если фрактал найден
        {
         kfr_all++;//счётчик фракталов
         //Сравнение фрактала с прошлым, если по возрастанию, то +1
         if(old_f>0 && old_f<f)
         {
         rit_fr++;
         
         }
         old_f=f;
        }
     //Если общее количество найденыx фракталов равно количеству возрастающих, то true
     if(kfr_all==rit_fr)return(true);
     }
   return(false);
   }
//

 

Edited by torgf
Link to post
Share on other sites
Ugar68

Зачем так усложнять? Всё можно сделать в одном цикле. Добавить поиск и счётчик нижних фракталов и сделать что бы счётчик верхних начинал работать после того как счётчик нижних досчитал до 2.

bool f_UPPER(int n_)
   {
   int tf=0;
   int CountFUp=0, CountFLow=0;
   string sy=Symbol();
   double f_up=0, f_low=0,fn=0,old_f=0;
   int    i;

   for(i=n_; i<Bars; i++)
     {
      f_up=iFractals(sy,tf,MODE_UPPER,i);
      f_low=iFractals(sy,tf,MODE_LOWER,i);
      if(f_low>0)CountFLow++;//Счётчик нижних фракталов
      if(f_up>0)//Если фрактал найден
        {
         //Если найдено 2 нижних фрактала, считать верхние
         if(CountFLow>=2)CountFUp++;//счётчик верхних фракталов
         //Сравнение фрактала с прошлым, если не по возрастанию - выйти вернув false
         if(old_f>0 && old_f<f_up)return(false);
         old_f=f_up;
        }
     //Если досчитали до 1 фрактал и не вылетели ранее-выйти вернув true
     if(CountFUp==1)return(true);
     }
   return(false);
   }

Как то так.

Edited by Ugar68
  • Thanks 1

Пишу советники и индикаторы по вашим алгоритмам. Пишите в личку.
Чужие программы не переделываю.

Link to post
Share on other sites
torgf
5 часов назад, Ugar68 сказал:

Как то так.

Спасибо.

Link to post
Share on other sites
  • 2 weeks later...
krolix

Здравствуйте, товарищи программисты! Помогите решить такой вопрос:

Имеется такой вот код когда советник завершает работу при достижении заданного процента в настройках (нашел на другом форуме). Подскажите пожалуйста как реализовать данную функцию в советнике? MetaEditor ругается на эту функцию ChekDayProfitByPercent. Google ничего не дал. 


//+------------------------------------------------------------------+
//Функция для проверки заработанного процента
bool ChekDayProfitByPercent(double StartBalanse, uint Percent)
{
bool Result = False;
MqlDateTime CurrentDate;
double DayProfit = 0.0;
int HistoryTotal = OrdersHistoryTotal();

//Формируем текушую дату
TimeToStruct(TimeCurrent(), CurrentDate);
CurrentDate.hour = 0;
CurrentDate.min = 0;
CurrentDate.sec = 0;

//Считаем дневной профит
for(int i = 0; i < HistoryTotal; i++)
if(OrderSelect(i, SELECT_BY_POS, MODE_HISTORY))
if(OrderCloseTime() >= StructToTime(CurrentDate))
DayProfit = DayProfit + OrderProfit();
//Сравниваем с заданным процентом
if(DayProfit >= StartBalanse * (Percent / 100.0))
Result = True;
//Выход
return(Result);
}

//Пример использования, Баланс = 100.00 уёв, процент = 10%
if(ChekDayProfitByPercent(100.00, 10)) return;

 

Link to post
Share on other sites
sviter

Граждане подскажите правильно ли я делаю!!! Нужно что бы советник торговал когда не вошел за зону 30 или 70, а когда зашел, то не торговал!!! Так правильно сделано?

RSI3 = iRSI(_Symbol, _Period, RSIPeriod, PRICE_CLOSE, 1);
RSI4 = iRSI(_Symbol, _Period, RSIPeriod, PRICE_CLOSE, 2);

bool RSItf = RSI3 > 30 && 30 > RSI4;
if(RSItf == true)
{
}
else
{
ordersend(_Symbol, OP_SELL, lot, Bid, Slippage, 0, 0, NULL, Magic, 0, clrRed);
}
bool RSItf = RSI3 > 70 && 70> RSI4;
if(RSItf == true)
{
}
else
{
ordersend(_Symbol, OP_BUY, lot, Ask, Slippage, 0, 0, NULL, Magic, 0, clrBlue);
}

Link to post
Share on other sites
Ugar68

Получается по коду:

Если на сформированном баре индикатор пересёк 30 снизу вверх, он ничего не делает. Всё остальное время от открывает Sell на каждом тике, независимо от того где находится индикатор выше или ниже 30.

Если на сформированном баре индикатор пересёк 70 снизу вверх, он ничего не делает. Всё остальное время от открывает Buy на каждом тике, независимо от того где находится индикатор выше или ниже 70.

1. Для открытия нужно какое то условие, характеризующее точку входа. Или хотя бы запретить открывать если уже есть открытый ордер. Иначе будут открываться сделки на каждом тике.

2. Судя по описанию надо разрешить торговлю когда индикатор находится между 30 и 70.

RSI3 = iRSI(_Symbol, _Period, RSIPeriod, PRICE_CLOSE, 1);

if(RSI3>30 && RSI3<70)
{
if(...)//вместо точек условие для открытия Sell
    {
    OrderSend(_Symbol, OP_SELL, lot, Bid, Slippage, 0, 0, NULL, Magic, 0, clrRed);         
    }
if(...)//вместо точек условие для открытия Buy
    {
    OrderSend(_Symbol, OP_BUY, lot, Ask, Slippage, 0, 0, NULL, Magic, 0, clrBlue);
    }
}

 

 

  • Upvote 1

Пишу советники и индикаторы по вашим алгоритмам. Пишите в личку.
Чужие программы не переделываю.

Link to post
Share on other sites
AntFX
В 15.08.2018 в 19:59, krolix сказал:

//Выход

return(Result);

}

 

//Пример использования, Баланс = 100.00 уёв, процент = 10%

if(ChekDayProfitByPercent(100.00, 10)) return;

Выделенное красным - это не часть кода, а пример его использования. Её нужно удалить из кода и тогда ругаться не будет.

Edited by AntFX

1

Link to post
Share on other sites
  • 3 weeks later...
torgf

Как получить значения линий сетки  Фибоначчи, натянутой по первым  фракталам?
В переменных LOWER, UPPER, значения фракталов.

Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

  • Recently Browsing   0 members

    No registered users viewing this page.


×
×
  • Create New...