C++11时间类

最近代码中需要用到时间功能,来判断某些操作是否超时未完成,发现C++11里面提供了时间类,自己摸索一下,写一篇文档分享心得体会,下文都是自己的理解。

std::chrono::duration
std::chrono::duration,进入源码中可以看到它是:需要用两个参数组合而成

template
    class duration

顾名思义:duration的意思是期间(周期次数与一个周期时间的结合),这个模板有两个参数,第一个是_Period,把它理解为周期,一个周期需要的时间单位,当然你也可以理解它为精度,分辨率。第二个是_Rep,我把他理解为一个重复次数或者说是数值,表示这个周期需要执行多少个单位。所以这个duration就通过_Rep*_Period,得到了这个期间的时长。当我们需要定义一个期间时,就可以先定义最小颗粒度的单位(即_Period,一个周期时间),再定义需要执行的周期次数(_Rep),则可以完成我们需要的周期。
给两个栗子:下面这两个表示方式都表示十秒钟

std::chrono::duration>  ten_secends(10);    //十秒钟
std::chrono::duration>  ten_secends(1);    //十秒钟

_Period
使用ratio实例化模板类_Period,ratio理解为精度,我把它理解为一个时间周期的意思。他的模板参数如下

template
    struct ratio

使用两个整型进行初始化,_Nx表示分子,_Dx表示分母,ratio<1,1>表示一秒钟的时间周期,C++标准中给我们定义了很多个ratio的初始化结构。我们可以在程序中直接使用,std::milli等精度。
C++11时间类_第1张图片
按照上面我所说,我们的duration期间,是通过两个参数组成,ratio是其一,其二就是一个重复的次数_Rep,基于生活中的习惯,C++chrono库中已经给我们typedef了常见的期间。
C++11时间类_第2张图片
如上图所示,给我们定义了纳秒,微妙,秒,分钟,小时等,我也不知道啥单位了。我们使用的时候就可以这样

    std::chrono::seconds twenty_secends(20);  //20秒
    std::chrono::minutes twenty_min(20);      //20分钟
    std::chrono::hours twenty_hour(20);       //20小时

其实duration的第一个参数_Rep不止于int类型,当你想表示0.5秒时,你也可以试试以下的用法。

std::chrono::duration halfSecs(0.5);    //默认参数ratio<1,1>
std::chrono::duration halfSecs(500);

std::duration为我们提供了count函数,返回的是_Rep在此_Period下的值,比如:

    std::chrono::seconds secend_one(1);
    std::cout << "秒数 : " << secend_one.count() << std::endl;         //在秒下的值
    std::chrono::milliseconds mill_one = std::chrono::duration_cast(secend_one);
    std::cout << "毫秒数 : " << mill_one.count() << std::endl;           //转换成毫秒后的值

小结std::duration其实很简单,由数量和单位组成,就好比10只,10是数量,只是单位。只要确定数量和单位,就可以定义出一个自己需要的期间了。
std::system_clock

system_clock提供了三个方法nowto_time_tfrom_time_t
typedef chrono::time_point time_point,实例化了系统时间的time_point
system_clock::now函数得到桌面右下角windows的系统时间,你右下角的时间是多少,它就得到的是什么,会被人为的修改后,得到不正确的时间。
to_time_t,将得到的time_point,转换成time_t结构。from_time_t
代码如下:

#include 
#include 
int main()
{
    std::chrono::system_clock::time_point tp = std::chrono::system_clock::now();  //得到系统时间
    time_t tt = std::chrono::system_clock::to_time_t(tp);            //将系统时间time_point 转化为time_t格式
    std::string strTime = ctime(&tt);                                //将time_t转换成字符串
    std::cout << strTime.c_str() << std::endl;
    return 0;
}

std::steady_clock
在上面的std::syste_clock中,我们知道这个时间是可以被人为的修改的,如果我们需要一个用户无法更改的时间时,std::steady_clock给我们提供了帮助,它提供一个相对于boot启动后到当前的时间,如果我们需要计算一件事情做了多长时间,std::steady_clock充当绝对主力。
std::chrono::steady_clock::now()提供了boot启动到当前的时间time_point。

#include 
#include 
#include 

int main()
{
    std::chrono::steady_clock::time_point start = std::chrono::steady_clock::now();     //得到开始时间点
    std::this_thread::sleep_for(std::chrono::seconds(1));   //做事情
    std::chrono::steady_clock::time_point end = std::chrono::steady_clock::now();       //得到结束时间点
    std::cout << (std::chrono::time_point_cast(end) - 
                  std::chrono::time_point_cast(start)).count() << std::endl;   //相对时间计算
    return 0;
}

time_point为我们提供了time_since_epoch方法,返回一个std::duration,在system_clock表示从1970年1月1日到现在经历的时间。steady_clock中,表示boot打开到现在经历的时间。调用count得到duration里面的值。

#include 
#include 
int main()
{
    std::chrono::system_clock::time_point system_clocktp = std::chrono::system_clock::now();
    std::cout << std::chrono::duration_cast(system_clocktp.time_since_epoch()).count() << std::endl;

    std::chrono::steady_clock::time_point steady_clocktp = std::chrono::steady_clock::now();
    std::cout << std::chrono::duration_cast(steady_clocktp.time_since_epoch()).count() << std::endl;
    return 0;
}

小结:在计算某个任务相对时间时,使用steady_clock是比较合适的,不会受到更改了系统时间而影响。如果使用了system_clock,在执行任务时,用户更改了系统时间,则下次调用就会出现时间异常等问题。

你可能感兴趣的:(C++)