Linux实现定时器

定时器实现的方式有很多。
1.alarm产生一个超时信号,在信号处理函数中再次alarm一下。
2.libevent和nginx的做法是用epoll/poll的超时时间来做,不过这需要额外的二叉堆/红黑树结构来维护。
3.muduo中使用了一种新的方式timerfd_*非常方便,使用的时候像IO事件一样直接扔进reactor中即可。

下面是代码:

#include <sys/timerfd.h>  
#include <sys/epoll.h>
#include <unistd.h>
#include <stdint.h>
#include <iostream>
using namespace std;

const int EPOLL_SIZE = 10;

int main(int argc, char* argv[])
{
    int tfd, epfd, nfds;
    struct epoll_event event;
    struct epoll_event events[EPOLL_SIZE];

    //创建timerfd, CLOCK_REALTIME为绝对时间,TFD_NONBLOCK为非阻塞
    tfd = timerfd_create(CLOCK_REALTIME, TFD_NONBLOCK);  
    if (tfd < 0)
    {
    cerr << "timerfd_create error!" << endl;
    return -1;
    }    
    struct timespec startTime, intervalTime;
    startTime.tv_sec = 0;    
    startTime.tv_nsec = 1;                                //相当于立即到达超时时间
    intervalTime.tv_sec = 3;                             //首次超时后,每三秒超时一次
    intervalTime.tv_nsec = 0;
    struct itimerspec newValue;
    newValue.it_value = startTime;
    newValue.it_interval = intervalTime;
    //设置超时时间,且为相对时间
    if (timerfd_settime(tfd, 0, &newValue, NULL) < 0)
    {
    cerr << "timerfd_settime error!" << endl;
    return -1;
    }
    //用epoll来监听描述符
    epfd = epoll_create(EPOLL_SIZE);
    if (epfd < 0)
    {
    cerr << "epoll_create error!" << endl;
    return -1;
    }

    event.data.fd = tfd;
    event.events = EPOLLIN;
    if (epoll_ctl(epfd, EPOLL_CTL_ADD, tfd, &event) < 0)
    {
    cerr << "epoll_ctl error!" << endl;
    return -1;
    }

    uint64_t count = 0;
    while (1)
    {
    //非阻塞等待
    nfds = epoll_wait(epfd, events, EPOLL_SIZE, 0);
    if (nfds == 0) continue;
    for (int i = 0; i < nfds; i++)
    {
        if (events[i].events & EPOLLIN)
        {
        uint64_t data;
        read(events[i].data.fd, &data, sizeof(uint64_t));
        count += data;
        cout << "read: " << data << ", timer count: " << count << endl;
        }
    }
    }
    return 0;
}

参考:
http://www.jianshu.com/p/66b3c75cae81

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值