Time points
Location
-
Courses
/
-
Complete C++ Course
/
-
The C++ Standard Library
/
-
Date and time
/
Time points
Summary
Epoch
A point in time is represented as a duration between a specific moment (Used as reference), called epoch, and the time point represented. For example, we represent dates with the year 1 as reference: The year 2000 is 1999 years after the year 1 (1 A.D.) and the year -500 (500 B.C.) is 499 years before the year (1 B.C.). The year 1 (1 A.D.) is the epoch used to represent dates with positive years and the year -1 (1 B.C.) is the epoch for dates with a negative year. For those who do not know, the Gregorian calendar starts at the year 1 (1 A.D.) and not 0, so the year 2000 is 1999 years after its epoch.
The class time_point
The class std::chrono::time_point<class C, class D = C::duration> is used to represent an exact moment in time (Example, the moment you first started learning C/C++).
The C++ Standard Library defines 3 types of clocks used to retrieve time points, and each of them may use a different epoch. Those clocks have a static method called now that returns an object of type std::chrono::time_point representing the time elapsed between right now and the epoch they use.
The first template argument of the class std::chrono::time_point is the clock type (Used to define the epoch of the time point) and the second one is the std::chrono::duration type used to represent the time elapsed between the epoch and the moment represented.
The 3 clocks are named system_clock, steady_clock and high_resolution_clock. They may all use different std::chrono::duration types. Their method now returns an object of type std::chrono::time_point, with, as template arguments, the type of the clock and the std::chrono::duration type they use.
To retrieve a time point returned by a clock, we must assign it to a time_point object of the same type (Or convert it). By default, the second template argument of the class std::chrono::time_point is set to the std::chrono::duration type used by the clock type given as first template argument.
Alternatively, we can use the type time_point defined in the namespace of the clock used, which is a typedef of the std::chrono::time_point type its method now returns.
We can retrieve the duration between the epoch and the moment represented by a time_point object by using its method duration std::chrono::time_point::time_since_epoch() const.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
#include <iostream>
#include <chrono>
int main()
{
std::chrono::time_point<std::chrono::system_clock> timePoint1 = std::chrono::system_clock::now();
/* Or */
// std::chrono::system_clock::time_point timePoint1 = std::chrono::system_clock::now();
std::chrono::time_point<std::chrono::steady_clock> timePoint2 = std::chrono::steady_clock::now();
/* Or */
// std::chrono::steady_clock::time_point timePoint2 = std::chrono::steady_clock::now();
std::chrono::time_point<std::chrono::high_resolution_clock> timePoint3 = std::chrono::high_resolution_clock::now();
/* Or */
// std::chrono::high_resolution_clock::time_point timePoint3 =
// std::chrono::high_resolution_clock::now();
std::cout << "system_clock: " << timePoint1.time_since_epoch().count() <<
" periods elapsed since the epoch.\n\n";
std::cout << "steady_clock: " << timePoint2.time_since_epoch().count() <<
" periods elapsed since the epoch.\n\n";
std::cout << "high_resolution_clock: " << timePoint3.time_since_epoch().count() <<
" periods elapsed since the epoch.\n\n";
return 0;
}

Operations with time points as operands
We can use the assignment, mathematical and logical operators with objects of type std::chrono::time_point as operands. The operands can be of different time_point types (But the clock type must be the same). In that case, they are automatically converted for the operation. Note that subtracting a time_point object from an other time_point object returns an object of type duration representing the (Positive of negative) duration between the two time points.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
#include <iostream>
#include <chrono>
int main()
{
std::chrono::steady_clock::time_point start =
std::chrono::steady_clock::now();
// Executes some instructions
for(unsigned c = 0; c < 10 * 1000 * 1000; c++)
{}
std::chrono::steady_clock::duration nbPeriodsElapsed =
std::chrono::steady_clock::now() - start;
std::cout << nbPeriodsElapsed.count() << " periods of " <<
std::chrono::steady_clock::duration::period::num << '/' <<
std::chrono::steady_clock::duration::period::den <<
" seconds elapsed.\n";
return 0;
}

Converting (Casting) time point types
Using the function time_point_cast, we can convert time_point objects to time_point objects of different types (With a different duration type).
It takes, in argument, the time_point object to convert and it takes, in template argument, the duration type the time_point type, to convert to, uses. It returns the converted time_point.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
#include <iostream>
#include <chrono>
// typedef named 'days' of a duration type using a period of 1 day.
typedef std::chrono::duration<unsigned long, std::ratio<3600 * 24>> days;
int main()
{
// Retrieves the current time point as an object of the time_point type used by system_clock.
std::chrono::system_clock::time_point sysTimeP =
std::chrono::system_clock::now();
// Converts the time_point object retrieved into a time_point object using a period of 1 day.
std::chrono::time_point<std::chrono::system_clock, days> nbDays =
std::chrono::time_point_cast<days>(sysTimeP);
// Retrieves the number of periods (Of 1 day) elapsed since the epoch used by system_clock.
std::cout << nbDays.time_since_epoch().count();
std::cout << " days since the epoch used by system_clock.\n";
return 0;
}

Note that time_point type casting may lead, in the same cases as duration type casting, to precision or data loss.