chrono 模块学习

三大类

顶级clock: system_clock日期时间; steady_clock启动时间, 硬件震动clock;

  • 内置四大类型: duration使用精度类型(min,sec,ms,ns等 加 数量); rep记录对应精度数量的类型(默认longlong, 也可以自定义其他类型); period: 精度, 即当前精度等于1s*ratio, (ms = 1 / 1000s); time_point: 用system_clock作为表达方式的时刻;
  • 一个成员变量: is_steady是否高精度;
  • 若干生成器; now, to_time_t, from_time_t, 即如何用系统的时间机制生成STL对象;

duration: 一段时间, 适用于日期计算;

即精度 + 精度数量; ms * 10001000ms;

time_point: 时刻点 = clock + duration, 适用于高精度程序执行耗时计算;

即起始时刻可以是1970.1.1为起始用于日期计算; 也可以是电脑开机时间为起始用于时间计算;

总结

  • 时间起点: epoch
  • duration: ratio * count, 转换规则count * ratio_new / ratio_old;
  • timepoint: epoch + duration
  • clock: 从系统获取对应类型值, 用于生成匹配类型;

clock

system_clock: 可变化计算量

定义了四种类型; 一个静态成员, 三个对象生成器;

class _LIBCPP_TYPE_VIS system_clock
{
public:
    typedef microseconds                     duration;
    typedef duration::rep                    rep;
    typedef duration::period                 period;
    typedef chrono::time_point<system_clock> time_point;
    static constexpr const bool is_steady = false;

    static time_point now() _NOEXCEPT;
    static time_t     to_time_t  (const time_point& __t) _NOEXCEPT;
    static time_point from_time_t(time_t __t) _NOEXCEPT;
};

steady_clock: 启动时间, 常量;

class _LIBCPP_TYPE_VIS steady_clock
{
public:
    typedef nanoseconds                                   duration;
    typedef duration::rep                                 rep;
    typedef duration::period                              period;
    typedef chrono::time_point<steady_clock, duration>    time_point;
    static _LIBCPP_CONSTEXPR_AFTER_CXX11 const bool is_steady = true;

    static time_point now() _NOEXCEPT;
};

high_resolution_clock: 即二选一, 优先steady_clock;

#ifndef _LIBCPP_HAS_NO_MONOTONIC_CLOCK
class _LIBCPP_TYPE_VIS steady_clock
{
public:
    typedef nanoseconds                                   duration;
    typedef duration::rep                                 rep;
    typedef duration::period                              period;
    typedef chrono::time_point<steady_clock, duration>    time_point;
    static _LIBCPP_CONSTEXPR_AFTER_CXX11 const bool is_steady = true;

    static time_point now() _NOEXCEPT;
};

typedef steady_clock high_resolution_clock;
#else
typedef system_clock high_resolution_clock;
#endif

总结: 支持单位不同换算

  • 两种clock定义了四种成员类型;
  • system_clock, steady_clock主要差异在使用精度(microseconds, nanoseconds)不同;
  • 类型分别是: 时长类型, 数学计数类型, 当前使用精度; 时间点;
  • duration = rep + period, time_point = clock + duration, time_point可以是时间日期, 也可以是启动时间点;

获取数据

获取对应精度的数量

duration::count()

不同精度的转换

template <class _ToDuration, class _Rep, class _Period>
inline _LIBCPP_INLINE_VISIBILITY
_LIBCPP_CONSTEXPR
typename enable_if
<
    __is_duration<_ToDuration>::value,
    _ToDuration
>::type
duration_cast(const duration<_Rep, _Period>& __fd)
{
    return __duration_cast<duration<_Rep, _Period>, _ToDuration>()(__fd);
}

template <class _ToDuration, class _Clock, class _Duration>
inline constexpr time_point<_Clock, _ToDuration>
time_point_cast(const time_point<_Clock, _Duration>& __t)
{
    return time_point<_Clock, _ToDuration>(_VSTD::chrono::duration_cast<_ToDuration>(__t.time_since_epoch()));
}

类型转换原理

  • 存储数量的算数类型转换;
  • 存储精度的转换;

精度转换并四舍五入: c++17


#if _LIBCPP_STD_VER > 14
template <class _ToDuration, class _Clock, class _Duration>
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
typename enable_if
<
    __is_duration<_ToDuration>::value,
    time_point<_Clock, _ToDuration>
>::type
floor(const time_point<_Clock, _Duration>& __t)
{
    return time_point<_Clock, _ToDuration>{floor<_ToDuration>(__t.time_since_epoch())};
}

template <class _ToDuration, class _Clock, class _Duration>
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
typename enable_if
<
    __is_duration<_ToDuration>::value,
    time_point<_Clock, _ToDuration>
>::type
ceil(const time_point<_Clock, _Duration>& __t)
{
    return time_point<_Clock, _ToDuration>{ceil<_ToDuration>(__t.time_since_epoch())};
}

template <class _ToDuration, class _Clock, class _Duration>
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
typename enable_if
<
    __is_duration<_ToDuration>::value,
    time_point<_Clock, _ToDuration>
>::type
round(const time_point<_Clock, _Duration>& __t)
{
    return time_point<_Clock, _ToDuration>{round<_ToDuration>(__t.time_since_epoch())};
}

template <class _Rep, class _Period>
inline _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR
typename enable_if
<
    numeric_limits<_Rep>::is_signed,
    duration<_Rep, _Period>
>::type
abs(duration<_Rep, _Period> __d)
{
    return __d >= __d.zero() ? +__d : -__d;
}
#endif

总结

日期计算: system_clock; 耗时计算: steady_clock

duration: 支持各种精度记录时间;

// 算数类型 + second 的 n 倍精度;
typedef duration<long long,         nano> nanoseconds;
typedef duration<long long,        micro> microseconds;
typedef duration<long long,        milli> milliseconds;
typedef duration<long long              > seconds;
typedef duration<     long, ratio<  60> > minutes;
typedef duration<     long, ratio<3600> > hours;

template <intmax_t _Num, intmax_t _Den = 1>
class ratio;

// 分数精度, 常用单位s
typedef ratio<1LL, 1000000000000000000LL> atto;
typedef ratio<1LL,    1000000000000000LL> femto;
typedef ratio<1LL,       1000000000000LL> pico;
typedef ratio<1LL,          1000000000LL> nano;
typedef ratio<1LL,             1000000LL> micro;
typedef ratio<1LL,                1000LL> milli;
typedef ratio<1LL,                 100LL> centi;
typedef ratio<1LL,                  10LL> deci;
typedef ratio<                 10LL, 1LL> deca;
typedef ratio<                100LL, 1LL> hecto;
typedef ratio<               1000LL, 1LL> kilo;
typedef ratio<            1000000LL, 1LL> mega;
typedef ratio<         1000000000LL, 1LL> giga;
typedef ratio<      1000000000000LL, 1LL> tera;
typedef ratio<   1000000000000000LL, 1LL> peta;
typedef ratio<1000000000000000000LL, 1LL> exa;

count()获取对应单位的时刻

不同精度转换;clock之间转换:, duration之间转换:duration_cast; time_point之间转换:time_point_cast;

参考链接

https://en.cppreference.com/w/cpp/chrono

案例

时间: 系统时间转换, clock之间计算返回结果duration, 之间类型转换并获取结果;

#include
#include 
#include
#include
int main() {
    //std::cout << std::chrono::system_clock::now().time_since_epoch().count() << std::endl;
    auto start = std::chrono::system_clock::now();
    sleep(1);
    auto end = std::chrono::system_clock::now();
    auto dif = end - start;
    std::cout << std::chrono::round<std::chrono::seconds>(dif).count() << std::endl;
}

建议用high_resolution_clock计算两个点程序执行时间差duration;

你可能感兴趣的:(optimization,Effectivve,Modern,Cpp,C/C++,学习,java,服务器)