Introducción: Por qué el trabajo estándar con el tiempo en C++ se ha vuelto más complejo (y mejor)
Durante mucho tiempo, el trabajo con fechas y horas en C++ se reducía al uso de funciones de <ctime>: time(), localtime(), strftime(). Esto era suficiente para tareas simples, pero con el aumento de la complejidad de los proyectos (sistemas distribuidos, servidores de alta carga, aplicaciones financieras) se necesitaron herramientas más precisas, seguras y convenientes.
El estándar C++11 nos trajo la biblioteca <chrono>, que resuelve los problemas de desbordamiento, confusión con las unidades de medida y dependencia de la plataforma. C++20 dio un paso importante al agregar soporte para husos horarios, tipos de calendario y formato a través de std::format. En este artículo, veremos técnicas avanzadas que van más allá de la simple obtención de la hora actual.
1. La biblioteca chrono: de milisegundos a nanosegundos y calendarios
El núcleo de std::chrono son tres componentes: reloj (clock), duración (duration) y instante de tiempo (time_point). A nivel avanzado, es importante saber elegir el reloj correcto y trabajar con la aritmética del tiempo.
1.1. Elección del reloj: system_clock, steady_clock, high_resolution_clock
system_clock— representa la hora del sistema (calendario). Puede ser ajustado por el usuario o por un servicio de sincronización (NTP). Se utiliza para mostrar la fecha al usuario.steady_clock— reloj monótono. Nunca se ajusta hacia atrás (sin retroceso). Ideal para medir intervalos (temporizadores, perfilado).high_resolution_clock— reloj con el menor ciclo posible. En la mayoría de las plataformas es sinónimo desteady_clock.
Consejo avanzado: Nunca use high_resolution_clock para perfilado si necesita estabilidad. Use steady_clock.
1.2. Trabajo con duration y time_point
El trabajo avanzado implica no solo medir el tiempo, sino también la conversión entre unidades, la aritmética y los tipos personalizados.
#include <iostream>#include <chrono>#include <thread>
int main() { using namespace std::chrono_literals; // para sufijos ms, s, us
// Creación avanzada de duration auto work_time = 2h + 30min + 15s; // 2 horas 30 minutos 15 segundos std::cout << "Tiempo de trabajo en segundos: " << work_time.count() << " s";
// Conversión con redondeo (duration_cast) auto ms = std::chrono::duration_cast<std::chrono::milliseconds>(work_time); std::cout << "En milisegundos: " << ms.count() << " ms";
// Medición del tiempo de ejecución de una función auto start = std::chrono::steady_clock::now(); std::this_thread::sleep_for(100ms); // simulación de trabajo auto end = std::chrono::steady_clock::now(); auto elapsed = std::chrono::duration_cast<std::chrono::microseconds>(end - start); std::cout << "La función se ejecutó en: " << elapsed.count() << " µs";
return 0;}1.3. Tipos de calendario (C++20)
C++20 agregó year_month_day, year_month, weekday y otros. Esto permite manipular fechas de forma segura sin trabajar con números en bruto.
#include <iostream>#include <chrono>
int main() { using namespace std::chrono;
// Creación de una fecha auto date = 2023y / October / 15d; // 15 de octubre de 2023 std::cout << "Fecha: " << date << '';
// Suma de días auto next_week = date + days(7); std::cout << "En una semana: " << next_week << '';
// Obtención del día de la semana weekday wd{date}; std::cout <&l