Un minuto y medio de diferencia entre la hora local y la hora fresca. Qué hacer. - página 2

 
prostotrader:

Hay código fuente con comentarios.

¿Te da pereza echarle un vistazo? ¿O hay algo que no entiendo?

Lo hice. Tengo la idea sin el código. No entiendo por qué me aconseja:

prostotrader:

Debe añadir los instrumentos más líquidos a Market Watch.

A continuación, añade capas de estos instrumentos.

Y, cuando OnBookEvent() se dispara, copia 1 tick (el último) habrá un tiempo e inmediatamente se toma la hora local y se compara.

¿Por qué es mejor su método?

 
pivomoe:

He echado un vistazo. Tengo la idea sin el código. No entiendo por qué me aconseja:

¿Por qué es mejor su método?

¡Porque es la correcta!

Me heequivocado, no en la hora local, sino en la del servidor.

1. Las garrapatas llegan al terminal en paquetes.

2. Cada paquete posterior puede contener ticks que no estaban "apilados" en el paquete anterior, pero que tienen el mismo tiempo que el anterior.

3. OnBookEvent() se activa al llegar cualquier tick (cambio de precio, volumen ) es decir, cada tick. (se activa un temporizador - ya es malo).

4. Utiliza el tiempo del ordenador local, que no es necesario en absoluto.

 

Aquí tiene todo lo que necesita para operar (consulte los horarios de las sesiones de negociación)

//+------------------------------------------------------------------+
//|                                                         Time.mq5 |
//|                                                   Copyright 2019 |
//|                                                                  |
//+------------------------------------------------------------------+
int is_book;
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
{
  is_book = MarketBookAdd(Symbol());
  if(is_book == false) return(INIT_FAILED);
  return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
  if(is_book == true) MarketBookRelease(Symbol()); 
}
//+------------------------------------------------------------------+
// Expert Book event function                                        |
//+------------------------------------------------------------------+  
void OnBookEvent(const string &symbol)
{
  if(symbol == Symbol())
  {
    if(CheckMarketTime() == true)
    {
     //Торговое время
     //Наш код
    }
  }
}
//+------------------------------------------------------------------+
//| Expert Check Market Time function                                |
//+------------------------------------------------------------------+
bool CheckMarketTime()
{
  MqlDateTime cur_time, sv_time;
  MqlTick ticks[];
  cur_time.year = 0;
  TimeTradeServer(cur_time); //Возвращает расчетное текущее время торгового сервера.
  if(cur_time.year > 0)
  {
    int result = CopyTicks(Symbol(), ticks, COPY_TICKS_ALL, 0, 1);
    if(result > 0)
    {
      if(TimeToStruct(ticks[0].time, sv_time) == true)
      {
        if(sv_time.day_of_year == cur_time.day_of_year)      //Проверка, что это сегодняшний тик
        {
          ulong tr_time = sv_time.hour * 3600 + sv_time.min * 60 + sv_time.sec;
          if(((tr_time >= 3600) && (tr_time < 50370)) ||   //10:00:00 - 13:59:30
             ((tr_time >= 50700) && (tr_time < 67470)) ||  //14:05:00 - 19:44:30 
             ((tr_time >= 68700) && (tr_time < 85770)))    //19:05:00 - 23:49:30
          {
            return(true);
          }
        }
      }
    }
  }   
  return(false);
} 

Añadido por

Si necesita una precisión de milisegundos, entonces este

double t_msc = double(ticks[0].time_msc - ulong(ticks[0].time) * 1000)/1000; //Получаем в секундах
double tr_time = sv_time.hour * 3600 + sv_time.min * 60 + sv_time.sec + t_msc;

Añadido

Pero todo esto no dará el resultado deseado (los límites del tiempo de negociación) porque

puede no haber ticks en una sesión de negociación, y el tiempo no se detiene.

Supongamos que alguien ha retirado su orden pendiente, el ticker ha cambiado,

hay una señal pero hay una correlación "antigua" (el tiempo no es el actual).

El terminal no transmite la hora exacta del servidor.

 

No me entiendes. Empecemos por el principio.

1) En su programa, llama a TimeCurrent() y obtiene la hora de llegada de la última cotización de uno de los símbolos seleccionados en Market Watch.

Que sean las 18:00 horas.

2) Con el siguiente comando, se obtiene la hora del último tick de SBER.

Que sea 17:58:00

3) Pasa un poco de tiempo y vuelve a solicitar la hora del último tick por SBER.

Que sean las 17:59:00


Nota la pregunta: ¿Crees que está bien que a las 18:00:00 por TimeCurrent() no se sepa de un tick con una hora de 17:59:00 ?

 
pivomoe:

No me entiendes. Empecemos por el principio.

1) En su programa, llama a TimeCurrent() y obtiene la hora de llegada de la última cotización de uno de los símbolos seleccionados en Market Watch.

Que sean las 18:00 horas.

2) Con el siguiente comando, se obtiene la hora del último tick de SBER.

Que sea 17:58:00

3) Pasa un poco de tiempo y vuelve a solicitar la hora del último tick por SBER.

Que sean las 17:59:00


Pregunta de atención: ¿Crees que está bien no ser consciente a las 18:00:00 por TimeCurrent() de un tick con la hora 17:59:00 ?

En el código que he citado se pueden contabilizar todos los ticks (sin problema)

El último código no utiliza TineCurrent() sinoTimeTradeServer() - esta vez sólo es necesario

para comprobar la garrapata con una precisión de un día y ya está.

Empecemos por el principio.

En general, ¿qué es lo que quiere hacer, averiguar?

¿Por qué has empezado a comparar la hora de las garrapatas con la hora local?

¿Cuál es el objetivo original?

 

A continuación le mostraré cómo se ve este problema en la práctica. He rediseñado completamente el Asesor Experto. Hice posible la captura de nuevos ticks en OnTimer así como en OnBookEvent.

Hay 45 símbolos en Market Watch. La mayoría de ellos no son líquidos.

Este es el resultado de la captura de nuevos ticks en OnBookEvent:

РЕКОРДная  Разница между временем последенго тика по ВСЕМ символам Минус только, что полученный новый тик по символу 494013 милесекундa.

CR      0       18:51:47.334    ProverkaAktyalnostiTikov (ALRS,H1)       Получен НОВЫЙ тик по символу                     SNGR-3.19 time_msc= 2019.03.18 18:41:47.988

HN      0       18:51:47.335    ProverkaAktyalnostiTikov (ALRS,H1)       ХОТЯ до этого был получeн тик                        ARMD time_msc 2019.03.18 18:50:02.001

Es decir, se ha capturado un nuevo tick a las 18:50 en TimeCurrent para el símboloSNGR-3.19 con una hora de 18:41.


Luego están las mediciones del tiempo del ordenador local en este momento:


1) obtener un nuevo tick, es decir, en el momento de la última llamada de CopyTick (o SymbolInfo dependiendo de la configuración).

2) El momento de la última llamada.

18:51:47.335    ProverkaAktyalnostiTikov (ALRS,H1)       Локальное время получения нового тика по символу.                      2019.03.18 18:51:47.334

18:51:47.335    ProverkaAktyalnostiTikov (ALRS,H1)       Предпоследние Локальное время попытки получить новый тик по символу    2019.03.18 18:41:47.204


Así que en este caso el problema se produjo porque la función get new simplemente no fue llamada durante 10 minutos.... Esto se debe a que el evento OnBookEvent deSNGR-3.19 no se generó durante 10 minutos.

Tal vez el terminal lo colocó en la cola de eventos y de alguna manera desapareció de esta cola. No hay tales errores con OnTimer. Sí, puede haber un tic con 20 segundos de retraso.


Archivos adjuntos:
 
pivomoe:


¿Cuál es su propósito original?

¿Por qué hay que comparar las horas de salida con la hora local?

 
prostotrader:

¿Cuál es su propósito original?

¿Por qué hay que comparar las horas de las garrapatas con la hora local?

Quiero saber el retraso máximo entre el momento en que se produce el tick en el servidor y cuando llega al terminal. Y quiero saber cómo minimizar este tiempo.

Este conocimiento puede ser utilizado en la escritura de mi propio probador. Incluso puede pedir a los desarrolladores que el retraso sea mayor.

TimeCurrent() - el tiempo del último tick de un símbolo será menor que el tiempo de retardo, por lo que se puede utilizar. Utilizar la hora local en la primera versión no fue una buena idea.

 
pivomoe:

Quiero saber el retraso máximo entre el momento en que se produce un tick en el servidor y cuando llega al terminal. Y cómo minimizar este tiempo.

Este conocimiento puede ser utilizado al escribir mi propio probador. Y tal vez incluso sea capaz de desconcertar a los desarrolladores con mayores retrasos.

Ya veo. Sigue... Sin mí.

Y para el resto del foro

//+------------------------------------------------------------------+
//|                                                         Time.mq5 |
//|                                                   Copyright 2019 |
//|                                                                  |
//+------------------------------------------------------------------+
enum FRESH_TICK
{
  UNKNOWN_TICK,
  NEW_TICK,
  CUR_TICK
};
//
int is_book;
ulong last_tick_time; //Время последнего тика
//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int OnInit()
{
  last_tick_time = 0;
  is_book = MarketBookAdd(Symbol());
  if(is_book == false) return(INIT_FAILED);
  return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| Expert deinitialization function                                 |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
  if(is_book == true) MarketBookRelease(Symbol()); 
}
//+------------------------------------------------------------------+
// Expert Book event function                                        |
//+------------------------------------------------------------------+  
void OnBookEvent(const string &symbol)
{
  if(symbol == Symbol())
  {
    MqlTick a_ticks[];
    int result = CopyTicks(symbol, a_ticks, COPY_TICKS_ALL, 0, 1);
    if(result > 0)
    {
      FRESH_TICK tick_state = CheckTickTime(a_ticks[0]);
      switch(tick_state)
      {
       case UNKNOWN_TICK:; //Тик не определен
       break;
       case NEW_TICK:;     //Торговое время, можно отсылать ордера;
       break;
       case CUR_TICK:;     //По усмотрению разработчика;
       break;
      }
    }  
  }
}
//+------------------------------------------------------------------+
//| Expert Check Market Time function                                |
//+------------------------------------------------------------------+
FRESH_TICK CheckTickTime(MqlTick &a_tick)
{
  MqlDateTime cur_time, tick_time;
  cur_time.year = 0;
  TimeTradeServer(cur_time); //Возвращает расчетное текущее время торгового сервера.
  if(cur_time.year > 0)
  {
    if(TimeToStruct(a_tick.time, tick_time) == true)
    {
      if(tick_time.day_of_year == cur_time.day_of_year)      //Проверка, что это сегодняшний тик
      {
        double t_msc = double(a_tick.time_msc - ulong(a_tick.time) * 1000)/1000;
        double tr_time = double(tick_time.hour * 3600 + tick_time.min * 60 + tick_time.sec) + t_msc;
        if(((tr_time >= 36000) && (tr_time < 50370)) ||   //10:00:00 - 13:59:30
           ((tr_time >= 50700) && (tr_time < 67470)) ||   //14:05:00 - 19:44:30 
           ((tr_time >= 68700) && (tr_time < 85770)))     //19:05:00 - 23:49:30
        {
          if(ulong(a_tick.time_msc) > last_tick_time)
          {
            last_tick_time = ulong(a_tick.time_msc);
            return(NEW_TICK);
          } else return(CUR_TICK);  
        }
      }
    }
  }   
  return(UNKNOWN_TICK);
} 
      
 
pivomoe:

Pregunta de atención: ¿crees que es normal que TimeCurrent() no se entere de un tick a las 18:00 con una hora de 17:59:00?

Creo que la cuestión es discutible. Queremos que la secuencia de garrapatas cumpla al menos los siguientes criterios:

1. Debe ser secuencial, es decir, el tiempo de cada tic posterior >= el tiempo del tic anterior;

2. actualidad. Es decir, la hora del último tic que llega es lo más cercana posible al momento actual;

Parece que el problema está en el segundo punto.

La argumentación del punto 2 es la siguiente: quiero que el tiempo desde la generación del tick en el servidor hasta que lo recibo (lag) sea mínimo, para poder procesarlo más rápido que los demás y tomar una decisión de trading. Pero si el retraso es el mismo para todos los licitadores, entonces no hay problema (por lo que yo entiendo). Es decir, el servidor del corredor tiene el problema, pero todos están en igualdad de condiciones. Si alguien recibió la información sobre la garrapata a las 17:59:01, y yo no la recibí ni siquiera a las 18:00 - este es el gran problema.

Y esta es la cuestión. ¿Cuál es el problema (y lo hay)? En el servidor del broker, que no da el tick (a todo el mundo) durante mucho tiempo, o en MT5, que no lo recibe durante mucho tiempo.

Razón de la queja: