C++11 定时器

/*
 * File: Timer
 * Module: service
 * Description:定时器类
 * Author: 
 */
#pragma once

#include<functional>
#include<chrono>
#include<thread>
#include<atomic>
#include<memory>
#include<mutex>
#include<condition_variable>

class Timer{
public:
    Timer() :expired_(true), try_to_expire_(false){
    }

    Timer(const Timer& t){
        expired_ = t.expired_.load();
        try_to_expire_ = t.try_to_expire_.load();
    }
    ~Timer(){
        Expire();
    }

    void StartTimer(int interval, std::function<void()> task){
        if (expired_ == false){
            return;
        }
        expired_ = false;
        std::thread([this, interval, task](){
            while (!try_to_expire_){
                std::this_thread::sleep_for(std::chrono::milliseconds(interval));
                task();
            }
            {
                std::lock_guard<std::mutex> locker(mutex_);
                expired_ = true;
                expired_cond_.notify_one();
            }
        }).detach();
    }

    void Expire(){
        if (expired_){
            return;
        }

        if (try_to_expire_){
            return;
        }
        try_to_expire_ = true;
        {
            std::unique_lock<std::mutex> locker(mutex_);
            expired_cond_.wait(locker, [this]{return expired_ == true; });
            if (expired_ == true){
                try_to_expire_ = false;
            }
        }
    }

    template<typename callable, class... arguments>
    void SyncWait(int after, callable&& f, arguments&&... args){

        std::function<typename std::result_of<callable(arguments...)>::type()> task
                (std::bind(std::forward<callable>(f), std::forward<arguments>(args)...));
        std::this_thread::sleep_for(std::chrono::milliseconds(after));
        task();
    }
    template<typename callable, class... arguments>
    void AsyncWait(int after, callable&& f, arguments&&... args){
        std::function<typename std::result_of<callable(arguments...)>::type()> task
                (std::bind(std::forward<callable>(f), std::forward<arguments>(args)...));

        std::thread([after, task](){
            std::this_thread::sleep_for(std::chrono::milliseconds(after));
            task();
        }).detach();
    }

private:
    std::atomic<bool> expired_;
    std::atomic<bool> try_to_expire_;
    std::mutex mutex_;
    std::condition_variable expired_cond_;
};


2、简单版本的定时器执行任务

time.h

#include <condition_variable>
#include <functional>
#include <memory>
#include <mutex>
#include <thread>

class Time {
 public:
  Time();
  ~Time();

  bool Init(size_t loop_interval_sec, const std::function<void(void)>& task);

 private:
  std::unique_ptr<std::thread> loop_thread_;
  std::mutex loop_cv_mtx_;
  std::condition_variable loop_cv_;
  int loop_interval_sec_;
  bool terminate_;
  std::function<void(void)> task_;
};

time.hpp

#include "timed_task.h"

#include <chrono>
#include <iostream>

Time::Time()
    : loop_thread_(nullptr)
    , loop_interval_sec_(0)
    , terminate_(false)
    , task_(nullptr) {
  
}

Time::~Time() {
  terminate_ = true;
  loop_cv_.notify_all();
  if (loop_thread_) {
    loop_thread_->join();
  }
}

bool Time::Init(size_t loop_interval_sec,
    const std::function<void(void)>& task) {
  if (loop_interval_sec == 0 || !task) {
    return false;
  }
  loop_interval_sec_ = loop_interval_sec;
  task_ = task;
  loop_thread_.reset(new std::thread([this]() {
    while (!terminate_) {
      std::unique_lock<std::mutex> lck(loop_cv_mtx_);
      loop_cv_.wait_for(lck, std::chrono::seconds(loop_interval_sec_));
      std::cout << "execute timed task" << std::endl;
      task_();
      if (terminate_) {
        break;
      }
    }
  }));
  return true;
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值