First of all, you generally shouldn't do this sort of thing. <chrono>
provides a type-safe and generic units library for handling time durations, and there are few good reasons to escape this safety and genericity.
Some examples of the ills that don't happen with a type-safe, generic units library and which do happen with type-unsafe integral types:
// a type-safe units library prevents these mistakes:
int seconds = ...
int microseconds = seconds * 1000; // whoops
int time = seconds + microseconds; // whoops
void bar(int seconds);
bar(microseconds); // whoops
// a generic duration type prevents the need for:
unsigned sleep(unsigned seconds);
int usleep(useconds_t useconds);
int nanosleep(const struct timespec *rqtp, struct timespec *rmtp);
int attosleep(long long attoseconds); // ???
// just use:
template<typename Duration>
int sleep_for(Duration t); // users can specify sleep in terms of hours, seconds, microseconds, femetoseconds, whatever. Actual sleep duration depends on QoI, as always.
An example of a good reason would be compatibility with a third party library that made the unfortunate decision not to use a type-safe, generic units library in their API. In this case the conversions should be done as close as possible to the API boundary in order to minimize the extent to which unsafe types are used.
So with that said, when you do have a good reason, you do so like this:
std::chrono::milliseconds x = ...
std::uint64_t num = x.count();
Keep in mind that the predefined chrono durations such as chrono::milliseconds
use signed representations, so you'll need to take care to ensure the value is appropriate for conversion to uint64_t
.