Cualquier pregunta de los recién llegados sobre MQL4 y MQL5, ayuda y discusión sobre algoritmos y códigos - página 795

 
Alexey Viktorov:
Establece el color de la pantalla en clrNONE.

Entonces, ¿sólo se puede emitir el buffer, pero no la variable por separado?

 
psyman:

Entonces, ¿sólo se puede emitir el buffer, pero no la variable por separado?

Sí, es la única manera. Y un truco más que puede ser útil, si se establece SetIndexLabel(0, ""); entonces estos valores no se mostrarán en la ventana de datos. E incluso la función iCustom() no estará disponible.
 
Igor Makanu:

Gracias por responder.

Así que lo que entiendo es crear un buffer, y luego llenarlo con

con valores RSI y luego alimentar este buffer coniMAOnArray().

¿Alguien ha hecho esto para EA y se mostrará al probar EA en la subventana?

Normalmente las pruebas de EA a través de iCustom son lentas.

 

He tomado el código del ejemplo en https://www.mql5.com/ru/docs/strings/stringadd y lo he pegado en el script. El resultado es el mismo en MQL4 y MQL5:


HE      0       22:42:49.015    Test Script (EURUSD,H1) time for 'c = a + b' = 235 milliseconds, i = 1000000
OH      0       22:42:50.187    Test Script (EURUSD,H1) time for 'StringAdd(a,b)' = 1156 milliseconds, i = 1000000
EP      0       22:42:50.781    Test Script (EURUSD,H1) time for 'StringConcatenate(c,a,b)' = 594 milliseconds, i = 1000000


Pensé que StringAdd() y StringConcatenate() deberían funcionar más rápido que "+". ¿Por qué no es así?

 
Northwest:

iCustom suele ralentizar las pruebas del Asesor Experto.

no es cierto, por lo general es al revés, porque la asignación de memoria para los búferes de los indicadores se hace por el terminal, no por el script MQL, por lo general estos problemas son el problema de cálculo no óptimo en el indicador, muchos novatos en una llamada de indicador - tick, calcular toda la longitud de los datos históricos

Si has entendido los fundamentos de MQL, lee los artículos, está todo escrito.

https://www.mql5.com/ru/articles/4602


Noroeste:

¿Quién ha hecho esto para un EA y se mostrará al probar el EA en una subventana?

nadie lo ha hecho, lee cuál es la diferencia entre un EA y un indicador, quién tiene topes de indicadores y quién no, quién tiene funciones de trading y quién....

ZZY: una subventana sólo puede crear un indicador. Si crea una subventana, puede añadir objetos gráficos a esta subventana utilizando el Asesor Expertohttps://www.mql5.com/ru/docs/constants/objectconstants/enum_object

ZSYZZ: la subventana se puede obtener aplicando una plantilla, hubo un tema hace un par de meses, pero creo que tienes un problema con otras cosas hasta ahora

Как перенести расчетную часть любого индикатора в код эксперта
Как перенести расчетную часть любого индикатора в код эксперта
  • www.mql5.com
Когда программист создает советник, который получает сигналы от индикаторов, он всякий раз сталкивается с вопросом: использовать обращение к индикатору или перенести код индикатора в советник? Причины этому могут быть различные: желание сохранить в тайне используемые индикаторы и стратегию в целом, необходимость распространения советника единым...
 
Igor Makanu:

esto no es cierto, por lo general es al revés, porque la asignación de memoria para los búferes de los indicadores se hace por el terminal, no por el script MQL, por lo general estos problemas son el problema de cálculo no óptimo en el indicador, muchos novatos en una llamada de indicador - tick, que calcular toda la longitud de los datos históricos

Si ha entendido los fundamentos de MQL, lea los artículos, se ha escrito durante mucho tiempo.

https://www.mql5.com/ru/articles/4602


nadie lo ha hecho, lee cuál es la diferencia entre un Asesor Experto y un indicador, quién tiene topes de indicadores y quién no, quién tiene funciones de trading y quién ....

ZZY: una subventana sólo puede crear un indicador, si crea una subventana, entonces puede añadir objetos gráficos a esta subventana usando el Asesor Expertohttps://www.mql5.com/ru/docs/constants/objectconstants/enum_object

ZSYZZ: la subventana se puede obtener aplicando una plantilla, fue un tema de hace un par de meses, pero creo que tienes un problema con otra cosa hasta ahora

Lo siento. Tal vez no lo expresé bien, pero

No quiero usarlo para hacer pruebas, pero no quiero ejecutarlo.

En cuanto a la visualización en el gráfico del indicador durante las pruebas, si utiliza

Cuando se utilizan funciones de indicador incorporadas, éstas se dibujan en el gráfico en el proceso de prueba

Eso es exactamente lo que quiero decir.

Pero si usted utiliza algún tipo de código de cálculo de indicador personalizado que se integra en el código de EA, entonces este indicador

no se mostrará en el proceso de prueba del EA.

En cuanto a iCustom, cuando lo utilices en el proceso de pruebas el EA se mostrará en el gráfico

cualquier indicador y el código del indicador puede ser compilado con el EA en un ex4 pero no lo necesito.

Sólo quería saber si hay alguna forma de saltarse iCustom en este asunto, pero si no es así, tampoco es un problema.

Muchas gracias por la exhaustiva respuesta.

 

Artem publicó una plantilla de indicador aquí, aquí está la parte deOnCalculate

//--- Проверка количества доступных баров (1 - минимально, 4 - оптимально для большинства расчётов. Но всё "по месту"...)
   if(rates_total<4) return 0;
//--- Проверка и расчёт количества просчитываемых баров
   int limit=rates_total-prev_calculated; // 0 - пришел новый тик, новый бар формироваться не начал. 1 - пришел новый тик и начал формироваться новый бар.
   if(limit>1) 
               // если вписать "limit>0", то на нулевом баре будет расчёт только нулевого бара, на каждом новом баре будет полный перерасчёт всей истории
               // если вписать "limit>1", то на нулевом баре будет расчёт только нулевого бара, на открытии нового бара - пересчёт первого и нулевого,
               // при подгрузке истории и на первом запуске - перерасчёт всей истории
     {
      limit=rates_total-1;
      // здесь должна быть инициализация всех используемых буферов индикатора необходимыми значениями (обычно EMPTY_VALUE и 0)
     }

Lo estoy usando pero tengo una pregunta)

¿Por qué utilizolimit= rates_total-1 para el cálculo del historial completo ynolimit=rates_total?

 
psyman:

¿Por qué se utiliza limit=rates_total-1 para el cálculo del historial completo ynolimit=rates_total?

Intente comprobarlo, se encontrará inmediatamente "fuera de rango " - numeración de barras de cero a ... Total -1 , una situación común en la programación - la numeración comienza con 0. Como ejemplo obvio, declare el array double x[5] e intente escribir algo en el último elemento x[5] = 100;

ZS: respondiendo a la pregunta que aún no has hecho.... OrderTotal() también numera desde cero hasta OrderTotal()-1 ;)

 
Igor Makanu:

ZS: responder a una pregunta que aún no se ha formulado.... OrderTotal() también numera desde cero hasta OrderTotal()-1 ;)

La pregunta surgió por cierto, ahora no puedo ganar un promedio en la matriz, aunque sí en cinco, pero en qué tema escribir, no sé, que sea aquí.

El indicador calcula la diferencia apertura-cierre y construye МА sobre ella. He elegido MA=2 para la depuración pero usando SimpleMAOnBuffer y iMAOnArray obtengo desplazamientos de línea inexplicables y iMAOnArray muestra un valor cero en la última barra.


//+------------------------------------------------------------------+
//|                                                        _null.mq4 |
//|                        Copyright 2014, MetaQuotes Software Corp. |
//|                                              http://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2014, MetaQuotes Software Corp."
#property link      "http://www.mql5.com"
#property version   "1.00"
#property strict
#property indicator_separate_window
#include <MovingAverages.mqh>

#property indicator_buffers 4
#property indicator_plots   2
//--- plot OC
#property indicator_label1  "OC"
#property indicator_type1   DRAW_COLOR_HISTOGRAM
#property indicator_color1  clrSteelBlue, clrRed,clrGreen
#property indicator_style1  STYLE_SOLID
#property indicator_width1  1

#property indicator_label2  "MA1"
#property indicator_type2   DRAW_LINE
#property indicator_color2  clrBrown
#property indicator_style2  STYLE_SOLID
#property indicator_width2  1


//--- indicator buffers
double   OC[], OC_color[], MA1_buf[];
input int MA1=2;

int OnInit()
  {
  
   IndicatorSetString(INDICATOR_SHORTNAME,"t1");
   
   SetIndexBuffer(0,OC,INDICATOR_DATA);
   SetIndexBuffer(1,OC_color,INDICATOR_COLOR_INDEX);
   
   SetIndexBuffer(2, MA1_buf,INDICATOR_DATA); 
   //PlotIndexSetInteger(2,PLOT_DRAW_BEGIN,50);

     
//--- indicator buffers mapping

   
//---
   return(INIT_SUCCEEDED);
  }
//+------------------------------------------------------------------+
//| Custom indicator iteration function                              |
//+------------------------------------------------------------------+
int OnCalculate(const int rates_total,
                const int prev_calculated,
                const datetime &time[],
                const double &open[],
                const double &high[],
                const double &low[],
                const double &close[],
                const long &tick_volume[],
                const long &volume[],
                const int &spread[])
{

//--- Проверка количества доступных баров (1 - минимально, 4 - оптимально для большинства расчётов. Но всё "по месту"...)
   if(rates_total<4) return 0;
//--- Проверка и расчёт количества просчитываемых баров
   int limit=rates_total-prev_calculated; // 0 - пришел новый тик, новый бар формироваться не начал. 1 - пришел новый тик и начал формироваться новый бар.
   //if(limit>1) 
   
               // если вписать "limit>0", то на нулевом баре будет расчёт только нулевого бара, на каждом новом баре будет полный перерасчёт всей истории
               // если вписать "limit>1", то на нулевом баре будет расчёт только нулевого бара, на открытии нового бара - пересчёт первого и нулевого,
               // при подгрузке истории и на первом запуске - перерасчёт всей истории
     {
     limit=rates_total-1;
           // здесь должна быть инициализация всех используемых буферов индикатора необходимыми значениями (обычно EMPTY_VALUE и 0)
     }
   for(int i=limit; i>=0 && !IsStopped(); i--)
     {
      // необходимые действия по расчёту индикатора
     
     OC[i]=fmax(open[i],close[i])-fmin(open[i],close[i]);
     if(OC[i]>0.001)
      {   OC_color[i]=1;
      }
      }  
   
 /*  for(int k=limit; k>=0 && !IsStopped(); k--)
     {
   
     MA1_buf[k]=iMAOnArray(OC,0,MA1,k,MODE_SMA,0);
     }
*/
      SimpleMAOnBuffer(rates_total,prev_calculated,0,MA1,OC,MA1_buf);

//--- return value of prev_calculated for next call
   return(rates_total);
  }




double iMAOnArray(double &array[],
                      int total,
                      int period,
                      int ma_shift,
                      int ma_method,
                      int shift)
  {
   double buf[],arr[];
   if(total==0) total=ArraySize(array);
   if(total>0 && total<=period) return(0);
   if(shift>total-period-ma_shift) return(0);
   switch(ma_method)
     {
      case MODE_SMA :
        {
         total=ArrayCopy(arr,array,0,shift+ma_shift,period);
         if(ArrayResize(buf,total)<0) return(0);
         double sum=0;
         int    i,pos=total-1;
         for(i=1;i<period;i++,pos--)
            sum+=arr[pos];
         while(pos>=0)
           {
            sum+=arr[pos];
            buf[pos]=sum/period;
            sum-=arr[pos+period-1];
            pos--;
           }
         return(buf[0]);
        }
      case MODE_EMA :
        {
         if(ArrayResize(buf,total)<0) return(0);
         double pr=2.0/(period+1);
         int    pos=total-2;
         while(pos>=0)
           {
            if(pos==total-2) buf[pos+1]=array[pos+1];
            buf[pos]=array[pos]*pr+buf[pos+1]*(1-pr);
            pos--;
           }
         return(buf[shift+ma_shift]);
        }
      case MODE_SMMA :
        {
         if(ArrayResize(buf,total)<0) return(0);
         double sum=0;
         int    i,k,pos;
         pos=total-period;
         while(pos>=0)
           {
            if(pos==total-period)
              {
               for(i=0,k=pos;i<period;i++,k++)
                 {
                  sum+=array[k];
                  buf[k]=0;
                 }
              }
            else sum=buf[pos+1]*(period-1)+array[pos];
            buf[pos]=sum/period;
            pos--;
           }
         return(buf[shift+ma_shift]);
        }
      case MODE_LWMA :
        {
         if(ArrayResize(buf,total)<0) return(0);
         double sum=0.0,lsum=0.0;
         double price;
         int    i,weight=0,pos=total-1;
         for(i=1;i<=period;i++,pos--)
           {
            price=array[pos];
            sum+=price*i;
            lsum+=price;
            weight+=i;
           }
         pos++;
         i=pos+period;
         while(pos>=0)
           {
            buf[pos]=sum/weight;
            if(pos==0) break;
            pos--;
            i--;
            price=array[pos];
            sum=sum-lsum+price*period;
            lsum-=array[i];
            lsum+=price;
           }
         return(buf[shift+ma_shift]);
        }
      default: return(0);
     }
   return(0);
  }
 
psyman:

Tengo una pregunta relacionada, sigo luchando con el promedio de arrays, aunque lo estoy haciendo en el 5, pero no sé en qué tema escribirlo, que sea aquí.

Tengo la sensación de que en MQL5 los buffers de los indicadores y las series temporales se "desdoblan" de forma inversa, por defecto la barra más a la izquierda en MT5 es la barra 0 y en MT4 la barra más a la derecha es la barra 0 y los buffers de los indicadores tienen la misma numeración

ZS: por desgracia, no quiero meterme con MT5, MT4 me basta para comprobar mis ideas, sólo miro preparaciones en MT5, si escribo algo usando MT5 nunca se lo enseño a nadie )))