Quaisquer perguntas de recém-chegados sobre MQL4 e MQL5, ajuda e discussão sobre algoritmos e códigos - página 1919

 
Artyom Trishkin #:

É pouco provável que você obtenha respostas dos desenvolvedores neste tópico. Se você encontrar um erro, certifique-se de que seja realmente um erro, relate-o à filial de Alexey. Não há necessidade de esperar ações de moderadores nesta ocasião - nós também somos pessoas e também não temos tempo.

Olá Artem!

Tudo está claro.

Atenciosamente, Vladimir.

 

Boa tarde!!!!

Aqui estão duas funções para o consultor da grade A primeira função é o cálculo do lucro, levando em conta o fechamento parcial de pedidos perdidos

//+----------------------------------------------------------------------------+
//| Калькуляция сетки ордеров                                                  |
//+----------------------------------------------------------------------------+
bool CalculiteProfit()
  {
   double oProfit=0,oLoss=0,percent;
   int i;
   nOrd=0;
   for(i = OrdersTotal()-1; i>=0; i--)
     {
      if(!OrderSelect(i, SELECT_BY_POS, MODE_TRADES) || OrderSymbol()!=Symbol() || OrderMagicNumber()!=Magic || OrderType()>OP_SELL)
         continue;
      if(OrderProfit()>=0)
         oProfit += OrderProfit();
      else
        {
         oLoss+=OrderProfit();
         Ord_ticket[nOrd]=OrderTicket();
         Ord_lot[nOrd]=OrderLots();
         nOrd++;
        }
     }
   oLoss = MathAbs(oLoss+GetOrderSwap()+GetOrderCommission());
   if(oLoss>0)
      percent=oProfit/oLoss*100;
   else
      percent=100;
   if(percent<MinPercentForClose) //MinPercentForClose переменная из настроек 
      return(false);
   for(i=0; i<nOrd; i++)
     {
      Ord_lot[i]=(MathCeil((Ord_lot[i]*RowLots)*percent)/100)/RowLots;
     }
   return(true);
  }

A segunda função é fechar ordens com fechamento parcial de ordens não-lucrativas

//+----------------------------------------------------------------------------+
//| Закрытие сетки ордеров при заданной команде с учетом части ордеров         |
//+----------------------------------------------------------------------------+
void ClosseAll()
  {
   int i,j,tkt;

   for(i = OrdersTotal()-1; i>=0; i--)
     {
      if(!OrderSelect(i, SELECT_BY_POS, MODE_TRADES) || OrderSymbol()!=Symbol() || OrderMagicNumber()!=Magic)
         continue;
      tkt=OrderTicket();
      RefreshRates();
      if(OrderProfit()>=0)
        {
         if(OrderType() == OP_BUY)
           {
            if(!OrderClose(OrderTicket(), OrderLots(), Bid, slip))
               Print("Не удалось закрыть ордера на покупку!");
           }
         else
            if(OrderType() == OP_SELL)
              {
               if(!OrderClose(OrderTicket(), OrderLots(), Ask, slip))
                  Print("Не удалось закрыть ордер на продажу!");
              }
        }
      else
         for(j=0; j<nOrd; j++)
            if(tkt==Ord_ticket[j])
              {
               if(OrderLots()<Ord_lot[j])
                  Ord_lot[j]=OrderLots();
               Ord_lot[j]=NRL(Ord_lot[j]);
               if(OrderType() == OP_BUY)
                 {
                  if(!OrderClose(OrderTicket(), Ord_lot[j], Bid, slip))
                     Print("Не удалось закрыть ордера на покупку!");
                 }
               else
                  if(OrderType() == OP_SELL)
                    {
                     if(!OrderClose(OrderTicket(), Ord_lot[j], Ask, slip))
                        Print("Не удалось закрыть ордер на продажу!");
                    }
               break;
              }
     }
  }

A situação é a seguinte: se eu fechar uma grade de ordens levando em conta o fechamento parcial de ordens perdidas, recebo uma perda como resultado do arredondamento para o lado maior de alguns lotes que precisam ser fechados

A questão é se você pode usar estas duas funções para escrever uma função para calcular a perda de pedidos, ou melhor, uma parte de um pedido a ser fechado.

Se for o caso, por favor, ajude-me a escrevê-lo

Obrigado

 
EVGENII SHELIPOV #:

Boa tarde!!!!

Se for o caso, ajude-me a escrevê-lo.

Não é um bom momento.

Você quer dizer escrevê-lo para você?

 
Andrey Sokolov #:

Estes não são bons tempos.

Você quer dizer escrever para você?

Não se rasgue Alexandre

 

perdido nas coisas elementares:

como organizo uma postura de arrasto - co-dirigida, por alguma razão ela arrasta uma postura, ou seja, não arrasta... MT5

for (i=0; i<PositionsTotal(); i++)   
     if (a_position.Select(_Symbol))       
     if (PositionSelect(_Symbol)) if(Symbol()==PositionGetSymbol(i))  
     if (Magic==PositionGetInteger(POSITION_MAGIC))  
   //  magic = myposition.Magic();   
      {
         //  ------------   перевод в бу  BUY   ------------    
         //if(PositionGetInteger(POSITION_TYPE)==POSITION_TYPE_BUY) 
         if (a_position.PositionType() == POSITION_TYPE_BUY)
          if (NLb_fun > 0)
            {
                Print(" перевод в безубыток BUY, _SL = ", _SL, " POSITION_PRICE_OPEN: ",
                     NormalizeDouble(PositionGetDouble(POSITION_PRICE_OPEN),_Digits),
                     " NLb_fun = ", NormalizeDouble(NLb_fun,_Digits));
               Modify = true;
 if(Modify)
              {
               Print(" серия рыночных позиций BUY назначена к переводу в безубыток, текущией позы POSITION_PRICE_OPEN = ",
               NormalizeDouble(PositionGetDouble(POSITION_PRICE_OPEN),_Digits)," тикет = ",PositionGetInteger(POSITION_TICKET));
                
               trade.PositionModify(_Symbol,SymbolInfoDouble(_Symbol, SYMBOL_BID) - 50*_Point,PositionGetDouble(POSITION_TP));
               Print(" Перенос в бу стоп лосса позиции Buy № ",  PositionGetInteger(POSITION_TICKET));
    ...
           } // к if(Modify)
        }    // к if(PositionGetInteger(POSITION_TYPE)==POSITION_TYPE_BUY) 

...

posso usar uma seção de código simples como enumeração de posições para uma rede de arrasto com posições de mercado HEDGE - obrigado.

o problema está resolvido! Parabéns mais uma vez a Vladimir Karputov!!!

com sua rede de arrasto!

https://www.mql5.com/ru/code/17263

o truque chave é olhar o índice no laço e modificá-lo com a opção ticket!!!

//--- при таком методе мы будет сюда попадать на каждом тике.
   for(int i=PositionsTotal()-1;i>=0;i--)
      if(m_position.SelectByIndex(i))
         if(m_position.Symbol()==Symbol() && m_position.Magic()==m_magic)
           {
            //--- TrailingStop -> подтягивание StopLoss у ПРИБЫЛЬНОЙ позиции
            if(m_position.PositionType()==POSITION_TYPE_BUY)
              {
               //--- когда у позиции ещё нет StopLoss
               if(m_position.StopLoss()==0)
                 {
                  //--- пока StopLoss равен 0.0, TrailingStep не учитываем
                  if(m_symbol.Bid()-ExtTrailingStop>m_position.PriceOpen())
                    {
                     //--- модификация позиции
                     m_trade.PositionModify(m_position.Ticket(),m_position.PriceOpen(),0.0);
                    }
                 } 
TrailingStop
TrailingStop
  • www.mql5.com
Пример советника с реализацией Trailing Stop.
 

Uma tarefa simples: você precisa bater todos os elementos do ArrayJ que são o mesmo índice e valor que os elementos do ArrayI:

int OnInit()
  {
   int CommonArray[]={1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 13, 13, 13, 13, 13, 13, 13};
   int ArrayI[20]=   {0, 0, 0, 0, 0, 0, 0, 8, 9, 10,  0, 12, 13, 13, 13, 13,  0,  0, 13,  0};
   int ArrayJ[];

   for(int j=0; j<ArraySize(ArrayI); j++)
   {
      ArrayResize(ArrayJ,j+1);
      ArrayJ[j]=CommonArray[j];
   }

   ArrayPrint(ArrayI);
   ArrayPrint(ArrayJ);

   for(int i=0; i<ArraySize(ArrayI); i++)
      if(ArrayI[i])
         for(int j=0; j<ArraySize(ArrayJ); j++)
            if(ArrayI[i]==ArrayJ[j])
               ArrayRemove(ArrayJ,j,1);

   ArrayPrint(ArrayJ);
//---
   return(INIT_SUCCEEDED);
  }

O fio condutor é destacado. Resultado:

2022.02.26 13:56:48.489 test (NZDUSD,H4)         0  0  0  0  0  0  0  8  9 10  0 12 13 13 13 13  0  0 13  0
2022.02.26 13:56:48.489 test (NZDUSD,H4)         1  2  3  4  5  6  7  8  9 10 11 12 13 13 13 13 13 13 13 13
2022.02.26 13:56:48.489 test (NZDUSD,H4)         1  2  3  4  5  6  7 11

Esperado:

2022.02.26 13:56:48.489 test (NZDUSD,H4)         0  0  0  0  0  0  0  8  9 10  0 12 13 13 13 13  0  0 13  0
2022.02.26 13:56:48.489 test (NZDUSD,H4)         1  2  3  4  5  6  7  8  9 10 11 12 13 13 13 13 13 13 13 13
2022.02.26 13:56:48.489 test (NZDUSD,H4)         1  2  3  4  5  6  7          11                13 13    13

O ArrayJ é dinâmico, parece haver algo de errado com ele. Mas eu também não preciso de um estático.

Partiu-me a cabeça. O QUE ESTÁ ACONTECENDO? Ou será este o equivalente da velha canção:

https://www.mql5.com/ru/forum/1111/page3141#comment_27152680

и

https://www.mql5.com/ru/forum/1111/page3142#comment_27371998

sobre constantes nomeadas?

Ошибки, баги, вопросы
Ошибки, баги, вопросы
  • 2022.01.28
  • www.mql5.com
Общее обсуждение: Ошибки, баги, вопросы
 
x572intraday elementos do ArrayI:

O fio condutor é destacado. Resultado:

Esperado:

O ArrayJ é dinâmico, parece haver algo de errado com ele. Mas eu também não preciso de um estático.

1. ArrayResize seria melhor sair do loop.

ArrayResize(ArrayJ,ArraySize(ArrayI));
for(int j=0; j<ArraySize(ArrayI); j++)
   {
      ArrayJ[j]=CommonArray[j];
   }

2. ArrayRemove não torna um elemento de matriz "vazio", ele "desloca" os elementos subseqüentes para seu lugar. Portanto, a correspondência de elementos em índices subseqüentes é quebrada.

 
JRandomTrader #:

1. ArrayResize deve ser movido para fora do loop

2. ArrayRemove não torna um elemento de matriz "vazio", mas "desloca" os elementos subseqüentes em seu lugar. Portanto, a correspondência de elementos em índices subseqüentes é quebrada.

Não há dúvidas sobre 2, eu apenas coloquei os intervalos lá para torná-lo mais claro. Além disso, no Help diz sobre uma matriz estática:"Se a função é usada para uma matriz de tamanho fixo, o tamanho da matriz em si não muda: a "cauda" restante é fisicamente copiada para a posição inicial. "O exemplo na Ajuda também usa uma matriz de tamanho fixo, e eu tenho uma dinâmica.

Re 1. Não podemos colocá-lo fora de um loop, pois em uma tarefa real não sabemos de antemão nem o tamanho do ArrayJ ou do ArrayI, muito menos o tamanho do CommonArray, já que todos eles não coincidem.

Tenho também um exemplo em que o embaralhamento de elementos não é interrompido pela metade, como no exemplo acima:

int OBJTFVArray[]={1, 2, 3, 4, 5, 6, 10, 12, 1520, 30, 16385, 16386, 16387, 16388, 16390, 16392, 16396, 16408, 32769, 49153, 49154, 49155, 49156, 49157, 49158, 49159, 49160};
int PArray[20]={0, 0, 0, 0, 0, 00, 16390, 16392, 163960, 32769, 49153, 49153, 49153, 49153, 0, 0, 49153, 0};
int PArray_[];

int OnInit()
  {
   for(int p_=0; p_<ArraySize(PArray); p_++)
   {
      ArrayResize(PArray_,p_+1);
      PArray_[p_]=OBJTFVArray[p_+8];
   }

   ArrayPrint(PArray);
   ArrayPrint(PArray_);

   for(int p=0; p<ArraySize(PArray); p++)
      if(PArray[p])
         for(int p_=0; p_<ArraySize(PArray_); p_++)
            if(PArray[p]==PArray_[p_])
               ArrayRemove(PArray_,p_,1);

   ArrayPrint(PArray_);

   return(INIT_SUCCEEDED);
  }

O resultado é bom:

 0     0     0     0     0     0     0 16390 16392 16396     0 32769 49153 49153 49153 49153     0     0 49153     0
15    20    30 16385 16386 16387 16388 16390 16392 16396 16408 32769 49153 49154 49155 49156 49157 49158 49159 49160
15    20    30 16385 16386 16387 16388                   16408             49154 49155 49156 49157 49158 49159 49160

Mas você precisa dessa variante para trabalhar. O engate aparentemente acontece se houver elementos com o mesmo valor (ver post anterior) na cauda à direita - o que é semelhante ao problema ao qual eu estava me referindo acima.

 
x572intraday #:

Não há perguntas sobre 2, eu coloco os intervalos para maior clareza. Além disso, no Help diz sobre a matriz estática:"Se a função é usada para uma matriz de tamanho fixo, o tamanho da matriz em si não muda: ela copia fisicamente a "cauda" restante para a posição inicial."O exemplo na Ajuda também usa uma matriz de tamanho fixo, e eu tenho uma dinâmica.

Re 1. Não podemos colocá-lo fora de um loop, pois em uma tarefa real não sabemos de antemão nem o tamanho do ArrayJ ou do ArrayI, muito menos o tamanho do CommonArray, já que todos eles não coincidem.

Tenho também um exemplo em que o despejo de elementos não quebra pela metade, como neste exemplo:

O resultado é bom:

Mas eu preciso dessa variante para trabalhar. O engate aparentemente acontece se houver elementos com o mesmo valor na cauda à direita (ver post anterior) - o que é semelhante ao problema a que me referi acima.

1. Você pode e deve tirá-lo do circuito, da maneira como eu mostrei. A menos que o tamanho do ArrayI mude ao longo do loop.

2. Então algo como isto

int k=0; // объявляем до цикла - чтобы использовать после
for(int i=0; i<ArraySize(ArrayI); i++) // после предыдущего кода (1) размеры ArrayI и ArrayJ равны
  if(ArrayI[i]!=ArrayJ[i])
    {
     ArrayJ[k++]=ArrayI[i];
    }
ArrayResize(ArrayJ,k);
 
E, de fato, é possível combinar os ciclos 1 e 2 copiando apenas elementos não correspondentes do ArrayI para o ArrayJ.