Useful features from KimIV - page 86

 

Igor, can you give me a hint? Something from the indicator(iMA) in the EA the values come with 4 decimal places, while I need 5 for work! I tried NormalizeDouble(iMA,Digits) - it is still 4 decimal places. Is it necessary to rewrite the entire indicator into subprogram-function of the Expert Advisor to get 5 digits?

 

Help: Alert(), Comment(), Print()

Data of double type is output with 4 decimal digits after the point.

Use DoubleToStr() to output numbers with greater accuracy.

 

Good evening,

I can't cope with the correct closing of positions. There are two conditions for closing: 1. if one position is open; 2. if two (or more positions) are open. In both cases, the lot volume = 0.03. In the first case, the lot is closed separately by 0.01 (worked out in the posts above). In the second case, two lots should be closed both by 0.03. Correspondingly, if:

if (OrderType()==OP_BUY && BuyTotalOp==1)

then the first variant of closing and if:

if (OrderType()==OP_BUY && BuyTotalOp>1)

then the other (in my variant (preliminary) if the sum of both positions' profits > 0, then both positions should be closed). It looks like this:

   extern double Lots=0.03;           // Жестко заданное колич. лотов
.................................
   // Учёт количества имеющихся ордеров
   Symb=Symbol();                               // Название фин.инстр.
   BuyTotalOp=0;                                // Количество Buy ордеров
   SellTotalOp=0;                               // Количество Sell ордеров
   for (int i=1; i<=OrdersTotal(); i++)         // Цикл перебора ордер
      {
      if (OrderSelect( i-1, SELECT_BY_POS)==true) // Если есть следующий
        {                                       // Анализ ордеров:
         if (OrderSymbol()!= Symb)continue;      // Не наш фин. инструм
         if (OrderType()>1)                     // Попался отложенный
           {
            Alert("Обнаружен отложенный ордер. Эксперт не работает.");
            return;                             // Выход из start()
           }
         if (OrderType()==OP_BUY)
           {
            BuyTotalOp++;                         // Счётчик ордеров Buy
......................................
   //Проверка если открыто несколько БАЙ-позиций
   if (OrderType()==OP_BUY && BuyTotalOp>1)        // Тип ордера бай и ордеров по циклу "с начала" = 1
     {
//....................................     
      //---- если условия закрытия нескольких лотов БАЙ
      if ( BuyOrdProf>0)
        {
         //---- закрываем 1-ю часть позиции
         Alert("Попытка закрыть Buy ", TicketCl,". Ожидание ответа..");
         RefreshRates();                            // Обновление данных
         Ans=OrderClose( CloseTicketCl, Lots,Bid,0,Red);          // Закрытие Buy
         if ( Ans==true)                             // Получилось :)
           { 
            Alert ("Закрыт ордер Buy ", TicketCl);
            break;                                  // Выход из цикла закр
           }
         if ( Fun_Error(GetLastError())==1)          // Обработка ошибок
            continue;                               // Повторная попытка
         return;                                    // Выход из start()
        }
     }
//.........................................
   //Проверка если открыта одна БАЙ-позиция
   if (OrderType()==OP_BUY && BuyTotalOp==1)        // Тип ордера бай и ордеров по циклу "с начала" = 1
     {
//....................................     
      //---- если условия закрытия одного лота БАЙ
      if ( BUYCLOSE_1PART && BuyClLot== Lots)
        {
         //---- закрываем 1-ю часть позиции
         Alert("Попытка закрыть Buy ", TicketCl,". Ожидание ответа..");
         RefreshRates();                            // Обновление данных
         Ans=OrderClose( CloseTicketCl, LotCloseBuy/3,Bid,0,Red);          // Закрытие Buy
         if ( Ans==true)                             // Получилось :)
           { 
            Alert ("Закрыт ордер Buy ", TicketCl);
            break;                                  // Выход из цикла закр
           }
         if ( Fun_Error(GetLastError())==1)          // Обработка ошибок
            continue;                               // Повторная попытка
         return;                                    // Выход из start()
        }
 

In fact, it turns out that when the conditions for closing both lots appear, the first lot closes completely, while the second lot "takes over" the closing conditions BuyTotalOp==1 and closes according to its own conditions.

Please advise what is wrong with the closing conditions and how to make both lots close at once? Thanks in advance.

 
I tried both OrderTicket() and Lots counting and plusing in the order loop - to no avail... Maybe, as always, "the truth is somewhere near", but it doesn't catch on...
 

Separate the flies from the cutlets... write some useful functions...

For example, count the number of open orders by order type, close orders by order type, etc...

then everything will be easier...

if ( ordersTotal( SYMBOL,OP_BUY)==1) closeAllOrders( SLIPPAGE, TRY, TRADESLEEP, SHOWERRORS, SYMBOL,OP_BUY);
if ( ordersTotal( SYMBOL,OP_BUY) > 1) closeAllOrders( SLIPPAGE, TRY, TRADESLEEP, SHOWERRORS, SYMBOL,OP_BUY);

...because you have a missing } somewhere, and it becomes unclear what exactly is being done...may be you are trying to temporarily count the number of orders and immediately delete them, or what ? pending orders might be better skipped and not interrupted when they exist ?

A good option would be a function that, according to given conditions, would form an array with parameters of open orders that you can run through and close them ... in general, work on the structure ...

 

Thanks keekkenen, I've just been thinking about creating an array lately. It's just that I've never worked with it and hoped there was a simpler solution, that I already have a "closed" eye, and someone with fresh eyes will look at it and say "geez, where's your counting so-and-so...". Well, all the buy orders in the loop have been calculated:

   // Учёт количества имеющихся ордеров от начала к концу
   Symb=Symbol();                               // Название фин.инстр.
   BuyTotalOp=0;                                // Количество Buy ордеров
   SellTotalOp=0;                               // Количество Sell ордеров
   for (int i=1; i<=OrdersTotal(); i++)         // Цикл перебора ордер
      {
      if (OrderSelect( i-1, SELECT_BY_POS)==true) // Если есть следующий
        {                                       // Анализ ордеров:
         if (OrderSymbol()!= Symb)continue;      // Не наш фин. инструм
         if (OrderType()>1)                     // Попался отложенный
           {
            Alert("Обнаружен отложенный ордер. Эксперт не работает.");
            return;                             // Выход из start()
           }
         if (OrderType()==OP_BUY)
           {
            BuyTotalOp++;                         // Счётчик ордеров Buy
....................................

and OrderClose doesn't count them...

   //Проверка если открыто несколько БАЙ-позиций
   if (OrderType()==OP_BUY && BuyTotalOp>1)        // Тип ордера бай и ордеров по циклу "с начала" = 1
     {
//....................................     
      //---- если условия закрытия нескольких лотов БАЙ
      if ( BuyOrdProf>0)
        {
         //---- закрываем 1-ю часть позиции
         Alert("Попытка закрыть Buy ", TicketCl,". Ожидание ответа..");
         RefreshRates();                            // Обновление данных
         Ans=OrderClose( CloseTicketCl, BuyTotalOp,Bid,0,Red);          // Закрытие Buy
...................................................................
well, yes, it's obvious "overkill" .......
 

and frankly, I don't understand this.

Ans=OrderClose( CloseTicketCl, Lots,Bid,0,Red);          // Закрытие Buy

and this one, especially the division of the lot by 3 ? the order is closed with the same lot as it was opened...

Ans=OrderClose( CloseTicketCl, LotCloseBuy/3,Bid,0,Red);          // Закрытие Buy

why not in both cases ?

Ans=OrderClose(OrderTicket(),OrderLots(),OrderClosePrice(),0,Red);          // Закрытие Buy
 

why not in both cases ?

Ans=OrderClose(OrderTicket(),OrderLots(),OrderClosePrice(),0,Red);          // Закрытие Buy

CloseTicketCl = OrderTicket () in general you can do this...

and this, especially dividing the lot by 3 ?? the order is closed with the same lot as it is opened...

Ans=OrderClose( CloseTicketCl, LotCloseBuy/3,Bid,0,Red);          // Закрытие Buy

not the same

.

One third of the lot is closed (according to one of the conditions - let's say the price has reached +150 pips). The second third will close, say, when +300 pips from the opening, etc...

and frankly I don't understand this

Ans=OrderClose( CloseTicketCl, Lots,Bid,0,Red);          // Закрытие Buy
here Lots and OrderLots() yes, the same thing.
 
hope >> Not the same. One third of the lot will be closed (according to one of the conditions - let us assume that the price has reached +150 points). The second third will close, say, when +300 pips from the opening, etc..

No, that will not work. one order - one lot, if you have opened an order with 3 lots, you cannot split the lot as you want - first 1, then 1 and then 1 more - the order closes the entire lot, i.e. the order closes with the same lot as it was opened, you cannot close orders in parts...

Reason: