[Archive!] Any rookie question, so as not to clutter up the forum. Professionals, don't pass it by. Couldn't go anywhere without you - 2. - page 294

 
CreAndr:
I have a question about the trawl, who can tell me. It seems to be the right trawl to breakeven, but it doesn't work.

Here is a trawl: https://www.mql5.com/ru/forum/131859

To insert the code into the text, press the SRC button above the text input field.

 
DhP:

Here is a trawl: https://www.mql5.com/ru/forum/131859

To insert the code into the text, press the SRC button above the text input field.


Thank you.
 
CreAndr:
I have a question about trawl, who can tell me. It seems to be correct trawl to breakeven, but it doesn't work.


List of reasons in descending order of importance:

1. The computer is not switched on

2. Metatrader is not switched on.

3. Script on the chart is not installed

4. Expert Advisors not enabled

5. Nothing to trawl.

6. Something in the code is wrong.

 
Roger:


Listing the reasons in descending order of importance:

1. The computer is not switched on

2. Metatrader is not switched on.

3. Script on the chart is not installed

4. Expert Advisors not enabled

5. Nothing to trawl.

6. Something in the code is wrong.

Great answer, Roger, but the computer is on, so is Metatrader, EA is attached to the chart, EAs are enabled, trades are opening and therefore there is something to trawl! But what's wrong with the code, that was the question.
 
artmedia70:
Use OrderOpenTime()
For - why do we need it then?


So, yes, but by order number I got pretty short, but with OrderOpenTime I don't understand what to do, I need to put open time somewhere, compare with next order in the list, if time is longer, rewrite the variable, etc. I don't understand the algorithm yet.


bool DeleteOrders()
{
   for(int i=0 ; i <=OrdersTotal() ; i++)
      {
      if(OrderSelect(i,SELECT_BY_POS,MODE_TRADES))
         {
         if(Symbol()==OrderSymbol())
            {
            if(OrderType()!= OP_SELL)
               {
               int ticket=OrderTicket();
               OrderDelete(ticket);
               return(true);
               }
            }
         }
      }
return(false);
} 
 
CreAndr:
Great answer, Roger, but the computer is enabled, so is MetaTrader, EA is attached to the chart, EAs are enabled, trades are opened and therefore there is something to trawl! But what's wrong with the code, that was the question.


At first there was no code, you attached it later.

Probably because you have put trailing in the order opening function, i.e. conditions for opening an order do come, the order is opened, but it may not get any further.

 
Pyro:

So, yes, but by order number I got pretty short, but with OrderOpenTime I don't understand what to do, I need to put open time somewhere, compare with next order in the list, if time is longer, rewrite the variable, etc. I do not understand the algorithm yet.


Serial number is not reliable, nothing is guaranteed in this numbering, only for tester. A couple of pages earlier, I had written code for searching for the last closed order. It is very simple, we have looked through the ticket, then we have chosen the order or position by the ticket, and that's it:

  int lastclosetime=-1;
  int lastcloseticket=-1;
  int lastdealtype=0;

  for (int i=0; i<OrdersHistoryTotal(); i++) 
  {
    if (!OrderSelect(i, SELECT_BY_POS, MODE_HISTORY)) continue; 
    if (OrderSymbol()==symbol || OrderMagicNumber()==magic) 
    {
      if (lastclosetime<OrderCloseTime()) 
      {
        lastclosetime=OrderCloseTime();
        lastcloseticket=OrderTicket();
      }
    }
  }

  if (OrderSelect(lastcloseticket, SELECT_BY_TICKET, MODE_HISTORY)) 
  {
    if (OrderType()==OP_BUY) lastdealtype=1;
    if (OrderType()==OP_SELL) lastdealtype=-1;   
  }
 
Figar0:


The order number is unreliable, no one guarantees anything in this numbering, only for the tester. A couple of pages earlier I wrote code to find the last closed order, the same for open ones. Everything is simple, we have gone through it, remembered the ticket, then chose an order or a position by the ticket, and that's it:

Thank you, it's really simple. I will look into it.
 
Roger:


At first there was no code, you added it later.

Probably because you have put trailing in the order opening function, i.e. conditions for order opening do occur, the order is opened, but it may not get any further.

I see, thank you.
 
Figar0:


The order number is unreliable, no one guarantees anything in this numbering, only for the tester. A couple of pages earlier I wrote code to find the last closed order, the same for open ones. It is very simple, we have looked through the ticket, then we have chosen an order or a position by the ticket and that's it:

The code is wrong.

First of all, here is this:

if (OrderSymbol()==symbol || OrderMagicNumber()==magic) 

If the order symbol is equal to the given symbol in the symbol variable or the order magic is equal to magic... So if any order with the symbol is selected and the magik is different or missing, the condition will be satisfied. Because it is either this or that. Correspondingly, we should replace either with or, or, better, separate checks into separate strings - the loop will be faster, which is crucial for optimization.

Further... Pick by ticket: The pool parameter is ignored, i.e., there's no sense in writing it here.

if (OrderSelect(lastcloseticket, SELECT_BY_TICKET, MODE_HISTORY)) 

After the order has been successfully selected by ticket, we should check from which list of orders it has been selected - the market ones or the closed ones. To do this, we need to check the time of order closing, and if it is higher than zero, then the order has definitely been closed. This parameter is always equal to zero for open positions. IMHO, after the last order is chosen, we should check its type immediately and write it in the variable.

The function will now look like this:

int   GetTypeLastClosePos(int symbol, int magic)   // Функция возвращает 0 если последний закрытый Бай, 1 - если Селл и -1 при ошибке
{
int   i, lastclosetime=0, 
         lastdealtype=-1;

   for (i=0; i<OrdersHistoryTotal(); i++) {
      if (OrderSelect(i, SELECT_BY_POS, MODE_HISTORY)) { // Если выбрали ордер в истории
         if (OrderSymbol()!=symbol)          continue;   // Если его символ не равен переданному в функцию - идём к следующему
         if (OrderMagicNumber()!=magic)      continue;   // Если его магик не равен переданному в функцию - идём к следующему
         if (OrderType()>1)                  continue;   // Если ищем только Бай и Селл, значит если больше единицы - к следующему
         // ... теперь выбранный ордер соответствует критериям поиска по символу, магику и типу
         if (lastclosetime<OrderCloseTime()) {           // Посмотрим время его закрытия и если оно больше предыдущего, то...
            lastclosetime=OrderCloseTime();              // ... запишем его как предыдущее
            lastdealtype=OrderType();                    // Тип текущего закрытого ордера: 0 для Бай, 1 для Селл
            }
         }
      else if (!OrderSelect(i, SELECT_BY_POS, MODE_HISTORY)) { // Иначе, если не удалось выбрать ордер в истории
         Print ("Func: GetTypeLastClosePos, Ошибка выбора ордера - ",GetLastError());  // Посмотрим номер ошибки
         break;                                                // Выходим из цикла перебора ордеров
         }
      }
   return(lastdealtype);
}

Now, if we want to check only Buy or Sell of the current chart and which of them was the last closed, we should call this function this way:

int LastPoseType=GetTypeLastClosePos(Symbol(), Magic);
if (LastPoseType==OP_BUY) {
   // ... код, если последний закрытый Buy ...
   }
if (LastPoseType==OP_SELL) {
   // ... код, если последний закрытый Sell ...
   }
else {// ... код обработки ошибки ... }

For error handling we can, in principle, create a global variable, e.g. int err; and in the body of the function itself store the error number in this variable:

else if (!OrderSelect(i, SELECT_BY_POS, MODE_HISTORY)) { // Иначе, если не удалось выбрать ордер в истории
         err=GetLastError();                                                     // Посмотрим номер ошибки
         Print ("Func: GetTypeLastClosePos, Ошибка выбора ордера - ",err);       // Сообщим об ошибке и в какой ф-ции она произошла
         break;                                                                  // Выходим из цикла перебора ордеров
         }

Then to process the error after calling the function ...

GetTypeLastClosePos(Symbol(), Magic);

... and error occurs, its number will be stored in variable err and in the processing block this number will be processed.

else {
   if (err==???) {
      // обработка этой ошибки
      }
   if (err==???) {
      // обработка этой ошибки
      }
// ... и т.д. ...
   }

Better yet, use switch

Reason: