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

 
Vladimir Karputov:

Allí:

Gracias. Estaré en el ordenador, quizá eche un vistazo.
 
Artyom Trishkin:
Gracias. Estaré en el ordenador, quizá eche un vistazo.

el indicador está escrito en un formato muy, muy antiguo en MQL4, no lo he tocado desde hace mucho tiempo, no estoy seguro de recordar cómo estaba escrito

@zig2003 como opción, intenta eliminar IndicatorBuffers(6) de start()

y en la parte superior fijar #property indicator_buffers 6

 
Igor Makanu, y después de arreglar el indicador, ¿qué tendré que comparar con lo que en el EA para programar una inversión?
Igor Makanu
Igor Makanu
  • www.mql5.com
Стал часто замечать у некоторых пользователей приаттаченные графики баланса из тестера стратегий. Я многое не понимаю, но видимо в этом есть смысл? Это религия? Или все таки работает примета деньги к деньгам... Появился интерес к изучению возможностей Python 3.7.2 Давно не занимался парсингом сайтов, ибо утомительное и неэффективное занятие...
 
zig2003:
Igor Makanu, y después de corregir el indicador ¿qué debo comparar en mi Asesor Experto para programar el pivote?

cada indicador se compone de varios topes de indicadores

cuando llamas al indicador desde el Asesor Experto a través de iCustom(), obtienes el valor de un buffer en una barra determinada, y puedes ver este valor en la ventana de datos Ctrl+D

lo que hay que comparar depende de su TS, ya sea los valores de los topes indicadores o el tope y el precio - hay muchas variantes

Primero debe crear un EA usando la MA, y luego, cuando entienda la MA, llamará a su indicador en lugar de la MA

no es tan fácil - sólo hay que escribir un par de comandos y su Asesor Experto está listo


ZS: un pivote del indicador es una comparación de varios valores de los búferes del indicador, a juzgar por su captura de pantalla en la barra número 2 se debe establecer cerca del precio del búfer número 1 y el resto de los búferes tendráValores EMPTY_VALUE, y en la barra №1, por el contrario, el búfer №1 tiene el valor EMPTY_VALUE , y uno de los 2 o 3 búferes tendrá el valor diferente de EMPTY_VALUE - debe mirarlo todo en la ventana de resumen de datos (mueva la flecha del ratón sobre las barras y verá los valores de los búferes)

 

Igor, gracias, he corregido el indicador, pero el valor del buffer seguía sin aparecer. Hace tiempo que pasé esa etapa, allí todo es sencillo, hay dos líneas - dos topes. Normalmente para indicadores similares, que consisten en una línea, pero con diferentes buffers para el color, escribo el código así:

//Функция для определения входа и выхода по AMA 
 int Enter()
  {
   double AMAbuy_1  =iCustom(NULL,_Period, "AMA", Range, FastMA,SlowMA,filter,normalizeDigits, 0,1);             //Подключаем AMA для первого бара (buy)
   double AMAsell_1 =iCustom(NULL,_Period, "AMA", Range, FastMA,SlowMA,filter,normalizeDigits, 1,1);             //                                (sell)
   double AMAbuy_2  =iCustom(NULL,_Period, "AMA", Range, FastMA,SlowMA,filter,normalizeDigits, 0,2);             //Подключаем AMA для второго бара (buy)       
   double AMAsell_2 =iCustom(NULL,_Period, "AMA", Range, FastMA,SlowMA,filter,normalizeDigits, 1,2);             //                                (sell)                    
                         
   if(AMAbuy_1>0 && AMAsell_2>0)                                                                                 //Вход в бай
      return(1);                                                                                           
   if(AMAsell_1>0 && AMAbuy_2>0)                                                                                 //Вход в селл
      return(-1);                                                                                          
        
   return(0);
  } 

Pero esto es sólo si se asigna un búfer real a cada color. Cuando se cambia de color en la primera barra cerrada, el valor del buffer pasa a ser mayor que cero, mientras que en la barra anterior era igual a cero o el buffer de otro color era mayor que cero. No puedo obtener el valor del segundo color de venta de este indicador y no sé con qué compararlo para captar la inversión. He probado con todos los números del buffer. Esto es lamentable, porque esta plataforma giratoria de Mladenov, aunque viejo, pero muy decente tendencia en las estrategias manuales.... ¿Puede alguien adivinar cómo tirar el valor de la segunda memoria intermedia y escribir la fórmula para la inversión?

 
zig2003:

Igor, gracias, he corregido el indicador, pero el valor del buffer seguía sin aparecer. Hace tiempo que pasé esa etapa, allí todo es sencillo, hay dos líneas - dos topes. Normalmente para indicadores similares, que consisten en una línea pero con diferentes buffers para el color, escribo el código de esta manera:

Pero esto es sólo si se asigna un búfer real a cada color. Cuando se cambia de color en la primera barra cerrada, el valor del buffer pasa a ser mayor que cero, mientras que en la barra anterior era igual a cero o el buffer de otro color era mayor que cero. No puedo obtener el valor del segundo color de este indicador y no puedo entender con qué compararlo para captar la inversión. Y esto es lamentable, porque este indicador de Mladenov, aunque viejo, pero muy bien la tendencia en manual strategics.... ¿Puede alguien averiguar cómo escribir la fórmula de inversión?

Sin ninguna edición de indicadores.

¿Qué significan los datos en los dos buffers - en 0 y 1:

  • Si hay un valor en el búfer 0 y ningún valor en el búfer 1, esta es la dirección para ir en largo ( línea indicadora azul (si es por defecto))
  • Si hay un valor en el búfer 0 y hay un valor en el búfer 1, se trata de una dirección corta (color rojo de la línea indicadora (si está predeterminada))

Cambio de dirección (color) de la línea:

  • Siempre hay un valor en el buffer 0 y, por cierto, siempre se puede definir (comparar valores en tres barras: 2<=1 && 1>0 --> abajo, 2>=1 && 1<0 --> arriba)
    ...
    Pero también puedes utilizar sólo el buffer 1:
  • Si no hay ningún valor en el buffer 1 en la barra 0 y hay un valor en la barra 1, se trata de un cambio de dirección de la línea a largo;
  • Si hay un valor en la barra 0 en el buffer 1 y ningún valor en la barra 1, esto es un cambio de dirección de la línea a corto;

"Sin valor" aquí es EMPTY_VALUE. O DBL_MAX - no importa, es lo mismo. Es decir, no es cero, sino EMPTY_VALUE.

 
zig2003:

¿Alguien puede adivinar cómo extraer el valor del segundo búfer y escribir la fórmula pivotante?

No tienes que adivinar, primero debes reescribir el indicador en una forma normal correspondiente al estado actual de MQL4

He ordenado un poco el código, pero no estoy seguro de que no haya errores. No me gusta el código fuente, pero he trabajado con lo que tengo.

#property indicator_chart_window
#property indicator_buffers 6
#property indicator_color1 clrDodgerBlue
#property indicator_color2 clrTomato
#property indicator_color3 clrTomato
#property indicator_width1 2
#property indicator_width2 2
#property indicator_width3 2
//----
input int    Range           = 9;
input int    FastMA          = 3;
input int    SlowMA          = 30;
input int    filter          = 25;
input int    normalizeDigits = 4;

input bool   alertsOn        = false;
input bool   alertsOnCurrent = false;
input bool   alertsMessage   = true;
input bool   alertsSound     = true;
input bool   alertsEmail     = false;
input string soundfile       = "alert2.wav";


double Downa[];
double Downb[];
double trend[];
double fAMA[];
double mAMA[];
double AMA[];
//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
int OnInit()
{
   SetIndexBuffer(0, fAMA);
   SetIndexLabel(0, "fAMA");
   SetIndexBuffer(1, Downa);
   SetIndexLabel(1, "Downa");
   SetIndexBuffer(2, Downb);
   SetIndexLabel(2, "Downb");
   SetIndexBuffer(3, trend);
   SetIndexLabel(3, "trend");
   SetIndexBuffer(4, mAMA);
   SetIndexLabel(4, "mAMA");
   SetIndexBuffer(5, AMA);
   SetIndexLabel(5, "AMA");
   for (int i=0; i<indicator_buffers; i++) {
      SetIndexStyle(i, DRAW_LINE);
   }
   return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
int OnCalculate (const int rates_total,      // размер входных таймсерий
                 const int prev_calculated,  // обработано баров на предыдущем вызове
                 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
                )
{
   int limit;
   if(prev_calculated==0) limit=rates_total-1;
   else limit=rates_total-prev_calculated+1;
   if (trend[limit] == -1) ClearPoint(limit, Downa, Downb);
   double k1 = 2.0 / (SlowMA + 1);
   double k2 = 2.0 / (FastMA + 1) - k1;
   for(int i = limit; i>= 0; i--) {
      double sdAMA = 0;
      double Noise = 0;
      for(int k=0; k<Range; k++) Noise += MathAbs(Close[i+k] - Close[i+k+1]);
      double ER    = 0;
      if(Noise != 0) ER = MathAbs(Close[i] - Close[i+Range]) / Noise;
      double SSC   = (ER*k2+k1);



      AMA[i]  = AMA[i+1] + NormalizeDouble(SSC*SSC*(Close[i] - AMA[i+1]), normalizeDigits);
      mAMA[i] = AMA[i];

      if(filter < 1) fAMA[i] = mAMA[i];
      else {
         for(k = i; k <= i + SlowMA - 1; k++)  sdAMA = sdAMA + MathAbs(mAMA[k] - mAMA[k+1]);
         double dAMA  = mAMA[i] - mAMA[i+1];
         if(dAMA >= 0)
            if(dAMA < NormalizeDouble(filter*sdAMA/(100*SlowMA), 4) &&  High[i] <= High[Highest(NULL, 0, MODE_HIGH, 4, i)]+10*Point)
               fAMA[i] = fAMA[i+1];
            else   fAMA[i] = mAMA[i];
         else if(MathAbs(dAMA) < NormalizeDouble(filter*sdAMA/(100*SlowMA), 4) && Low[i] > Low[Lowest(NULL, 0, MODE_LOW, 4, i)]-10*Point)
            fAMA[i] = fAMA[i+1];
         else  fAMA[i] = mAMA[i];
      }

      Downa[i] = EMPTY_VALUE;
      Downb[i] = EMPTY_VALUE;
      trend[i] = trend[i+1];
      if (fAMA[i]> fAMA[i+1]) trend[i] =1;
      if (fAMA[i]< fAMA[i+1]) trend[i] =-1;
      if (trend[i]==-1) PlotPoint(i, Downa, Downb, fAMA);
   }

//


   if (alertsOn) {
      if (alertsOnCurrent)
         int whichBar = 0;
      else     whichBar = 1;
      if (trend[whichBar] != trend[whichBar+1])
         if (trend[whichBar] == 1)
            doAlert("buy");
         else  doAlert("sell");
   }
   return(rates_total);
}
//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
void doAlert(string doWhat)
{
   static string   previousAlert="nothing";
   static datetime previousTime;
   string message;

   if (previousAlert != doWhat || previousTime != Time[0]) {
      previousAlert  = doWhat;
      previousTime   = Time[0];

      //
      //


      message =  StringConcatenate(Symbol(), " at ", TimeToStr(TimeLocal(), TIME_SECONDS), " AMA STL_Color ", doWhat);
      if (alertsMessage) Alert(message);
      if (alertsEmail)   SendMail(StringConcatenate(Symbol(), " AMA STL_Color "), message);
      if (alertsSound)   PlaySound(soundfile);
   }
}
//+------------------------------------------------------------------+
//|                                                                  |
//+------------------------------------------------------------------+
void ClearPoint(int i, double& first[], double& second[])
{
   if ((second[i]  != EMPTY_VALUE) && (second[i+1] != EMPTY_VALUE))
      second[i+1] = EMPTY_VALUE;
   else if ((first[i] != EMPTY_VALUE) && (first[i+1] != EMPTY_VALUE) && (first[i+2] == EMPTY_VALUE))
      first[i+1] = EMPTY_VALUE;
}
void PlotPoint(int i, double& first[], double& second[], double& from[])
{
   if (first[i+1] == EMPTY_VALUE)
      if (first[i+2] == EMPTY_VALUE) {
         first[i]  = from[i];
         first[i+1]  = from[i+1];
         second[i] = EMPTY_VALUE;
      }
      else  {
         second[i] = from[i];
         second[i+1] = from[i+1];
         first[i]  = EMPTY_VALUE;
      }
   else     {
      first[i]  = from[i];
      second[i]   = EMPTY_VALUE;
   }
}
//+------------------------------------------------------------------+

Aquí veo los valores de los buffers de este indicador:


 
Chicos, gracias por los consejos. EspecialmenteIgor Makanu. Sí, efectivamente, hice 6 buffers en lugar de los tres que vienen por defecto y los valores 1 y -1 aparecieron en uno de los buffers, pero no en los originales. Por eso no pude sacar los valores. Y yo nunca lo hubiera imaginado. Todo ha vuelto a la normalidad. Todo está funcionando. Igor, gracias también por la destilación del indicador en el nuevo formato. Gracias de nuevo por tus conocimientos!!!
Igor Makanu
Igor Makanu
  • www.mql5.com
Стал часто замечать у некоторых пользователей приаттаченные графики баланса из тестера стратегий. Я многое не понимаю, но видимо в этом есть смысл? Это религия? Или все таки работает примета деньги к деньгам... Появился интерес к изучению возможностей Python 3.7.2 Давно не занимался парсингом сайтов, ибо утомительное и неэффективное занятие...
 
Igor Makanu:

No hay que adivinar, primero hay que reescribir el indicador en una forma normal correspondiente al estado actual del lenguaje MQL4

He ordenado un poco el código, pero no estoy seguro de que no haya errores, no me gusta el código fuente, pero he trabajado con lo que tengo

Aquí veo los valores de los buffers de este indicador:

Funciona sin sobrescribir, y hace que sea muy fácil obtener sus datos. Lo he descrito más arriba - sólo tienes que mirar sus lecturas en el buffer en la ventana de datos (Ctrl+D)

 
Artyom Trishkin:

Funciona sin reescribir y permite recibir sus datos de forma muy sencilla. Lo he descrito más arriba - sólo tienes que mirar sus lecturas en el buffer en la ventana de datos (Ctrl+D)

Escribí arriba que no recuerdo cómo funciona la función IndicatorCounted() en los antiguos indicadores, la nueva forma de indicadores con OnCalculate() es más comprensible

Bueno, parece que el tema está resuelto, de acuerdo ;)

Razón de la queja: