Descargar MetaTrader 5

Modificación en dos etapas de posiciones abiertas

13 abril 2016, 09:54
Genkov
0
204
  if(OrderStopLoss()>=OrderOpenPrice()) // StopLoss is on a lossless level
   {    // calculate correction coefficient
    double Coeff_up = NormalizeDouble((Bid-OrderOpenPrice())*0.382,Digits);
    // and if the differnece between the current and the open price of the position is greater than corr. coefficient 
    if(Bid-OrderOpenPrice()>Coeff_up) 
     {    // calculate the value of new StopLoss with the margin of 2 points
      double New_S_Loss = Bid-Coeff_up-2*Point;
      // and if the value of new StopLoss is higer than the current one
      if(New_S_Loss-OrderStopLoss()>3*Point)
       {     // move S/L and T/P
        OrderModify(OrderTicket(),OrderOpenPrice(),
        New_S_Loss,OrderTakeProfit()+Step*Point,0,Yellow);
        }
//        Print(" Bid-OrderOpenPrice()= ",Bid-OrderOpenPrice());
//        Print("  2   Coeff_up= ",Coeff_up," Order_S_Los= ",New_S_Loss," Bid= ",Bid);
       return;
       }
      }
     }

Introducción

El artículo llamado "Método de T.DeMark para el análisis técnico" contiene los coeficientes recomendados para la longitud de corrección, en particular 0.382 y 0.618. El uso de estos coeficientes durante la apertura de posiciones nos permite evitar las situaciones innecesarias de cierre y reapertura de posiciones en situaciones cercanas a la tendencia. La función funciona bien, especialmente cuando se produce una situación de divergencia.

Este método, siempre que se reinicie el valor del beneficio, ayuda a detectar la aparición de una tendencia "favorable". Por ejemplo, como se muestra en la Fig. 1 y comparada con la Fig. 2.




Algoritmo de la función

La primera modificación de la orden se realiza por el valor especificado TrailingStop, las posteriores establecen StopLoss más pequeñas que el nivel de corrección posible en 1 o 2 puntos (en este caso el coeficiente de corrección = 0,382 "Coeff_"). Incrementar el valor de TakeProfit en cada paso en, por ejemplo, la mitad del valor de TrailingStop (puede elegir también cualquier otro valor). El valor de TakeProfit también puede cambiarse. Para ello, debe establecerse el valor cero de March = 0 doble externo del operador al comienzo del programa.

Sería más inteligente para los traders que prefieren el análisis y soporte de la dirección de acciones específicas del programa que se realizara directamente durante el trading para transferir la variable MagicNumber al propio código del asesor experto donde la posición es abierta. Puede leer más información en detalle sobre la ayuda sobre la dirección específica en el libro de S. Kovalyov publicado en el sitio web de MQL4.com.


Vamos a analizar el código recomendado de la función prospectiva en el asesor experto y los comentarios en detalle:

//+------------------------------------------------------------------+
//|      Two-stage variant of TrailingStop       Modify_2step v5.mq4 |
//|   Orders modification: re-placing StopLoss and TakeProfit        |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2008, GenKov"
#property link      Genkov@bk.ru
//+------------------------------------------------------------------+

/* Magic=N

Magic=N - Este operador debe insertarse durante la apertura de la posición justo después del operador de control del cumplimiento de la condición en el propio programa (asesor experto) y en la función. No puede crear un modificador universal, puede que debido a que el mercado no es predecible, según me parece a mí, por lo que la función de seguimiento (movimiento de S/L y T/P) y las condiciones de cierre de la posición deben escribirse para cada tipo de condición de apertura de la posición (en Magic=N).

extern double    March         =  1;  // step of increasing TakeProfit 
                                      // step 0 doesn't increase T/P.

S/L debe ser inferior a TrailingStop en un punto para llevar S/L a un nivel seguro en la primera activación. De esta manera, nos aseguramos frente a posibles pérdidas (gestión del capital).

extern double    StopLoss      = 15;  
extern double    TrailingStop  = 16;  
extern double    TakeProfit    = 60;  // fitting with the tester
//+------------------------------------------------------------------+
//void TrailingStop()
  int start()                                   
   {
   //----------------------------------------------------------------+
   int point  = MarketInfo(Symbol(),MODE_POINT);      // Point size 
   int StopLev= MarketInfo(Symbol(),MODE_STOPLEVEL);  
   double half_Trail = MathRound(TrailingStop/2);//half TrailingStop
   double Step = March*half_Trail;  //value of TakeProfit increase
  if (TrailingStop<0) return;
   { 
   for (int i=0; i<OrdersTotal(); i++)
    {
    if (OrderSelect(i,SELECT_BY_POS,MODE_TRADES)==false) break;
    if (OrderSymbol()!=Symbol() || OrderMagicNumber()!=Magic) continue;
    if (OrderType()==OP_BUY)
     {

Primera etapa de la modificación de la posición BUY

if(OrderStopLoss()<OrderOpenPrice())//if S/L is less than the order open price
      {   // and if the difference between the current price and the position opening price is greater than T/S
      if(Bid-OrderOpenPrice()>TrailingStop*Point) // && 
       {     // and if OrderStopLoss() is less than the difference between the current price and T/S
       if(OrderStopLoss()<Bid-TrailingStop*Point)
        {    // calculate new T/P value
        double Now_T_P=(OrderTakeProfit()+Step*Point);
       { 
       OrderModify(OrderTicket(),OrderOpenPrice(),
       OrderStopLoss()+TrailingStop*Point,
       OrderTakeProfit()+Step*Point,0,Aqua); // increasing T/P value
      return;
      }
     }
    }
   }

No obstante, puede producirse la siguiente situación: el cambio de TakeProfir se hace 2-3 puntos superior que el nivel de beneficio previsto anteriormente y las paradas y los inicios disminuyen lentamente.



Para evitar perder beneficios, vamos a introducir el operador de control de la situación que cerrará la orden en el nivel de beneficio previsto. Si el precio sigue creciendo, el cambio de StopLoss y TakeProfit continuará.

if(Bid-OrderOpenPrice()>=TakeProfit*Point && (Pr_Op_1-Pr_Op_0)>2*Point) 
   {
    // Print(" Bid= ",Bid," >= ",OrderTakeProfit()," Magic= ",Magic);
    OrderClose(OrderTicket(),Lots,Bid,2,Red);
    }

// Second stage of BUY position modification

El método de la posición corta es el mismo que el descrito anteriormente, por lo que hay menos comentarios.

// ---------------------------- 1 stage of modification -----SELL-------------&
   else  if(OrderType()==OP_SELL) 
    {
   if(OrderStopLoss()>OrderOpenPrice())//if S/L is greater than order open price
     {
     if(OrderOpenPrice()-Ask>TrailingStop*Point && 
        OrderStopLoss()>Ask+TrailingStop*Point)
     { 
      OrderModify(OrderTicket(),OrderOpenPrice(),
      Ask+TrailingStop*Point,OrderTakeProfit()-Step*Point,0,SkyBlue);
      return;
      }
     }
if(OrderOpenPrice()-Ask>=TakeProfit*Point && (Pr_Op_0-Pr_Op_1)>2*Point) 
   {
    OrderClose(OrderTicket(),Lots,Bid,2,Red);
    }     
// ---------------------------- 2 stage of modification -----SELL-------------&
   if(OrderStopLoss()<=OrderOpenPrice()) // StopLoss is on a lossless level
    { // calculate correction coefficient
     double Coeff_down = NormalizeDouble((OrderOpenPrice()-Ask)*0.382,Digits);
     // and if the difference between the price of position opening and the current price is greater than corr. coefficient 
    if(OrderOpenPrice()-Ask>Coeff_down) 
     {    // calculate the value of new StopLoss with the margin of 2 points
      New_S_Loss = Ask+Coeff_down+2*Point; 
      // and if the value of new StopLoss is less than the current value
      if(New_S_Loss-OrderStopLoss()>3*Point)
       {     // move S/L and T/P   
       OrderModify(OrderTicket(),OrderOpenPrice(),
       New_S_Loss,OrderTakeProfit()-Step*Point,0,Khaki);
      return;
      }
     }
    }
   }
  } 
 //  -----------------------------------------------------------------------------------

Para convertir este asesor experto en una función, es necesrio comentar la función especial int start() ubicada al comienzo del programa y sustituirla por una descripción sin comentario de la función TrailingStop() situada al comienzo del programa. Llamada de la función sin comentario:

//TrailingStop();

al final del programa.

Si añadimos el bloque representado a continuación podemos comprobar la eficiencia de la función usándola como un asesor experto en el probador.

// --------------------------------------------------------------------------------
  
   double Macd_m15_0= iMACD(NULL,PERIOD_M15,12,26,9,PRICE_CLOSE,MODE_MAIN,0);
   double Macd_m15_1= iMACD(NULL,PERIOD_M15,12,26,9,PRICE_CLOSE,MODE_MAIN,1);
   
   if(OrdersTotal()<2)
    {
    if(Macd_m15_0<Macd_m15_1)
     {
     OrderSend(Symbol(),OP_SELL,0.1,Bid,3,Ask+StopLoss*Point,Bid-TakeProfit*Point,"",Magic,0,Red);
     }
    if(Macd_m15_0>Macd_m15_1)
     {
     OrderSend(Symbol(),OP_BUY,0.1,Ask,3,Bid-StopLoss*Point,Ask+TakeProfit*Point,"",Magic,0,Blue);
     }
    return(0);
   }
// --------------------------------------------------------------------------------
//  TrailingStop();
  }
   return(0);
  }
// --- end --- &

Ahora eliminamos los comentarios detallados del texto del código mencionado anteriormente y lo formamos como una función de ejecución: obtendremos el archivo ejecutable que se recomienda guardar en el directorio terminal_folder\experts\include con la extensión .mqh o en el directorio terminal_folder\libraries con la extensión mq4.



//+------------------------------------------------------------------+
//|                                             Modify_2_Step v5.mq4 |
//|                                         Copyright © 2008, GenKov |
//|                                                     Genkov@bk.ru |
//+------------------------------------------------------------------+
#property copyright "Copyright © 2008, GenKov"
#property link      "Genkov@bk.ru"
extern double    March         =  1;  // the step of TakeProfit increase
                                      // "0" step doesn't increase T/P.
// S/L must be less than TrailingStop by 1 point to bring the S/L  
// on a safe level in the time of the very first triggering
extern double    StopLoss      = 15;  
extern double    TrailingStop  = 16;
extern double Lots             = 0.1;  
extern double    TakeProfit    = 60;  // fitting with the tester
void TrailingStop()
  {
   int Magic=3090;  //  number of condition that opens position
   int point  = MarketInfo(Symbol(),MODE_POINT);      // Point size 
   int StopLev= MarketInfo(Symbol(),MODE_STOPLEVEL);  
   double half_Trail = MathRound(TrailingStop/2);//half TrailingStop
   double Step = March*half_Trail;  //TakeProfit-а increase size
  if (TrailingStop<0) return;
   { 
   for (int i=0; i<OrdersTotal(); i++)
    {//1 +cycle by orders search
    if (OrderSelect(i,SELECT_BY_POS,MODE_TRADES)==false) break;
    if (OrderSymbol()!=Symbol() || OrderMagicNumber()!=Magic) continue;
    if (OrderType()==OP_BUY)
     {
// --------------------------- 1 stage of modification -----BUY-------------&     
    if(OrderStopLoss()<OrderOpenPrice())//if the S/L is less than the order open price
      {   // and if the difference between the current and the open price is greater than T/S
      if(Bid-OrderOpenPrice()>TrailingStop*Point) // && 
       {     // and if OrderStopLoss() is less than the difference between current price andT/S
       if(OrderStopLoss()<Bid-TrailingStop*Point)
        {    // calculate new T/P value
        double Now_T_P=(OrderTakeProfit()+Step*Point);
       { 
       OrderModify(OrderTicket(),OrderOpenPrice(),
       OrderStopLoss()+TrailingStop*Point,
       OrderTakeProfit()+Step*Point,0,Aqua); // increase T/P value
      return;
      }
     }
    }
   }
  if(Bid-OrderOpenPrice()>=TakeProfit*Point) 
   {
    OrderClose(OrderTicket(),Lots,Bid,2,Red);
    }
//------------------------- 2 stage of modification -----BUY---------------&
  if(OrderStopLoss()>=OrderOpenPrice()) // StopLoss is on the lossless level
   {    // calculate correction coefficient
    double Coeff_up = NormalizeDouble((Bid-OrderOpenPrice())*0.382,Digits);
    // and if the difference between the current and the position price is greater than correction coefficient
    if(Bid-OrderOpenPrice()>Coeff_up) 
     {    // clculate new StopLoss value with the margin of 6 points
      double New_S_Loss = Bid-Coeff_up-6*Point-StopLev*Point;
      // if the value of new StopLoss is greater than the current value
      if((New_S_Loss-OrderStopLoss())<2*Point)
       {     // move S/L and T/P
        OrderModify(OrderTicket(),OrderOpenPrice(),
        OrderStopLoss(),OrderTakeProfit()+Step*Point/2,0,Yellow);
        }
        else
        {
         OrderModify(OrderTicket(),OrderOpenPrice(),
        New_S_Loss+1*Point,OrderTakeProfit()+Step*Point,0,Yellow);
        }
       return;
       }
      }
     }
// ---------------------------- 1 stage of modification -----SELL-------------&
  else if(OrderType()==OP_SELL)
    {
   if(OrderStopLoss()>OrderOpenPrice())//if S/L is greater than the order open price
     {
     if(OrderOpenPrice()-Ask>TrailingStop*Point && 
        OrderStopLoss()>Ask+TrailingStop*Point)
     { 
      OrderModify(OrderTicket(),OrderOpenPrice(),
      Ask+TrailingStop*Point,OrderTakeProfit()-Step*Point,0,SkyBlue);
      return;
      }
     }
if(OrderOpenPrice()-Ask>=TakeProfit*Point) 
   {
    OrderClose(OrderTicket(),Lots,Bid,2,Red);
    }     
// ---------------------------- 2 stage of modification -----SELL-------------&
   if(OrderStopLoss()<=OrderOpenPrice()) // StopLoss is on the lossless level
    if(OrderOpenPrice()-Ask>=OrderTakeProfit()) OrderClose(OrderTicket(),Lots,Ask,2,Red);   
    { // calculate correction coefficient
     double Coeff_down = NormalizeDouble((OrderOpenPrice()-Ask)*0.382,Digits);
     // and if the difference between the position open price and the current price is greater than corr. coefficient
    if(OrderOpenPrice()-Ask>Coeff_down) 
     {   // calculate the value of new StopLoss with the margin of 6 points
      New_S_Loss = Ask+Coeff_down+6*Point; 
      // and if the value of new StopLoss is less than the current value
      if((OrderStopLoss()-New_S_Loss-StopLev*Point)>=10*Point)
       {    // move S/L and T/P
       OrderModify(OrderTicket(),OrderOpenPrice(),
       New_S_Loss-5*Point,OrderTakeProfit()-Step*Point,0,Khaki);
      return;
      }
     }
    }
   }
  } 
return(0);
}
}
// ---end----- void TrailingStop()--------------------------------&
  // this block is only for error controlling in the function code
  //  int start()  
  //   {
  //    if(25>26) TrailingStop();
  //    }
  // --------------------------------


Conclusión

Debe decirse que, en comparación con la "ejemplar trailing-stop" descrita en el artículo "Una plantilla Trailing Stop y de salida del mercado" de Sergey Kravchuk, la versión recomendada es más fácil de comprender y ahora ha funcionado en mi asesor experto (a decir verdad, en una cuenta demostración) y, creo, que se ajusta al trailing agresivo y moderado.

Las versiones adjuntas:

v4 - con cierre de S/L; v5 - con cierre previsto de T/P; v6 - con una mirada en la ayuda a la predicción y dirección por el número mágico.



Traducción del ruso hecha por MetaQuotes Software Corp.
Artículo original: https://www.mql5.com/ru/articles/1529

Archivos adjuntos |
Una plantilla para una orden trailing stop y de salida del mercado Una plantilla para una orden trailing stop y de salida del mercado

Los desarrolladores de algoritmos de modificación/cierre sufren un infortunio perenne: ¿cómo comparar los resultados obtenidos por distintos métodos? El mecanismo de comprobación es bien conocido: el probador de estrategias. Pero ¿cómo realizar un asesor experto que funcione igualmente para las órdenes de apertura y cierre? El artículo describe una herramienta que proporciona una sólida repetición de aperturas de órdenes que nos permite mantener una plataforma matemáticamente correcta para comparar los resultados de algoritmos distintos para órdenes trailing stop y de salida del mercado.

Falacias, Parte 1: La gestión del dinero es secundario y no muy importante Falacias, Parte 1: La gestión del dinero es secundario y no muy importante

La primera demostración de los resultados de las pruebas de una estrategia basada en el lote 0,1 se está convirtiendo en un estándar de facto en el foro. Habiendo recibido un "no tan mal" de los profesionales, un principiante ve que la prueba "0,1" consigue resultados muy modestos y decide introducir una gestión del dinero agresiva pensando que la esperanza matemática positiva proporciona resultados positivos automáticamente. Veamos qué resultados pueden obtenerse. Junto con eso, intentaremos construir varios gráficos de balance artificiales que son muy instructivos.

Falacias, Parte 2. La estadística es una pseudociencia o la "crónica de la caída en picado de cada día" Falacias, Parte 2. La estadística es una pseudociencia o la "crónica de la caída en picado de cada día"

Muchos intentos de aplicar los métodos estadísticos a la realidad objetiva, como las series financieras, fracasan cuando se encuentran con los procesos no estacionarios, "colas gruesas" de las distribuciones probabilísticas que los acompañan y el insuficiente volumen de la información financiera. En este artículo intentaré referirme no a las series financieras como tales, sino a su presentación subjetiva, en este caso a la forma en que un trader intenta dominar las series, como el sistema de trading. La educción de las regularidades estadísticas de los resultados del trading es una tarea muy apasionante. En algunos casos, pueden sacarse verdaderas conclusiones sobre el modelo de este proceso y estas pueden aplicarse al sistema de trading.

El espectáculo debe continuar, o una vez más sobre el ZigZag El espectáculo debe continuar, o una vez más sobre el ZigZag

Sobre un método obvio pero todavía no estándar de composición ZigZag y cuál es el resultado: el indicador ZigZag fractal multimarco que representa los ZigZag en tres conexiones más grandes en un único periodo de tiempo de funcionamiento. A su vez, esos periodos de tiempo mayores pueden no ser estándar tampoco y variar desde M5 a MN1.