Linux下的时间函数

2020-04-12  本文已影响0人  Jimmy_Nie

0. 写在前面

最近在做一个项目,频繁的需要使用到获取时间,包括相对时间、绝对时间等,发现C/C++和linux本身都提供了很多的API接口,看的眼花缭乱的,下面针对这些情况,我统一的做一下分类讲述。

1. 基本概念

所谓时间精度,也成为时间颗粒,是指系统/函数所能给出的时间的最小单位;通常内核和应用层给出的时间精度各不相同:

  • 内核:tick(节拍)即CPUP的时钟定时器的一次终端;Jiffies用来记录自系统启动以来产生的节拍的总数,因此最小的时间颗粒为 Jiffies/Hz

2. Linux API

2.1 获取相对时间 (即系统起到后到目前的时间段)

1). sysinfo()

函数原型

#include <sys/sysinfo.h>    //头文件
int sysinfo(struct sysinfo *info);  //函数原型

结构体类型

struct sysinfo {  //结构体数据类型
           long uptime;               /* Seconds since boot */
           unsigned long loads[3];     /* 1, 5, and 15 minute load averages */
           unsigned long totalram;    /* Total usable main memory size */
           unsigned long freeram;      /* Available memory size */
           unsigned long sharedram;   /* Amount of shared memory */
           unsigned long bufferram;   /* Memory used by buffers */
           unsigned long totalswap;   /* Total swap space size */
           unsigned long freeswap;    /* swap space still available */
           unsigned short procs;      /* Number of current processes */
           char _f[22];               /* Pads structure to 64 bytes */
};

实例演示

#include <stdio.h>
#include <sys/sysinfo.h>
#include <time.h>
#include <errno.h>
#include <stdlib.h>
#include <string.h>
int main(void)
{
    struct sysinfo info;
    char run_time[128];
    if (sysinfo(&info)) {
        fprintf(stderr, "Failed to get sysinfo, errno:%u, reason:%s\n",errno, strerror(errno));
        return -1;
    }
    long timenum=info.uptime;
    printf("The timenum=%ld\n", timenum);
    int runday=timenum/86400;
    int runhour=(timenum%86400)/3600;
    int runmin=(timenum%3600)/60;
    int runsec=timenum%60;
    bzero(run_time, 128);
    sprintf(run_time,"系统已运行:%d天%d时%d分%d秒",runday,runhour,runmin,runsec);
    printf("--->%s\n",run_time);
    return 0; 
}

运行结果

The timenum=127432
--->系统已运行:1天11时23分52秒

3. C lib

4. C++ STL

#include<iostream>
#include <chrono>
#include <thread>
#include <cstdint>
#include <cmath>
#include <ctime>
using namespace std;

class SimpleTime
{
public:
    typedef std::chrono::duration<long long, std::ratio<1,1000000> > macrosec_type;    
    typedef std::chrono::duration<long long, std::milli> millisec_type;    
    typedef std::chrono::duration<long long> seconds_type;    
    typedef std::chrono::duration<int, std::ratio<60> > minute_type;    
    typedef std::chrono::duration<int, std::ratio<60*60> > hour_type;    
    typedef std::chrono::duration<int, std::ratio<60*60*24> > day_type;    

public:
    SimpleTime(){ start(); }

    //sleep milliseconds / seconds
    void sleep_msec(double num){
        long long _num = static_cast<long long>(round(num)); 
        std::this_thread::sleep_for(std::chrono::milliseconds(_num));
    }
    void sleep_sec(double num) { double _num=num*1e3*1.0; sleep_msec(_num); }

    //Get the point time
    std::string get_date_string(){
        std::chrono::system_clock::time_point today = std::chrono::system_clock::now();
        time_t tt = std::chrono::system_clock::to_time_t(today);
        return ctime(&tt);
    }
    int get_timezone(){
        int timezone = 0;
        time_t t1, t2;
        struct tm *tm_local, *tm_utc;
    
        time(&t1);//返回从公元1970年1月1日的UTC时间从0时0分0秒算起到现在所经过的秒数
        tm_utc = gmtime(&t1);//返回的时间日期未经时区转换,格林尼治时间
        t2 = mktime(tm_utc);//转换为秒
        timezone = (t1 - t2) / 3600;
    
        return timezone;
    }

    //Get the milliseconds/seconds from epoch
    uint64_t since_epoch_msec(){
        std::chrono::time_point<std::chrono::system_clock, std::chrono::milliseconds> tp = \
            std::chrono::time_point_cast<std::chrono::milliseconds>(std::chrono::system_clock::now());
        return (tp.time_since_epoch().count());
    }
    uint64_t since_epoch_sec(){
        return (static_cast<uint64_t>(round(since_epoch_msec()/1000)));
    }
    
    //Get the duration sinch system startup
    uint64_t elapsed_usec(){
        return static_cast<uint64_t>(std::chrono::duration_cast<std::chrono::microseconds>(std::chrono::steady_clock::now() - m_start).count());
    }   
    uint64_t elapsed_msec(){
        return static_cast<uint64_t>(round(elapsed_usec()/1000));
    }   
    uint64_t elapsed_sec(){
        return static_cast<uint64_t>(round(elapsed_usec()/1000000));
    }

    //restart the startup time 
    void start(){ m_start = std::chrono::steady_clock::now(); }

private:
    std::chrono::steady_clock::time_point m_start;
};

void sp(int j)
{
    SimpleTime tm;
    for(int i=1; i<100; i++)
    {
        tm.sleep_msec(2.5e3);
        cout<<j<<"The time is: TZ:"<<tm.get_timezone()<<" : " <<tm.get_date_string()<<endl;
        /*
        cout<<j<<" : sleep "<<2.5*i<<"seconds"<<endl;
        cout<<"Now time is: "<<tm.get_date_string() << '\n'<<"since epoch is:"<<tm.since_epoch_msec()<<"ms" <<"\n"<< " since_epoch: "<<tm.since_epoch_sec()<<" seconds"<<endl;

        cout<<"seconds elapsed: "<<tm.elapsed_sec()<<"s"<<endl;
        cout<<"mseconds elapsed: "<<tm.elapsed_msec()<<"ms"<<endl;
        cout<<"useconds elapsed: "<<tm.elapsed_usec()<<"us"<<endl;
        */
    }
}

int main()
{
    thread t1(sp, 1);
    thread t2(sp, 2);
    thread t3(sp, 3);
    while(true);
}
上一篇下一篇

猜你喜欢

热点阅读