Perguntas de Iniciantes MQL5 MT5 MetaTrader 5 - página 64

 
Leser: Aconselhar como e onde especificar no EA o MA pertencente à janela nº 2. Por exemplo, acrescentei MA à IFM e quero registar este MA no meu EA. Não sei onde nem como o fazer.
Quer entrar em detalhes? O seu Consultor Especialista já está a utilizar o indicador MFI e quer que ele utilize o segundo indicador - o indicador MA? Ou, o seu consultor especializado não utiliza nenhum indicador e precisa dele para usar o indicador de MA?
 
Yedelkin:

1. Eu diria o seguinte: usar o código de outra pessoa com muito cuidado. Porque o código de outra pessoa significa também os erros de outra pessoa.

2. Aqui(https://www.mql5.com/ru/forum/6343/page64#comment_357008) sugeri que se tentasse zerar correctamente as variáveis antes de as utilizar. Mas o seu código ainda não implementou esta sugestão. Além disso, o seu código contém construções do seguinte tipo:

Como vê, nesta construção, as variáveis de pedido e resultado são zeradas não antes de serem utilizadas, mas depois de serem utilizadas. Além disso, quando estas variáveis locais são zeradas, a função deixa de funcionar, ou seja, essa zeragem em si não tem qualquer significado. Por outras palavras, uma tal construção é um bom exemplo de como as variáveis MqlTradeRequest e MqlTradeResult não devem ser zeradas. Portanto, se estiver ansioso, por favor, tente limpar correctamente as variáveis. Se algo correr mal, por favor, descreva em detalhes o que "não está a funcionar".

3. A Biblioteca Standard tem uma classe comercial"MQL5 Reference / Standard Library / Trade Classes / CTrade". Tente descobrir como aplicá-lo na prática. Na fase inicial de imersão na língua, esta classe pode ser bastante suficiente. Por exemplo, esta classe tem o seguinte método:"MQL5 Reference / Standard Library / Trade Classes / 2CTrade/ PositionModify". É implementado da seguinte forma:

A linha 'ClearStructures();' nela limpa a variável m_request antes de a utilizar.

Yedelkin,

Muito obrigado :)

Procurei-o e vi o meu erro.

Posso fazê-lo desta forma:

//+------------------------------------------------------------------+
//| Clear structures request,result and check_result                 |
//+------------------------------------------------------------------+
void ClearStructures()
  {
   MqlTradeRequest request;
   MqlTradeResult result;
   MqlTradeCheckResult check_result;
   ZeroMemory(request);
   ZeroMemory(result);
   ZeroMemory(check_result);
  } 

Mas gostei das vossas sugestões:

   MqlTradeRequest request={0};
   MqlTradeResult result={0};
Mesmo assim, os resultados são os mesmos.

Agora que a posição não foi encontrada, vou-me esforçar com esta tarefa.

Obrigado.

 

Yedelkin,

Estou a escrever-lhe porque está a responder adequadamente.

Tenho dois sors-MT4 e MT5.

Porque não funciona no MT5, eles são os mesmos.

Arquivos anexados:
MTB_1E.mq4  4 kb
MTB_E.mq5  9 kb
 
mario065: Dois sors-MT4 e MT5. Porque não funciona no MT5 - eles são o mesmo.

Infelizmente, não compreendo de todo o MT4. Darei uma vista de olhos e se apanhar alguma coisa, avisar-vos-ei.

Adenda. Em geral, esperará pela abertura do mercado e relatará o que exactamente deveria ter funcionado, mas não funcionou.

 
Yedelkin:

Infelizmente, não compreendo de todo o MT4. Darei uma vista de olhos e se apanhar alguma coisa, avisar-vos-ei.

Adenda. Em geral, espera-se até que o mercado abra e descreve-se o que deveria ter funcionado, mas não funcionou.

Por isso faço-o por mim e por quem, se necessário.

Aqui estão os comentários:

Se a indicação do bolshego zero para a modificação de duas yazikas (MT4 e MT5):

if(TradeTrailing>0)

if(MStop > 0)

Se estes pips (Bid - pips) bolshe abrir posishon:

if((NormalizeDouble(Bid, Digits)-TradeTrailing)>=OrderOpenPrice())

if(NormalizeDouble(Bid - MStop,4) >= Open)
Se stop = 0 ou Bid - pipsi dal trailing >= da definição Open Posishon + pips:
if(OrderStopLoss()==0 || (NormalizeDouble(Bid, Digits)-TradeTrailing)>=(OrderStopLoss()+0.0005))

if(SL == 0 || NormalizeDouble(Bid - MStop,4) >= NormalizeDouble(SL + MStop,4))

modificação:

ОrderModify(OrderTicket(),OrderOpenPrice(),NormalizeDouble(Bid, Digits)-TradeTrailing,OrderTakeProfit(),0,Blue);

ModifyPosition(Symbol(),NormalizeDouble(Bid - MStop,4),TP);

É isso mesmo.

Quero fazer uma função separada para a modificação.

 
Yedelkin:
Pode ser mais específico? O seu Consultor Especialista já está a utilizar o indicador MFI e agora precisa dele para utilizar o segundo indicador - o indicador MA? Ou, o seu Consultor Especialista não utiliza nenhum indicador, mas precisa dele para usar o indicador MA?
O meu Consultor Especialista utiliza IFM, mas não consigo perceber como escrever o indicador de Mestrado! A condição principal é a localização da MA. O MA não está no gráfico (janela 1), mas na janela com o indicador de IFM (janela 2).
 
Leser: O meu Consultor Especialista utiliza IFM, mas não consigo perceber como escrever o indicador de Mestrado! A condição principal é a localização do MA. O MA não está no gráfico (janela #1), mas na janela com o indicador MFI (janela #2).

Se o Consultor Especialista utilizar MFI, então o seu código deve conter uma linha com a obtenção do cabo deste indicador:"MQL5 Reference / Technical Indicators / iMFI". Assim sendo, o controlo do indicador da média móvel é descrito aqui:"MQL5 Reference Guide / Technical Indicators / iMA".

Tente também ler o artigo"Indicador por Indicador em MQL5".

 
mario065: Eis o comentário: Se um Bid-STOPS_LEVEL é mais do que zero para modificação: Se este Bid-STOPS é mais do que Posições Abertas: Se Stop = 0 ou Bid-STOPS está a seguir >= de Posições Abertas + definição de Pips: Modificação: É tudo. Gostaria de fazer uma função separada para modificação.

1. Infelizmente, ainda não especificou o que "não funciona". Declarou a lógica do programa (como deve funcionar), mas não declarou onde a lógica está quebrada e como está quebrada. Sem uma descrição detalhada do problema, só se pode fazer comentários sobre o código.

2. A função bool ModifyPosition(const string symbol,double StopLoss,double Takeprofit) contém tais linhas:

   if(!OrderSend(request,result) || result.deal==0)
     {
      Print("Modify error =", GetLastError());
      return(false);
     }

Se olhar para a descrição da estrutura MqlTradeResult, pode ver que o campo de negócio é descrito da seguinte forma

negócio

Bilhete de negócio, se um acordo tiver sido executado. É relatado durante uma operação comercial TRADE_ACTION_DEAL

Uma vez que a sua função ModifyPosition() realiza uma operação completamente diferente, o valor do resultado.deal deve ser sempre zero. Consequentemente, o operador
if(!OrderSend(request,result) || result.deal==0)

será sempre accionada, mesmo que a modificação tenha sido bem sucedida, e ao mesmo tempo imprimirá uma mensagem de erro.

2. Vejam-se as linhas do ponto 2 anterior. Utiliza a função GetLastError() que se destina a devolver o código do último erro. Mas não se limpa a variável que contém o código de erro antes de a utilizar, por isso, mesmo que a modificação seja bem sucedida, imprime-se um erro que pode ter ocorrido muito antes do pedido de modificação da posição ter sido enviado. Deveria ser algo do género:

ResetLastError();   
if(!OrderSend(request,result))
   { 
    ... 
    Print("Modify error =", GetLastError());
    ...
   }

3. Vejam estas linhas:

          if(SL == 0 || NormalizeDouble(Bid - MStop,4) >= SL) 
           {
            ModifyPosition(Symbol(),NormalizeDouble(Bid - MStop,4),TP);
           }

Suponha que no próximo tick a sua condiçãoNormalizeDouble(Bid - MStop,4) == SL desencadeado. Suponha que SL===1.11110. Mas depois também ModifyPosition(Symbol(),1.11110,TP). Ou seja, esta modificação especificará os níveis previamente estabelecidos.

E o que acontecerá, se a igualdade NormalizeDouble(Bid - MStop,4) == SL irá funcionar novamente no próximo tick?) Especialmente se considerarmos que (a) a normalização é realizada em quatro dígitos, quando pode haver cotações de cinco dígitos, (b) os pedidos de comércio podem ser executados no servidor com algum atraso.

4. Existe também uma propriedade de carácter como SYMBOL_TRADE_STOPS_LEVEL. Mas este nível não é verificado no seu código. Ou seja, se o candidato a uma nova paragem de perda para uma posição Buy for especificado como SL_new, seria útil verificar a condição se(Bid-STOPS_LEVEL>SL_new).

 

De facto, tente procurar no Manual de Referência para comparação de números reais. Tanto quanto me lembro, aconselha fortemente a não comparar dois números reais como este: if(double_1 == double_2).

 

Yedelkin,

Muito obrigado. Reshetov também me mostrou onde se encontra o erro.

Aqui está a própria função:

//+------------------------------------------------------------------+
//| Modify position.                                                 |
//+------------------------------------------------------------------+
bool ModifyPosition(const string symbol,double StopLoss,double Takeprofit){
//---- обявяване на структурата и резултата на търговското искане
   MqlTradeRequest request={0};
   MqlTradeResult result={0};
//---- структурна инициализация на  търговското искане MqlTradeRequest за модифициране на  позиция
   request.action       = TRADE_ACTION_SLTP;
   request.symbol       = symbol;
   request.sl           = StopLoss;
   request.tp           = Takeprofit;
   string word          = "";
   StringConcatenate(word,
                     "<<< ============ Modifyposition():   Модифицираме позицията  ",
                     symbol," ============ >>>");
   Print(word);
//---- модифицираме позицията и  проверяваме резултата от търговското искане
   if(!OrderSend(request,result))
     {
      Print("Modify error =", GetLastError());
      return(false);
     }
   return(true);
  }

Eis como eu deveria ter feito a função em si:

  double buy_trail = 0;
  double sel_trail = 0;
  double SL,TP,Open;
  if(PositionSelect(Symbol())){
    if(PositionGetInteger(POSITION_TYPE)==POSITION_TYPE_BUY)
      {
      Open = PositionGetDouble(POSITION_PRICE_OPEN);
      SL   = PositionGetDouble(POSITION_SL);
      TP   = PositionGetDouble(POSITION_TP);
      Bid  = SymbolInfoDouble(Symbol(),SYMBOL_BID);
      buy_trail = NormalizeDouble(Bid - Open,Digits());
      if(buy_trail > MStop)
       {
        if(NormalizeDouble((Bid - MStop),Digits()) >= Open && Open > SL)
          {
           ModifyPosition(Symbol(),Open,TP);
          }
          if(NormalizeDouble((Bid - MStop),Digits()) > SL && Open <= SL)
           {
            ModifyPosition(Symbol(),NormalizeDouble((SL + 0.001),Digits()),TP);
           }
        }
      }
    if(PositionGetInteger(POSITION_TYPE)==POSITION_TYPE_SELL)
      {
      Open = PositionGetDouble(POSITION_PRICE_OPEN);
      SL   = PositionGetDouble(POSITION_SL);
      TP   = PositionGetDouble(POSITION_TP);
      Ask  = SymbolInfoDouble(Symbol(),SYMBOL_ASK);
      sel_trail = NormalizeDouble(Open - Ask,Digits());
      if(sel_trail > MStop)
       { 
        if(NormalizeDouble((Ask + MStop),Digits()) <= Open && Open < SL)
          {
           ModifyPosition(Symbol(),Open,TP);
          }
          if(NormalizeDouble((Ask + MStop),Digits()) < SL && Open >= SL)
           {
            ModifyPosition(Symbol(),NormalizeDouble((SL - 0.001),Digits()),TP);
           }
        }
      }
     }

Agora está tudo a funcionar bem.

Obrigado.