这只是数据。 c++ 类型系统很强大,但不是绝对的。您可以在 std::chrono::system_clock 和 time_t 之间进行转换的原因是它们共享相同的纪元,或“时钟开始的时间”。对于 time_t,这是自纪元“1969 年 12 月 31 日星期三 19:00:00”或自 1970 年 1 月 1 日 00:00 UTC 以来的秒数,although it is not defined。因此,转换系统时钟就像将时钟原始分辨率转换为自纪元以来的秒数一样简单。 time_point 封装了自纪元以来的时间。对于 high_resolution_clock 或 system_clock 以外的任何其他时钟,不保证 epoch 相同。可能是电脑启动的时候,或者是插入CMOS电池的时候,程序开始的时候……谁知道呢?谁在乎?时代的差异是它们不兼容的原因。不一定是他们的类型。虽然......,别名将确保共享相同的时代。因此,任何给定时间点的时期之间的差异,以秒为单位的偏移量,将为我们提供转换。没有更多的热身,这里是代码:
#include <iostream>
#include <chrono>
#include <ctime>
namespace joe {
template<typename Test, template<typename...> class Ref>
struct is_specialization : public std::false_type {};
template<template<typename...> class Ref, typename... Args>
struct is_specialization<Ref<Args...>, Ref> : public std::true_type {};
template <class Duration >
using is_duration = is_specialization<Duration, std::chrono::duration>;
template<class, class = void>
struct is_clock : public std::false_type {};
template<class Clock>
struct is_clock<Clock, std::void_t<typename Clock::rep, typename Clock::period, typename Clock::duration,
typename Clock::time_point, decltype(Clock::is_steady), decltype(Clock::now())>> : public std::true_type {};
template<typename Clock, class Duration = typename Clock::duration>
[[nodiscard]] static inline time_t to_time_t(const std::chrono::time_point<Clock, Duration>& time) noexcept {
static_assert(joe::is_clock<Clock>::value, "The given type for Clock does not fulfill the requirements of a clock.");
static_assert(joe::is_duration<Duration>::value, "The given type for Duration is not of std::chrono::duration.");
static const long long offset = (std::is_same< Clock, std::chrono::system_clock>::value) ? 0
: (std::chrono::duration_cast<std::chrono::seconds>(std::chrono::system_clock::now().time_since_epoch()).count()
- std::chrono::duration_cast<std::chrono::seconds>(Clock::now().time_since_epoch()).count());
return std::chrono::duration_cast<std::chrono::seconds>(time.time_since_epoch()).count() + offset;
}
template<typename Clock, class Duration = typename Clock::duration>
[[nodiscard]] static inline std::chrono::time_point<Clock, Duration> from_time_t( time_t time) noexcept {
static_assert(joe::is_clock<Clock>::value, "The given type for Clock does not fulfill the requirements of a clock.");
static_assert(joe::is_duration<Duration>::value, "The given type for Duration is not of std::chrono::duration.");
static const long long offset = (std::is_same< Clock, std::chrono::system_clock>::value) ? 0
: (std::chrono::duration_cast<std::chrono::seconds>(std::chrono::system_clock::now().time_since_epoch()).count()
- std::chrono::duration_cast<std::chrono::seconds>(Clock::now().time_since_epoch()).count());
return std::chrono::time_point<Clock, Duration>{ std::chrono::duration_cast<Duration>(std::chrono::seconds{ time - offset }) };
}
[[nodiscard]] static inline std::string ctime( time_t result) noexcept
{
char str[26];
ctime_s(str, sizeof str, &result);
return std::string(str);
}
}
void check_system_epoch()
{
const std::chrono::system_clock::time_point timePoint;
time_t time = joe::to_time_t(timePoint);
std::cout << "system clock epoch : " << joe::ctime(time) << std::endl;
}
void check_high_res_epoch()
{
const std::chrono::high_resolution_clock::time_point timePoint;
time_t time = joe::to_time_t(timePoint);
std::cout << "high resolution clock epoch : " << joe::ctime(time) << std::endl;
}
int main()
{
const std::chrono::high_resolution_clock::time_point & timePoint = std::chrono::high_resolution_clock::now();
time_t time = joe::to_time_t(timePoint);
std::cout << joe::ctime( time ) << std::endl;
std::cout << "Press the enter key to continue!\n";
check_system_epoch();
std::cin.ignore();
std::cout << "Press the enter key to continue!\n";
check_high_res_epoch();
std::cin.ignore();
}
`
这为您提供了 to_time_t、from_time_t 和一个 ctime,适用于任何时钟。