std :: tiempo crono

Archivo de encabezado: #include <chrono>

El cronógrafo de la biblioteca de tiempo de c ++ 11 se encuentra en el espacio de nombres std :: chrono.

Espacio de nombres: usando el espacio de nombres std :: chrono;

Definición de macro:

#define _XTIME_NSECS_PER_TICK 100
#define _XTIME_TICKS_PER_TIME_T (long long) 10000000

reloj

 El cronógrafo de biblioteca de tiempo c ++ 11 simplifica la programación y el desarrollo del cálculo de la hora, la fecha y el intervalo de tiempo; reflejado principalmente en:

    1. Obtenga el punto de tiempo exacto (time_point) del reloj (clock) basado en system_clock, stable_clock y high_resolution_clock;

    2. Cálculo del intervalo de tiempo (duración) basado en la diferencia entre diferentes unidades de tiempo y diferentes puntos de tiempo;

El cronógrafo de la biblioteca de tiempo de c ++ 11 se encuentra en el espacio de nombres std :: chrono.

 1. Reloj:

    包括 reloj_sistema 、 reloj_constante 、 reloj_de_resolución_alta ;

    1. system_clock: El reloj en tiempo real proporcionado por el sistema, el tiempo obtenido por todos los procesos que utilizan el método now () es el mismo;

    2. Steady_clock: un reloj monótono que no se ajustará, lo que garantiza que incluso si se modifica el sistema mientras el proceso se está ejecutando, y se vuelve a llamar al método now (), la hora actual basada en la hora del sistema anterior aún se puede obtener ;

    3. high_resolution_clock: es el typedef de system_clock y stable_clock

chrono :: system_clock :: now ()
Para system_clock, su punto de partida es epoch, que es 1970-01-01 00:00:00 UTC, y su escala es 1 tick, que es _XTIME_NSECS_PER_TICK nanosegundos.

El reloj fijo_clock es diferente del reloj_sistema. El reloj_sistema corresponde a la hora del sistema. Si lo ajusta manualmente o el sistema operativo se sincroniza automáticamente con el reloj de la red, la hora obtenida al llamar a system_clock.now () también se verá afectada. La segunda llamada puede En cambio, el tiempo obtenido al llamar es anterior. Steady_clock garantiza que el tiempo avanza a una velocidad constante y no se ve afectado por el ajuste del reloj del sistema.

Steady_clock :: duration d = Steady_clock :: now (). time_since_epoch (); Lo que obtienes es el intervalo de tiempo entre la hora actual y 1970.1.1. Mediante la conversión de tipos, se puede convertir en varias representaciones de precisión.

La precisión de esta función es de 1 tick, que es 100 nanosegundos;

二 、 time_point :

    Basado en el reloj, se puede obtener time_point. El llamado time point se refiere a un momento determinado, como 2018.4.17 17:13:15;

    time_point aparece de dos formas:

    1. Time_point bajo el espacio de nombres std :: chrono:

          std :: chrono :: time_point es una clase de plantilla, debe especificar la clase de reloj utilizada (system_clock / Steady_clock / high_resolution_clock) y precisión (el valor predeterminado es el nivel de hora, que se puede especificar mediante std :: ratio);

//std::chrono::time_point is a template class, not used usually.
std::chrono::time_point<std::chrono::high_resolution_clock, std::chrono::duration<int, std::ratio<60 * 60 * 24>>> now_daylevel = std::chrono::time_point_cast<std::chrono::duration<int, std::ratio<60 * 60 * 24>>>(std::chrono::high_resolution_clock::now());
std::chrono::time_point<std::chrono::high_resolution_clock, std::chrono::duration<int, std::ratio<60 * 60>>> now_hourlevel = std::chrono::time_point_cast<std::chrono::duration<int, std::ratio<60 * 60>>>(std::chrono::high_resolution_clock::now());
std::chrono::time_point<std::chrono::high_resolution_clock, std::chrono::duration<int, std::ratio<60>>> now_minutelevel = std::chrono::time_point_cast<std::chrono::duration<int, std::ratio<60>>>(std::chrono::high_resolution_clock::now());
std::chrono::time_point<std::chrono::high_resolution_clock, std::chrono::duration<int, std::ratio<1>>> now_secondlevel = std::chrono::time_point_cast<std::chrono::duration<int, std::ratio<1>>>(std::chrono::high_resolution_clock::now());
std::chrono::time_point<std::chrono::high_resolution_clock> now_deflevel = std::chrono::time_point_cast<std::chrono::duration<int, std::ratio<60 * 60 * 24>>>(std::chrono::high_resolution_clock::now());

La hora actual obtenida por hora, minuto, segundo y los 4 métodos predeterminados se obtienen arriba y luego se convierten a una marca de tiempo unixtime:

std::time_t ut_day = std::chrono::high_resolution_clock::to_time_t(now_daylevel);
ut_hour = std::chrono::high_resolution_clock::to_time_t(now_hourlevel);
ut_minute = std::chrono::high_resolution_clock::to_time_t(now_minutelevel);
ut_second = std::chrono::high_resolution_clock::to_time_t(now_secondlevel);
ut_def = std::chrono::high_resolution_clock::to_time_t(now_deflevel);

Luego use ctime para convertir al formato de fecha y hora:

    std::cout << ut_day << std::endl;
    std::cout << ctime(&ut_day) << std::endl;
 
    std::cout << ut_hour << std::endl;
    std::cout << ctime(&ut_hour) << std::endl;
 
    std::cout << ut_minute << std::endl;
    std::cout << ctime(&ut_minute) << std::endl;
 
    std::cout << ut_second << std::endl;
    std::cout << ctime(&ut_second) << std::endl;
 
    std::cout << ut_def << std::endl;
    std::cout << ctime(&ut_def) << std::endl;

Resultados de la observación:

 1523923200

            Tue Apr 17 08:00:00 2018------------------day

            1523955600

            Tue Apr 17 17:00:00 2018------------------hour

            1523957460

            Tue Apr 17 17:31:00 2018------------------minute

            1523957497

            Tue Apr 17 17:31:37 2018------------------second

            1523923200

            Tue Apr 17 08:00:00 2018------------------default

   Puntos a dominar:

            1. Cómo definir un punto en el tiempo

                1.1. Clase de plantilla std :: chrono :: time_point:

                Necesita instanciación de plantilla: tipo de reloj (obligatorio, system_clock / Steady_clock / high_resolution_clock), nivel de precisión (opcional)

               如 : std :: chrono :: time_point <std :: chrono :: high_resolution_clock, std :: chrono :: duration <int, std :: ratio <60 * 60 * 24 >>> now_daylevel = std :: chrono :: time_point_cast <std :: chrono :: duración <int, std :: ratio <60 * 60 * 24 >>> (std :: chrono :: high_resolution_clock :: now ());

                Este método es más problemático

                1.2, std :: chrono :: tipo de reloj :: time_point

                  incluir:

                    std :: chrono :: system_clock :: time_point

                    std :: chrono :: reloj_estable :: punto_tiempo

                    std :: chrono :: high_resolution_clock :: time_point

                    如 : std :: chrono :: high_resolution_clock :: time_point ahora = std :: chrono :: high_resolution_clock :: ahora ();

                    De esta manera es relativamente simple

            2. Conversión de time_point a unixtime timestamp:

                Método: std :: chrono :: clock type :: método to_time_t (time_point)

                Como:

                std :: chrono :: high_resolution_clock :: time_point ahora = std :: chrono :: high_resolution_clock :: ahora ();

                std :: time_t ut_now = std :: chrono :: high_resolution_clock :: to_time_t (ahora) ;

                Puede usar ctime de stl para realizar la conversión de la marca de tiempo unixtime al formato de fecha y hora:

                std :: cout << "ahora:" << ctime (& ut_now);

            3. Método time_since_epoch

                Calcule cuántos días, horas, minutos y segundos han pasado desde el 1 de enero de 1970 hasta el presente.

            4. Realice un cálculo de tiempo incremental a través de la duración

                Pase un tiempo time_point_1, sume y reste la duración para obtener otro tiempo time_point_2

                Vea la introducción de duración a continuación
 

#include <chrono>   
using namespace std;
using namespace chrono;

auto start = system_clock::now();
// do something...
auto end   = system_clock::now();
auto duration = duration_cast<microseconds>(end - start);
cout <<  "花费了" 
     << double(duration.count()) * microseconds::period::num / microseconds::period::den   << "秒" << endl;

duration_cast <> significa conversión de tipo
microsegundos significa sutil. Además, hay cinco unidades de tiempo: horas, minutos, segundos, milisegundos, nanosegundos
num y den representan el numerador y el denominador, respectivamente. En el código que di, num es igual a 1, den es igual a 1,000,000
count () se usa para devolver la hora

steady_clock::duration d = steady_clock::now().time_since_epoch();
minutes min = duration_cast<minutes>(d);
seconds sec = duration_cast<seconds>(d);
milliseconds mil = duration_cast<milliseconds>(d);
microseconds mic = duration_cast<microseconds>(d);
nanoseconds nan = duration_cast<nanoseconds>(d);
cout << min.count() << "分钟" << endl;
cout << sec.count() << "秒" << endl;
cout << mil.count() << "毫秒" << endl;
cout << mic.count() << "微妙" << endl;
cout << nan.count() << "纳秒" << endl;

reloj_constante

Se utiliza en escenarios donde es necesario obtener el intervalo de tiempo, y este intervalo de tiempo no se verá afectado por la modificación de la hora del sistema.

auto tp1 = std::chrono::steady_clock::now();
//do something
auto tp2 = std::chrono::steady_clock::now();
std::cout << std::chrono::duration_caststd::chrono::microseconds(tp2 - tp1).count() << “microseconds” << std::endl;

Obtener marca de tiempo

std::time_t getTimeStamp()
{
    std::chrono::time_point<std::chrono::system_clock,std::chrono::milliseconds> tp = std::chrono::time_point_cast<std::chrono::milliseconds>(std::chrono::system_clock::now());
    auto tmp=std::chrono::duration_cast<std::chrono::milliseconds>(tp.time_since_epoch());
    std::time_t timestamp = tmp.count();
    //std::time_t timestamp = std::chrono::system_clock::to_time_t(tp);
    return timestamp;
}

Marca de tiempo hasta la fecha

Donde int64 es un tipo de datos multiplataforma personalizado

std::tm* gettm(int64 timestamp)
{
    int64 milli = timestamp+ (int64)8*60*60*1000;//此处转化为东八区北京时间,如果是其它时区需要按需求修改
    auto mTime = std::chrono::milliseconds(milli);
    auto tp=std::chrono::time_point<std::chrono::system_clock,std::chrono::milliseconds>(mTime);
    auto tt = std::chrono::system_clock::to_time_t(tp);
    std::tm* now = std::gmtime(&tt);
    printf("%4d年%02d月%02d日 %02d:%02d:%02d\n",now->tm_year+1900,now->tm_mon+1,now->tm_mday,now->tm_hour,now->tm_min,now->tm_sec);
   return now;
}

Tres, duración

Puntos centrales:

            1. Duración significa un período de tiempo, como "100 milisegundos", "un segundo", "2 minutos", "5 horas", "10 días" ...

            2. La duración se basa en segundos, y cada unidad de tiempo personalizada se deriva de std :: ratio, que incluye, entre otros: días, horas, minutos, segundos, milisegundos, microsegundos, nanosegundos, stl proporciona de forma predeterminada: horas, minutos, Segundos, milisegundos, microsegundos, nanosegundos;

            3. La duración misma puede realizar operaciones de suma y resta, como: período de tiempo d3 = período de tiempo d1-período de tiempo d2

            4. La duración puede proporcionar duration_cast, que se puede convertir de una unidad de tiempo a otra, por ejemplo, 1 hora y 60 minutos se pueden convertir entre sí

            5. Time time_point puede obtener otro tiempo sumando y restando duración;

            1 y 2, introducción a la duración

            std :: ratio representa un ratio, o ratio, es una clase de plantilla, la definición es:

template<intmax_t _Nx, intmax_t _Dx = 1>  
struct ratio  
{    // holds the ratio of _Nx to _Dx  
    static_assert(_Dx != 0, "zero denominator");  
    static_assert(-INTMAX_MAX <= _Nx, "numerator too negative");  
    static_assert(-INTMAX_MAX <= _Dx, "denominator too negative");  
      
    static constexpr intmax_t num = _Sign_of<_Nx>::value  
            * _Sign_of<_Dx>::value * _Abs<_Nx>::value / _Gcd<_Nx, _Dx>::value;  
      
    static constexpr intmax_t den = _Abs<_Dx>::value / _Gcd<_Nx, _Dx>  
            ::value;  
      
    typedef ratio<num, den> type;  
};

                PD: intmax_t es long long

                En resumen, _Nx = 60 y _Dx = 1, entonces la proporción es 60, que se puede usar para representar minutos:               

std::chrono::duration<int, std::ratio<60>> one_minute(1);
std::chrono::duration<int, std::ratio<60>> three_minute(3);

                i. std :: chrono :: duratio representa el intervalo de tiempo, el punto de referencia es 1 segundo;

                ii) El primer parámetro int de la instanciación de plantilla, que representa la longitud del intervalo de tiempo, está representado por un número entero;

                iii. El segundo parámetro de instanciación de plantilla, std :: ratio <60>, representa la relación entre el intervalo de tiempo y el segundo es 60: 1. Tenga en cuenta que la instanciación predeterminada de ratio _Dx es 1, es decir, std :: ratio <60 > es equivalente en std :: ratio <60, 1>; la relación de 60: 1 es equivalente a std :: chrono :: duration <int, std :: ratio <60>> es una estructura de datos que representa un minuto intervalo;

                iv. Según esta estructura de datos, el objeto one_minute se construye con un parámetro de construcción de 1, que representa el objeto one_minute que representa un intervalo de tiempo de un minuto; el objeto three_minute se construye con un parámetro de construcción de 3, que representa el objeto three_minute que representa un intervalo de tiempo de 3 minutos;

                Si el principio de la estructura de minutos es claro, entonces es factible construir un intervalo de tiempo de cualquier duración;

                Código:   

std::chrono::duration<int, std::ratio<3>> three_second(1);
     
    std::chrono::high_resolution_clock::time_point t1 = std::chrono::high_resolution_clock::now();  std::this_thread::sleep_for(three_second);   std::chrono::high_resolution_clock::time_point t2 = std::chrono::high_resolution_clock::now();
     
    std::time_t ut1 = std::chrono::high_resolution_clock::to_time_t(t1), ut2 = std::chrono::high_resolution_clock::to_time_t(t2);
    std::cout << "t1: " << ctime(&ut1);
    std::cout << "t2: " << ctime(&ut2);

                El código anterior significa construir un intervalo de tiempo de 3 segundos, three_minute, y luego registrar la hora y el momento (time_point) t1 en este momento, luego poner el hilo actual en reposo durante 3 segundos y luego registrar la hora y el momento (time_point ) nuevamente después de que el hilo se reanude) t2, luego emitir t1 y t2, y observar si la diferencia entre t1 y t2 es de 3 segundos;

                Como se mencionó anteriormente, time_point puede obtener diferentes momentos sumando y restando duración:   

    std::chrono::high_resolution_clock::time_point now = std::chrono::high_resolution_clock::now();
     
    std::chrono::duration<int, std::ratio<60>> one_minute(1);
    std::chrono::duration<int, std::ratio<60 * 60 * 24>> one_day(1);

    std::chrono::high_resolution_clock::time_point next_minute = now + one_minute;   

    std::chrono::high_resolution_clock::time_point last_minute = now - one_minute;  

    std::chrono::high_resolution_clock::time_point next_day = now + one_day;
    std::chrono::high_resolution_clock::time_point last_day = now - one_day;
     
    std::time_t ut_now = std::chrono::high_resolution_clock::to_time_t(now);
    std::time_t ut_next_minute =  std::chrono::high_resolution_clock::to_time_t(next_minute);
    std::time_t ut_last_minute = std::chrono::high_resolution_clock::to_time_t(last_minute);
    std::time_t ut_next_day = std::chrono::high_resolution_clock::to_time_t(next_day);
    std::time_t ut_last_day = std::chrono::high_resolution_clock::to_time_t(last_day);
     
    std::cout << "now: " << ctime(&ut_now);
    std::cout << "next minute: " << ctime(&ut_last_minute);
    std::cout << "last minute: " << ctime(&ut_next_minute);
    std::cout << "next day: " << ctime(&ut_last_day);
    std::cout << "last day: " << ctime(&ut_next_day);

                El código anterior primero obtiene la hora actual (time_point) ahora, y luego construye los objetos de intervalo de tiempo one_minute y one_day, que representan un minuto y un día respectivamente, y luego suma y resta un_minute y un_day de la hora actual para obtener el minuto anterior y el siguiente Un minuto, este momento ayer, este momento mañana (time_point);


  stl ha construido la estructura de datos de horas, minutos, segundos, milisegundos, microsegundos y nanosegundos, por lo que no es necesario que la construya usted mismo a través de std :: ratio:

typedef duration <Rep, ratio<3600,1>> hours;
typedef duration <Rep, ratio<60,1>> minutes;
typedef duration <Rep, ratio<1,1>> seconds;
typedef duration <Rep, ratio<1,1000>> milliseconds;
typedef duration <Rep, ratio<1,1000000>> microseconds;
typedef duration <Rep, ratio<1,1000000000>> nanoseconds;

            Por ejemplo, los siguientes ejemplos representan la suspensión del hilo actual durante un segundo, 1000 milisegundos y 1 microsegundo:

std::this_thread::sleep_for(std::chrono::seconds(1));
std::this_thread::sleep_for(std::chrono::milliseconds(1000));
std::this_thread::sleep_for(std::chrono::microseconds(1));

            La duración del intervalo de tiempo no solo se puede usar para sumar y restar por time_point, sino que también se puede usar para sumar y restar entre duraciones, como:

std::chrono::seconds tm_span1(10);
std::chrono::minutes tm_span2(1);
std::chrono::seconds tm_span3 = tm_span2 - tm_span1;
std::cout << tm_span3.count() << std::endl;

                Primero defina 10 segundos tm_span1 en segundos, y luego defina 1 minuto tm_span2 en minutos, la diferencia entre los dos es 50 segundos, tm_span2-tm_span1 = 50 segundos se asignan a tm_span3 definido en segundos;

               Nota: la asignación directa de tm_span2-tm_span1 a tm_span4 definido en minutos provocará un error de compilación. Si desea asignar un valor, debe realizar una conversión de estructura a través de duration_cast:   

std::chrono::seconds tm_span1(10);
std::chrono::minutes tm_span2(1);
std::chrono::minutes tm_span4 = std::chrono::duration_cast<std::chrono::minutes>(tm_span2 - tm_span1);
std::cout << tm_span4.count() << std::endl;

     El método de recuento de la duración es el resultado de dividir la longitud del intervalo de tiempo representado por la duración por su unidad nominal. Como en el ejemplo anterior, tm_span3 representa una longitud de 50 segundos y su unidad de tiempo es 1 segundo, por lo que el resultado obtenido por el método de conteo es 50.

Supongo que te gusta

Origin blog.csdn.net/sunlin972913894/article/details/103194920
Recomendado
Clasificación