共享boost::deadline_timer封装模板,可以接受任何函数对象

//
// fox_timer.hpp
// ~~~~~~~~~~~~~~~~
//
// Copyright (c) 2014-2015 yoen.xu (181471112 at  qq dot com)
//
//说明:该类线程安全
//eg:
//	启动:	fox_timer::run(io_, func, interval);运行一个定时器:T 为func的返回类型,当T为int的时候(范围值-1代表取消定时器,0定时器时间不变 >0重置定时器时间)
//	停止:	fox_timer::stop_all();取消所有定时器(在io退出之前要先调用)

#ifndef  FOX_TIMER_HPP
#define  FOX_TIMER_HPP

#if defined(_MSC_VER) && (_MSC_VER >=1200)
#pragma once
#endif // defined(_MSC_VER) && (_MSC_VER >= 1200)

#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
#include 
using namespace boost;
using namespace boost::asio;
namespace thefox{

	template 	
	class fox_timer:public boost::enable_shared_from_this< fox_timer >{
	public:
		typedef boost::function func_t;
		typedef boost::shared_ptr< fox_timer > type;
		static std::list timer_list_ ;
		static boost::mutex mutex_;
		static size_t s_use_;
		static void run(io_service& ios,func_t func,const long seconds=DEFAULT_INTERVAL_SECONDS){
			type ptr = boost::make_shared< fox_timer >(ios, func,seconds);

			if (ptr)
			{
				{
					boost::unique_lock lock(mutex_);
					fox_timer::timer_list_.push_back(ptr);
					++s_use_;
				}
				ptr->start();
			}else
				throw std::runtime_error("run unbound fox_timer");
		}

		static void stop_all(){
			boost::unique_lock lock(mutex_);
			for (std::list::iterator itr=timer_list_.begin(); itr!=timer_list_.end();)
			{
				(*itr)->cancle();
				itr = timer_list_.erase(itr);
				--s_use_;
			}
		}

		explicit  fox_timer(io_service& ios, func_t func, const long seconds=DEFAULT_INTERVAL_SECONDS)
			:f_(func),interval_(seconds)
			,t_(ios,posix_time::seconds(seconds))
		{
			assert(typeid(boost::result_of::type) == typeid(ReturnType));
		}

		~fox_timer()
		{
			cancle();
		}

		void set_interval(const long seconds){
			interval_ = seconds;
		}

		void start(){
			do_wait();	
		}



	private:
		//default dead time(seconds)
		const static long DEFAULT_INTERVAL_SECONDS = 3;
		func_t f_;
		//async_wait callback function
		deadline_timer t_;
		long interval_;

		void cancle(){
			t_.cancel();
		}
		void do_wait(){
			t_.expires_from_now(posix_time::seconds(interval_));
			t_.async_wait(boost::bind(&fox_timer::call_func,shared_from_this(),boost::asio::placeholders::error));	
		}
		void call_func(const system::error_code& err){
			if (err){
				return;
			}
			else{
				assert(!f_.empty());
				f_();
				do_wait();
			}
		}



	};

	template  boost::mutex fox_timer::mutex_ ;
	template  std::list< typename fox_timer::type  > fox_timer::timer_list_ ;
	template  size_t fox_timer::s_use_=0; 
	
	//模板成员函数特化
	template<> 
	void fox_timer::call_func(const system::error_code& err){
		if (err){
			return;
		}
		else{
			assert(!f_.empty());
			int iret = f_();
			assert(iret >= -1);
			switch(iret){
			case -1:
				return;
			case 0:
				break;
			default:
				set_interval(iret);
			}
			do_wait();
		}
	}
}//namespace fox
#endif //FOX_TIMER_HPP


你可能感兴趣的:(c++开发)