English Русский 中文 Español Deutsch 日本語 한국어 Français Italiano Türkçe
Criando um indicador de várias moedas utilizando um número de buffers indicadores intermediários

Criando um indicador de várias moedas utilizando um número de buffers indicadores intermediários

MetaTrader 5Indicadores | 22 janeiro 2014, 09:08
2 513 0
Alexey Klenov
Alexey Klenov

Introdução

Tudo começou quando ouvi pela primeira vez sobre indicadores de conjuntos do artigo Base teórica para a construção de indicadores em conjunto (cluster) para FOREX. Isso foi muito interessante para mim na época, e eu decidi escrever algo similar em termos de análise de múltiplos mercados. Primeiro, eu implementei minha própria versão do indicador, com o codinome MultiCurrencyIndex, no qual os valores calculados dos índices de moeda são usados para calcular as taxas de indicadores clássicos (RSI, MACD, CCI).

E agora vou dizer a você como transferi esse indicador para uma nova plataforma, MetaTrader 5 em complemento com MQL5, exceto que em vez de calcular o CCI, vou calcular o indicador estocástico (oscilador estocástico), que é mais prospectivo (em minha opinião).

Vamos começar com algumas definições.

índice do dólar - - valor duplo calculado pela fórmula, gentilmente fornecido a mim por Neutron.

A fórmula para calcular o índice USD,

onde há USD / YYY - todas as cotações diretas, como USD / CHF, XXX / USD - todas ao contrário, como EUR / USD.

Outros índices são calculados dos valores de pares de moedas correntes fechados, contendo USD.

Linhas principais - duas linhas do indicador, refletindo os dados calculados, relacionados diretamente ao gráfico atual. Por exemplo, no gráfico de EURUSD serão as linhas das moedas correntes EUR e USD.

Linhas suplementares - outras linhas indicadoras calculadas, não relacionadas ao gráfico atual. Por exemplo, para o mesmo gráfico de EURUSD, serão as linhas das moedas correntes GBP, CHF, JPY, CAD, AUD e NZD.

Fechamento - o valor do preço de fechamento da barra do cronograma atual (tipo duplo) para o par de moeda corrente necessário.

Vamos iniciar.

A definição do problema

Para começar nós precisamos definir o problema.

  1. Sincronize os gráficos dos pares de moedas correntes afetados desse cronograma.
  2. Ganhe acesso aos dados fechados dos sete pares de moedas correntes: EURUSD, GBPUSD, USDCHF, USDJPY, USDCAD, AUDUSD, NZDUSD, e coloque-os nos buffers do indicador, projetados para cálculos auxiliares.
  3. Baseado nos dados obtidos no item (2), calcule para a barra atual o índice do dólar.
  4. Sabendo o índice do dólar para a barra atual, calcule os índices das moedas correntes restantes.
  5. Realize cálculos de dados (itens 3 e 4) um número necessário de vezes para o comprimento selecionado do histórico.
  6. Dependendo do destino do indicador, calcule os valores de moeda corrente para cada um dos índices selecionados:
    • índice de força relativa (índice de forma relativa, RSI);
    • Médias móveis de convergência / divergência (média móvel de convergência / divergência, MACD);
    • Oscilador estocástico (oscilador estocástico);
    • No futuro, a lista pode ser suplementada.

Para isso precisaremos:

31 buffer do indicador:

  • 0-7 inclusivo - buffers para representar as linhas finais;
  • 8-14 inclusivo - buffers dos pares de moedas correntes principais, que contém USD;
  • 15-22 inclusivo - buffers dos índices das moedas correntes;
  • 23-30 inclusivo - buffers dos dados intermediários estocásticos pelo tipo fechado / fechado sem suavização.

Para selecionar o destino para um indicador, faremos um tipo enumerado enum :

enum Indicator_Type
  {
   Use_RSI_on_indexes             = 1, // RSI of the index  
   Use_MACD_on_indexes            = 2, // MACD from the index  
   Use_Stochastic_Main_on_indexes = 3  // Stochastic on the index
  };
A seguir, usando o comando input, na janela de preferências do indicador, derivamos para as seleções do usuário a partir desta lista
input Indicator_Type ind_type=Use_RSI_on_indexes;  // type of the indicator from the index

é possível fazer uma forma mais fácil para o usuário de exibir os nomes dos parâmetros de entrada na aba "entradas". Para fazer isso utilizamos propositalmente o comentário urgente, que deve ser posicionado após a descrição do parâmetro de entrada, na mesma fileira. Assim os parâmetros de entrada podem ser comparados a nomes mais compreensíveis para o usuário.

As mesmas regras se aplicam para os comando de listagem enum . Isto é se o nome mnemônico está associado a um comentário, como mostrado em nosso exemplo, em vez de nome mnemônico, os conteúdos desse comentário serão exibidos. . Isso fornece flexibilidade adicional para escrever programas com descrições claras dos parâmetros de entrada.

Os desenvolvedores tentaram fornecer ao usuário final meios convenientes de trabalhar com o programa MQL5, se certificando de que ele veja nomes compreensíveis dos parâmetros em vez do que está escrito no código. Mais informações podem ser encontradas aqui.

Figura 1. Selecionando o tipo do indicador

Figura 1. Selecionando o tipo do indicador

Fornecemos ao usuário uma escolha das moedas correntes necessárias para representar o indicador e sua cor:

input bool USD=true;
input bool EUR=true;
input bool GBP=true;
input bool JPY=true;
input bool CHF=true;
input bool CAD=true;
input bool AUD=true;
input bool NZD=true;

input color Color_USD = Green;            // USD line color
input color Color_EUR = DarkBlue;         // EUR line color
input color Color_GBP = Red;             // GBP line color
input color Color_CHF = Chocolate;        // CHF line color
input color Color_JPY = Maroon;           // JPY line color
input color Color_AUD = DarkOrange;       // AUD line color
input color Color_CAD = Purple;          // CAD line color
input color Color_NZD = Teal;            // NZD line color

Figura 2. Selecionando a cor das linhas do indicador

Figura 2. Selecionando a cor das linhas do indicador

Alguns outros parâmetros configuráveis

input string rem000        =  ""; // depending on the type of the indicator
input string rem0000       =  ""; // requires a value :
input int rsi_period       =   9; // period RSI
input int MACD_fast        =   5; // period MACD_fast
input int MACD_slow        =  34; // period MACD_slow
input int stoch_period_k   =   8; // period Stochastic %K
input int stoch_period_sma =   5; // period of smoothing for Stochastics %K
input int shiftbars        = 500; // number of bars for calculating the indicator

Figura 3. Parâmetros do indicador

Figura 3. Parâmetros do indicador

Um limite de 500 barras para o cálculo do indicador é artificial, mas é suficiente pata demonstrar o conceito do cálculo. Mas, devemos lembrar que cada buffer de indicador requer memória, e um display de tamanho variável muito grande (em milhões de barras) pode fazer com que o computador não tenha memória suficiente.

Buffers indicadores:

double  EURUSD[], // quotes
        GBPUSD[],
        USDCHF[],
        USDJPY[],
        AUDUSD[],
        USDCAD[],
        NZDUSD[];   
               
double    USDx[], // indexes
          EURx[],
          GBPx[],
          JPYx[],
          CHFx[],
          CADx[],
          AUDx[],
          NZDx[];
                         
double USDplot[], // results of currency lines
       EURplot[],
       GBPplot[],
       JPYplot[],
       CHFplot[],
       CADplot[],
       AUDplot[],
       NZDplot[]; 

double USDStoch[], // buffers of intermediate data schotastics by the close/close type without smoothing
       EURStoch[],
       GBPStoch[],
       JPYStoch[],
       CHFStoch[],
       CADStoch[],
       AUDStoch[],
       NZDStoch[];
Também precisaremos de algumas variáveis globais (nível indicador):
int              i,ii;
int           y_pos=0; // Y coordinate variable for the informatory objects  
datetime   arrTime[7]; // Array with the last known time of a zero valued bar (needed for synchronization)  
int        bars_tf[7]; // To check the number of available bars in different currency pairs  
int        countVal=0; // Number of executable Rates  
int           index=0;
datetime  tmp_time[1]; // Intermediate array for the time of the bar 

E agora chegamos a uma característica bastante extensa OnInit, usando o que distribuiremos, os buffers de indicador de acordo com seu propósito.

Já que os cálculos iniciais passam através do índice do dólar, então para USD simplesmente estabelecemos a possibilidade de desabilitar a representação dos buffers do indicador de moedas correntes.

Ela é assim:

if(USD)
  {
   countVal++;
   SetIndexBuffer(0,USDplot,INDICATOR_DATA);               // array for rendering
   PlotIndexSetString(0,PLOT_LABEL,"USDplot");              // name of the indicator line (when selected with a mouse)
   PlotIndexSetInteger(0,PLOT_DRAW_BEGIN,shiftbars);       // from which we begin rendering
   PlotIndexSetInteger(0,PLOT_DRAW_TYPE,DRAW_LINE);         // drawing style (line)
   PlotIndexSetInteger(0,PLOT_LINE_COLOR,Color_USD);       // color of line rendering
   if(StringFind(Symbol(),"USD",0)!=-1)
     {PlotIndexSetInteger(0,PLOT_LINE_WIDTH,wid_main);}    // if the symbol name contains USD 
                                                       // then draw a line of appropriate width 
   else
     {PlotIndexSetInteger(0,PLOT_LINE_STYLE,style_slave);}
   ArraySetAsSeries(USDplot,true);                       // indexation of array as a timeseries   
   ArrayInitialize(USDplot,EMPTY_VALUE);                  // zero values 
   f_draw("USD",Color_USD);                            // rendering in the indicator information window 
  }
SetIndexBuffer(15,USDx,INDICATOR_CALCULATIONS);            // array of dollar index for calculations
                                                      // (is not displayed in the indicator as a line) 
ArraySetAsSeries(USDx,true);                            // indexation of an array as a time series
ArrayInitialize(USDx,EMPTY_VALUE);                       // zero values

if(ind_type==Use_Stochastic_Main_on_indexes)
  {
   SetIndexBuffer(23,USDstoch,INDICATOR_CALCULATIONS);     // if the destination of the indicator as a Use_Stochastic_Main_on_indexes,
                                                           // then this intermediate array is needed
   ArraySetAsSeries(USDstoch,true);                        // indexation of array as a time series
   ArrayInitialize(USDstoch,EMPTY_VALUE);                  // zero values
  }
Para a moeda corrente EUR o código da função OnInit se parece com isso:
if(USD)
  {
   countVal++;
   SetIndexBuffer(0,USDplot,INDICATOR_DATA);              // array for rendering
   PlotIndexSetString(0,PLOT_LABEL,"USDplot");             // name of the indicator line (when selected with a mouse)
   PlotIndexSetInteger(0,PLOT_DRAW_BEGIN,shiftbars);       // from which we begin rendering
   PlotIndexSetInteger(0,PLOT_DRAW_TYPE,DRAW_LINE);         // drawing style (line)
   PlotIndexSetInteger(0,PLOT_LINE_COLOR,Color_USD);       // color of line rendering
   if(StringFind(Symbol(),"USD",0)!=-1)
     {PlotIndexSetInteger(0,PLOT_LINE_WIDTH,wid_main);}    // if the symbol name contains USD 
                                                       // then draw a line of appropriate width 
   else
     {PlotIndexSetInteger(0,PLOT_LINE_STYLE,style_slave);}
   ArraySetAsSeries(USDplot,true);                       // indexation of array as a timeseries
   ArrayInitialize(USDplot,EMPTY_VALUE);                  // zero values 
   f_draw("USD",Color_USD);                             // rendering in the indicator information window 
  }
SetIndexBuffer(15,USDx,INDICATOR_CALCULATIONS);             // array of dollar index for calculations
                                                       // (is not displayed in the indicator as a line) 
ArraySetAsSeries(USDx,true);                             // indexation of an array as a time series
ArrayInitialize(USDx,EMPTY_VALUE);                        // zero values

if(ind_type==Use_Stochastic_Main_on_indexes)
  {
   SetIndexBuffer(23,USDstoch,INDICATOR_CALCULATIONS);      // if the destination of the indicator as a Use_Stochastic_Main_on_indexes,
                                                       // then this intermediate array is needed
   ArraySetAsSeries(USDstoch,true);                      // indexation of array as a time series
   ArrayInitialize(USDstoch,EMPTY_VALUE);                 // zero values
  }

if(EUR)
  {
   countVal++;
   SetIndexBuffer(1,EURplot,INDICATOR_DATA);              // array for rendering
   PlotIndexSetString(1,PLOT_LABEL,"EURplot");             // name of the indicator line (when pointed to with a mouse)
   PlotIndexSetInteger(1,PLOT_DRAW_BEGIN,shiftbars);       // which we begin rendering from
   PlotIndexSetInteger(1,PLOT_DRAW_TYPE,DRAW_LINE);         // drawing style (lines)
   PlotIndexSetInteger(1,PLOT_LINE_COLOR,Color_EUR);       // the color of rendering lines
   if(StringFind(Symbol(),"EUR",0)!=-1)
     {PlotIndexSetInteger(1,PLOT_LINE_WIDTH,wid_main);}    // if the symbol name contains EUR
                                                       // then we draw a line of the appropriate width 
   else
     {PlotIndexSetInteger(1,PLOT_LINE_STYLE,style_slave);}  // if the symbol name does NOT contain EUR,
                                                       // then we draw a line of an appropriate style (on the crosses)
   ArraySetAsSeries(EURplot,true);                       // indexation of the array as a time series
   ArrayInitialize(EURplot,EMPTY_VALUE);                  // zero values
   SetIndexBuffer(8,EURUSD,INDICATOR_CALCULATIONS);        // data of Close currency pair EURUSD
   ArraySetAsSeries(EURUSD,true);                        // indexation of the array as a time series
   ArrayInitialize(EURUSD,EMPTY_VALUE);                   // zero values
   SetIndexBuffer(16,EURx,INDICATOR_CALCULATIONS);         // array of the EURO index for calculations
                                                      // (not displayed on the indicator as a line) 
   ArraySetAsSeries(EURx,true);
   ArrayInitialize(EURx,EMPTY_VALUE);
   if(ind_type==Use_Stochastic_Main_on_indexes)
     {
      SetIndexBuffer(24,EURstoch,INDICATOR_CALCULATIONS);   // if the indicator destination as a Use_Stochastic_Main_on_indexes,
                                                       // then this intermediate array is needed
      ArraySetAsSeries(EURstoch,true);                   // indexation of the array as a time series
      ArrayInitialize(EURstoch,EMPTY_VALUE);              // zero values
     }
   f_draw("EUR",Color_EUR);                            // rendering in the indicator information window
  }
Por analogia com EUR, o código parecerá similar para moedas como GBP, JPY, CHF, CAD, AUD e NZD, alternando os índices dos buffers do indicador. O código para essas moedas correntes pode ser encontrado no arquivo anexado do indicador.

Isso completa a descrição da inicialização do indicador.

Em seguida, precisaremos algumas características de usuário personalizadas:

  • O cálculo do RSI no buffer do usuário
  • Calculando a MACD
  • O cálculo do SMA no buffer do usuário
  • Calculando o fechamento estocástico / fechamento sem suavização
  • Representando objetos (informação)
  • Comentários na extremidade inferior direita do indicador (indicador de status)
  • Inicialização dos pares de moeda corrente TF afetados

Breve descrição de cada um desses:

  • O cálculo do RSI no buffer do usuário

Parâmetros de entrada:

double f_RSI(double &buf_in[], int period,int shift),

onde buf_in[] - arranjo do tipo duplo (como série temporal), período - período indicador do RSI, mudança - para qual barra do índice nós calculamos o indicador. Retorna um valor do tipo duplo.

  • Calculando a MACD

Parâmetros de entrada:

double f_MACD(double &buf_in[], int period_fast,int period_slow,int shift),

onde buf_in[] - arranjo do tipo duplo (como série temporal), period_fast - MA de período rápido, period_slow - MA de período lento, mudança - para qual barra do índice nós calculamos o indicador. Retorna um valor do tipo duplo.

  • Cálculo de SMA

Parâmetros de entrada:

double SimpleMA(const int position,const int period,const double &price[]),

onde posição - para qual barra do índice calculamos o indicador. período - período do indicador SMA, price[] - arranjo do tempo duplo (como série temporal). Retorna um valor do tipo duplo.

  • Calculando o fechamento estocástico / fechamento sem suavização

Parâmetros de entrada:

double f_Stoch(double &price[], int period_k, int shift),

onde price[] - arranjo do tipo duplo (como série temporal), period_fast - linha indicadora de K% do período, mudança - para qual barra do índice calculamos o indicador. Retorna um valor do tipo duplo.

  • Representação de objetos

Parâmetros de entrada:

int f_draw(string name, color _color)

onde nome - nome do objeto, _color - cor do objeto. A função é para propósitos normais. Começando da extremidade superior esquerda da janela de exibição e mais pra baixo, essa função exibe os nomes das moedas correntes afetadas. O texto da moeda corrente é da mesma cor que a linha indicadora, relacionada a essa moeda corrente.

  • Comentários estão na extremidade inferior direita do indicador

Parâmetros de entrada:

int f_comment(string text)

texto - O texto que precisa ser colocado na extremidade inferior direita do indicador. Um tipo de barra de condição do trabalho do indicador.

Finalmente, a função de conclusão e uma das mais importantes:

  • Inicialização dos pares de moeda corrente TF afetados

Sem parâmetros de entrada.

O histórico do MetaTrader é armazenado na forma de dados por minuto de TF para todas as ferramentas. Portanto, antes de iniciar o programa, todos os gráficos necessários (afetados) são construídos, baseados nos mesmos dados por minuto de TF, uma vez que o terminal está aberto. A construção também acontece quando o tráfico corrente TF está sendo alternado ou durante uma tentativa de acesso ao gráfico do TF através do código do programa MQL5.

Portanto:

  • Durante a primeira vez que o terminal é lançado, algum tempo é necessário para a construção do TF necessário (talvez até o plano de fundo, isto é o usuário não vê eles) dos pares de moedas correntes utilizados.
  • sincronize a barra zero para todas as moedas correntes afetadas, de forma a exibir com precisão o indicador. Em outras palavras, se há um novo gráfico ou ponto chegando, que abre uma nova barra (por exemplo, barra de hora), você precisará esperar pela chegada dos pontos para os outros pares de moedas correntes, que, por sua vez, abrirão uma nova barra (nova hora). Apenas então prossiga para o cálculo de um indicador para a barra nova.

A primeira parte dessa tarefa é implementada utilizando a função Bars integrada, que retorna o número de barras no histórico pelo período correspondente ao símbolo. é suficiente utilizar a versão dessa função, que é mostrada abaixo.

int  Bars(
   string          symbol_name,   // symbol name
   ENUM_TIMEFRAMES   timeframe    // period
   );

Na função especialmente anunciada para esse arranjo, coletamos o número das barras disponíveis para todos os pares de moedas correntes afetados. Verificamos cada valor para a quantidade minimamente necessária do histórico (a variável "número de barras para calcular o indicador" nos parâmetros do indicador). Se o número disponível de barras no histórico de qualquer instrumento é menor do que o valor dessa variável, então consideramos que a construção não foi bem sucedida, e examinamos novamente o número de dados disponíveis. Uma vez que há mais histórico disponível, para todos os pares de moeda corrente, do que pedido pelo usuário - então podemos considerar que essa parte da inicialização foi completada com sucesso.

A segunda parte da tarefa de sincronização é implementada utilizando a função CopyTime.

Em um arranjo especialmente criado para esse propósito, copiamos a abertura da barra zero de cada instrumento afetado. Se todos os elementos desse arranjo são o mesmo e não iguais a 0, vamos considerar que a nossa barra zero está sincronizada, e vamos começar o cálculo. Para compreender como isso é implementado em mais detalhes, veja o código do indicador anexado.

Isso termina a descrição das funções adicionais, e nós passamos para implementar a função OnCalculate. Uma vez que isso é um indicador de múltiplas moedas correntes, precisaremos da segunda versão do pedido dessa função.

int OnCalculate(const int     rates_total, // size of incoming time series
                const int prev_calculated, // processing of bars on the previous request
                const datetime&    time[], // Time
                const double&      open[], // Open
                const double&      high[], // High
                const double&       low[], // Low
                const double&     close[], // Close
                const long& tick_volume[], // Tick Volume
                const long&      volume[], // Real Volume
                const int&       spread[]  // Spread
   );

Determine a quantidade de barras, necessárias para o cálculo:

   int limit=shiftbars;

   if(prev_calculated>0)
     {limit=1;}
   else
     {limit=shiftbars;}

Sincronize gráficos de pares de moedas correntes:

   init_tf();

A seguir, utilizando a função CopyClose, copiamos os dados de fechamento dos pares de moeda corrente necessários, nos buffers indicadores, registrados especialmente para isso. (Para mais sobre acesso a dados de outro TF da ferramenta atual e / ou outra ferramenta, encontre em Ajuda )

Se, por qualquer razão, a função não copiou os dados e retornou uma resposta -1, então exibimos uma mensagem de erro do par de moedas correntes no comentário, e esperamos pela recepção de um novo ponto para o instrumento atual.

   if (EUR){copied=CopyClose("EURUSD",PERIOD_CURRENT,0,shiftbars,EURUSD); if (copied==-1){f_comment("Wait...EURUSD");return(0);}}
   if (GBP){copied=CopyClose("GBPUSD",PERIOD_CURRENT,0,shiftbars,GBPUSD); if (copied==-1){f_comment("Wait...GBPUSD");return(0);}}
   if (CHF){copied=CopyClose("USDCHF",PERIOD_CURRENT,0,shiftbars,USDCHF); if (copied==-1){f_comment("Wait...USDCHF");return(0);}}
   if (JPY){copied=CopyClose("USDJPY",PERIOD_CURRENT,0,shiftbars,USDJPY); if (copied==-1){f_comment("Wait...USDJPY");return(0);}}
   if (AUD){copied=CopyClose("AUDUSD",PERIOD_CURRENT,0,shiftbars,AUDUSD); if (copied==-1){f_comment("Wait...AUDUSD");return(0);}}
   if (CAD){copied=CopyClose("USDCAD",PERIOD_CURRENT,0,shiftbars,USDCAD); if (copied==-1){f_comment("Wait...USDCAD");return(0);}}
   if (NZD){copied=CopyClose("NZDUSD",PERIOD_CURRENT,0,shiftbars,NZDUSD); if (copied==-1){f_comment("Wait...NZDUSD");return(0);}}  

Em seguida no ciclo (de 0 ao limite) produzimos:

  • O cálculo do índice do dólar;
  • Cálculo dos índices de outras moedas com base em Fechar e o índice do dólar para a barra atual;
for (i=limit-1;i>=0;i--)
   {
      //calculation of USD index
      USDx[i]=1.0;
      if (EUR){USDx[i]+=EURUSD[i];}         
      if (GBP){USDx[i]+=GBPUSD[i];}
      if (CHF){USDx[i]+=1/USDCHF[i];}
      if (JPY){USDx[i]+=1/USDJPY[i];}
      if (CAD){USDx[i]+=1/USDCAD[i];}
      if (AUD){USDx[i]+=AUDUSD[i];}
      if (NZD){USDx[i]+=NZDUSD[i];}
      USDx[i]=1/USDx[i];
      //calculation of other currency values
      if (EUR){EURx[i]=EURUSD[i]*USDx[i];}
      if (GBP){GBPx[i]=GBPUSD[i]*USDx[i];}
      if (CHF){CHFx[i]=USDx[i]/USDCHF[i];}
      if (JPY){JPYx[i]=USDx[i]/USDJPY[i];}
      if (CAD){CADx[i]=USDx[i]/USDCAD[i];}
      if (AUD){AUDx[i]=AUDUSD[i]*USDx[i];}
      if (NZD){NZDx[i]=NZDUSD[i]*USDx[i];}
   }

Os dados são colocados em buffers de indicadores apropriados. Verifique que tipo de indicador foi selecionado pelo usuário durante a inicialização, e com base nisso, produza os cálculos relevantes.

Se há o desejo de olhar para o RSI dos índices demonstrados, então execute o código abaixo:

if (ind_type==Use_RSI_on_indexes)
   {
      if (limit>1){ii=limit - rsi_period - 1;}
      else{ii=limit - 1;}
      for(i=ii;i>=0;i--)
         {
            if (USD){USDplot[i]=f_RSI(USDx,rsi_period,i);}
            if (EUR){EURplot[i]=f_RSI(EURx,rsi_period,i);}
            if (GBP){GBPplot[i]=f_RSI(GBPx,rsi_period,i);}
            if (CHF){CHFplot[i]=f_RSI(CHFx,rsi_period,i);}
            if (JPY){JPYplot[i]=f_RSI(JPYx,rsi_period,i);}
            if (CAD){CADplot[i]=f_RSI(CADx,rsi_period,i);}
            if (AUD){AUDplot[i]=f_RSI(AUDx,rsi_period,i);}
            if (NZD){NZDplot[i]=f_RSI(NZDx,rsi_period,i);}                  
         }
   }  

Se quiséssemos ver o MACD pelos índices, então vamos aqui (mas até o momento é apenas implementado na base do SimpleMA, e será implementado posteriormente na base do EMA):

if (ind_type==Use_MACD_on_indexes)
   {
      if (limit>1){ii=limit - MACD_slow - 1;}
      else{ii=limit - 1;}
      for(i=ii;i>=0;i--)
         {
           if (USD){USDplot[i]=f_MACD(USDx,MACD_fast,MACD_slow,i);}
           if (EUR){EURplot[i]=f_MACD(EURx,MACD_fast,MACD_slow,i);}
           if (GBP){GBPplot[i]=f_MACD(GBPx,MACD_fast,MACD_slow,i);}
           if (CHF){CHFplot[i]=f_MACD(CHFx,MACD_fast,MACD_slow,i);}
           if (JPY){JPYplot[i]=f_MACD(JPYx,MACD_fast,MACD_slow,i);}
           if (CAD){CADplot[i]=f_MACD(CADx,MACD_fast,MACD_slow,i);}
           if (AUD){AUDplot[i]=f_MACD(AUDx,MACD_fast,MACD_slow,i);}
           if (NZD){NZDplot[i]=f_MACD(NZDx,MACD_fast,MACD_slow,i);}                  
         }
   } 

Se Estocástico, você deve primeiro calcular a linha% K e depois suavizá-la pelo método SimpleMA. A linha final suavizada deve ser exibida no gráfico.

if (ind_type==Use_Stochastic_Main_on_indexes)
   {
      if (limit>1){ii=limit - stoch_period_k - 1;}
      else{ii=limit - 1;}
      for(i=ii;i>=0;i--)
         {
           if (USD){USDstoch[i]=f_Stoch(USDx,rsi_period,i);}
           if (EUR){EURstoch[i]=f_stoch(EURx,stoch_period_k,i);}
           if (GBP){GBPstoch[i]=f_stoch(GBPx,stoch_period_k,i);}
           if (CHF){CHFstoch[i]=f_stoch(CHFx,stoch_period_k,i);}
           if (JPY){JPYstoch[i]=f_stoch(JPYx,stoch_period_k,i);}
           if (CAD){CADstoch[i]=f_stoch(CADx,stoch_period_k,i);}
           if (AUD){AUDstoch[i]=f_stoch(AUDx,stoch_period_k,i);}
           if (NZD){NZDstoch[i]=f_stoch(NZDx,stoch_period_k,i);}                  
         }
      if (limit>1){ii=limit - stoch_period_sma - 1;}
      else{ii=limit - 1;}
      for(i=ii;i>=0;i--)
         {
            if (USD){USDplot[i]=SimpleMA(i,stoch_period_sma,USDstoch);}
            if (EUR){EURplot[i]=SimpleMA(i,stoch_period_sma,EURstoch);}
            if (GBP){GBPplot[i]=SimpleMA(i,stoch_period_sma,GBPstoch);}
            if (CHF){CHFplot[i]=SimpleMA(i,stoch_period_sma,CHFstoch);}
            if (JPY){JPYplot[i]=SimpleMA(i,stoch_period_sma,JPYstoch);}
            if (CAD){CADplot[i]=SimpleMA(i,stoch_period_sma,CADstoch);}
            if (AUD){AUDplot[i]=SimpleMA(i,stoch_period_sma,AUDstoch);}
            if (NZD){NZDplot[i]=SimpleMA(i,stoch_period_sma,NZDstoch);}                  
          }                     
   }       

Isso completa o cálculo dos indicadores. Figuras 4-6 demonstram algumas figuras dos diferentes tipos de indicadores.

Figura 4. RSI ao lado dos índices

Figura 4. RSI ao lado dos índices

Figura 5. MACD ao lado dos índices das moedas correntes

Figura 5. MACD ao lado dos índices das moedas correntes

Figura 6. Estocástico ao lado dos índices das moedas correntes

Figura 6. Estocástico ao lado dos índices das moedas correntes

Conclusão

Enquanto implementando o indicador MultiCurrencyIndex , utilizei um número ilimitado de buffers de indicadores no MQL5, que simplificaram muito o código. Esse artigo é um exemplo de tal abordagem. Para dados confiáveis de um indicador, demonstrei um algoritmo de sincronização de diferentes instrumentos relativos à barra zero. Também demonstrei um dos possíveis algoritmos de acesso de dados dos outros instrumentos, relativo ao símbolo, ao qual o indicador está anexado.

Uma vez que o propósito do artigo foi demonstrar a possibilidade de trabalhar com uma grande quantidade de buffers de indicadores; a função acima de calcular os indicadores pelos arranjos de dados dos usuários, não foi a melhor forma de evitar sobrecarga do leitor. Mas foi suficiente para realizar os cálculos necessários.

Há muitas vantagens e desvantagens da análise de conjuntos do mercado Forex. Sistemas de negociação, baseados nessa abordagem, estão disponíveis gratuitamente, e há discussões sobre eles em vários fóruns, incluindo na Comunidade MQL4. Portanto, os princípios de negociação por esse indicador não são considerados nesse artigo.

Traduzido do russo pela MetaQuotes Ltd.
Artigo original: https://www.mql5.com/ru/articles/83

Arquivos anexados |
Um Administrador de ordem virtual para rastrear ordens dentro do ambiente MetaTrader 5 de posição centrada Um Administrador de ordem virtual para rastrear ordens dentro do ambiente MetaTrader 5 de posição centrada
Esta biblioteca de classe pode ser adicionada a um Expert Advisor do MetaTrader 5 para possibilitar que seja escrito com uma abordagem de ordem cêntrica amplamente similar ao MetaTrader 4, em comparação com a abordagem baseada em posição do MetaTrader 5. Ela faz isso mantendo um registro das ordens virtuais no cliente do terminal do MetaTrader 5, enquanto mantém uma parada de quebra protetora para cada posição para proteção contra desastres.
Migrando do MQL4 para o MQL5 Migrando do MQL4 para o MQL5
Este artigo é um guia rápido para as funções da linguagem MQL4, ele o ajudará a migrar seus programas do MQL4 para MQL5. Para cada função do MQL4 (exceto funções de negociação), são apresentadas a implementação do MQL5 e descrição, isso permite a redução do tempo de conversão significativamente. Para conveniência, as funções do MQL4 são divididas em grupos, similar à referência MQL4.
Um exemplo de um Sistema de Comércio Baseado no indicador Heiken-Ashi Um exemplo de um Sistema de Comércio Baseado no indicador Heiken-Ashi
Neste artigo veremos a questão de uso de um indicador Heiken-Ashi na negociação. Com base neste indicador, um simples sistema de negócio é considerado e um Expert Advisor MQL5 é escrito. As operações de negócio são implementadas nas bases de classes da biblioteca de classe padrão. São fornecidos neste artigo os resultados de teste da estratégia de negócio revisada que são baseados no histórico e obtidos usando o strategy tester do MetaTrader 5 embutido.
MetaTrader 5: A publicação de previsões comerciais e declarações de negociação ao vivo via e-mail em blogs, redes sociais e sites dedicados MetaTrader 5: A publicação de previsões comerciais e declarações de negociação ao vivo via e-mail em blogs, redes sociais e sites dedicados
Este artigo tem como objetivo apresentar as soluções prontas para as previsões de publicação usando o MetaTrader 5. Ele cobre uma gama de ideias: a partir do uso de sites dedicados à publicação das declarações do MetaTrader, através da criação de seu próprio site com praticamente nenhuma experiência em programação web necessária e, finalmente, a integração com um serviço de microblogging e rede social que permite que muitos leitores participem e sigam as previsões. Todas as soluções apresentadas aqui são 100% gratuitas e possíveis de instalar por qualquer pessoa com um conhecimento básico de e-mail e serviços FTP. Não existem obstáculos para usar as mesmas técnicas para hospedagem profissional e serviços de previsões de negociação comercial.