OperationWithLambda

#ifndef OPERATION_D8F2BC78_108D_4219_9D6E_F1728D1B8C95_H__
#define OPERATION_D8F2BC78_108D_4219_9D6E_F1728D1B8C95_H__
#include 

class  Operation 
{
	enum OperationState
	{
		OPERATION_IDLE = 0,
		OPERATION_STARTING,
		OPERATION_RUNNING,
		OPERATION_CANCELLING,
		OPERATION_FINISHED
	};
public:
    Operation();
	Operation(const std::string& name);
    virtual ~Operation();
public:
	virtual void processOpertion() = 0;

public:
	virtual void process();
	virtual void release();
    inline std::string name() const { return m_name; }
    inline void set_name(__in std::string name){ m_name = name; }
private:
	OperationState			m_state;
    std::string				m_name;
};
#endif
#ifndef OPERATIONMANAGER_7EEF3272_2557_4A76_9C25_67D4639F40DB_H__
#define OPERATIONMANAGER_7EEF3272_2557_4A76_9C25_67D4639F40DB_H__

#include 
#include 
#include 
#include 
#include 

class Operation;
class OperationManager
{
public:
	OperationManager() = default;
	~OperationManager();
	OperationManager(OperationManager&) = delete;
	OperationManager(OperationManager&&) = delete;
	OperationManager& operator= (OperationManager&) = delete;
	OperationManager& operator= (OperationManager&&) = delete;
public:
	uint32_t startup();
    void shutdown( int seconds = 2000);
    uint32_t startOperation( Operation* pOperation, int delay);
    uint32_t startOperationWithLambda(std::function operationRun
        , int delay
        , std::string oper_name);
    uint32_t clearOperationByName(std::string oper_name);
private:
	std::list      m_vecDelayOperations;
	std::list      m_vecRealtimeOperations;
	std::mutex					m_cvMutex; // 互斥锁.
	std::condition_variable		m_CV; // 条件变量
	std::mutex					m_mutexOperation;
	bool                        m_bContinue = true;
	std::thread					m_operationThread;
};

OperationManager* getOperationManager();
#endif// OPERATIONMANAGER_7EEF3272_2557_4A76_9C25_67D4639F40DB_H__
#include "Operation.h"
#include 

const std::string OPERATION_NAME_COMMON = "operation_name_common";

Operation::Operation()
:m_state(OPERATION_IDLE)
, m_name(OPERATION_NAME_COMMON)
{

}

Operation::Operation(const std::string& name)
:m_state(OPERATION_IDLE)
,m_name(name)
{

}

Operation::~Operation()
{

}

void Operation::process()
{
	try
	{
		m_state = OPERATION_RUNNING;
		processOpertion();
	}
	catch (std::exception& exc)
	{
		assert(false);
		
	}
	catch (...)
	{
		assert(false);
	}
	m_state = OPERATION_FINISHED;
}

void Operation::release()
{
	delete this;
}
/******************************************************************************/
#include "Operation.h"
#include "OperationManager.h"
#include 
#include 

namespace
{
	class LambdaOperation : public Operation
	{
	public:
		LambdaOperation(std::function operationRun)
			:m_operationRun(operationRun)
		{
		}

		virtual void processOpertion()
		{
			m_operationRun();
		}
		virtual void release()
		{
			delete this;
		}

	private:
		std::function m_operationRun;
	};
}

uint32_t OperationManager::startup()
{
	m_operationThread = std::thread([&]
	{
		std::unique_lock  lck(m_cvMutex);
		Operation* pOperation = nullptr;
		while (m_bContinue)
		{
			if (!m_bContinue)
				break;
			if (m_vecRealtimeOperations.empty())
				m_CV.wait(lck);
			if (!m_bContinue)
				break;
			{
				std::lock_guard lock(m_mutexOperation);
				if (m_vecRealtimeOperations.empty())
					continue;
				pOperation = m_vecRealtimeOperations.front();
				m_vecRealtimeOperations.pop_front();
			}

			if (!m_bContinue)
				break;

			if (pOperation)
			{
				pOperation->process();
				pOperation->release();
			}
		}
	});

	return 1;
}

void OperationManager::shutdown( int seconds /*= 2000*/)
{
	m_bContinue = false;
	m_CV.notify_one();
	if (m_operationThread.joinable())
		m_operationThread.join();

	{
		std::lock_guard locker(m_mutexOperation);
		for (Operation* pOper : m_vecRealtimeOperations)
		{
			try
			{
				pOper->release();
			}
			catch (...)
			{
			}
		}
		m_vecRealtimeOperations.clear();
	}

	for (Operation* pOper : m_vecDelayOperations)
	{
		delete pOper;
		pOper = 0;
	}
	m_vecDelayOperations.clear();
}

uint32_t OperationManager::startOperation( Operation* pOperation, int delay)
{
	assert(pOperation);
	if (0 == pOperation)
	{
		return 0;
	}

	if (delay > 0)
	{
	}
	else
	{
		std::lock_guard locker(m_mutexOperation);
		m_vecRealtimeOperations.push_back(pOperation);
		m_CV.notify_one();
	}

	return 1;
}

uint32_t OperationManager::startOperationWithLambda(std::function operationRun
                                                            , int delay
                                                            , std::string oper_name)
{
    LambdaOperation* pLambdaOper = new LambdaOperation(operationRun);
    pLambdaOper->set_name(oper_name);
    return startOperation(pLambdaOper, delay);
}

uint32_t OperationManager::clearOperationByName(std::string oper_name)
{
    std::lock_guard locker(m_mutexOperation);
    auto iter = std::remove_if(m_vecRealtimeOperations.begin(), m_vecRealtimeOperations.end(),
        [=](Operation* pOper)
    {
        if (pOper->name() == oper_name)
        {   
            pOper->release();
            return 1;
        }
        return 0;
    });

    if (iter != m_vecRealtimeOperations.end())
    {
        m_vecRealtimeOperations.erase(iter, m_vecRealtimeOperations.end());
    }

    return 1;
}

OperationManager::~OperationManager()
{
	try
	{
		shutdown();
	}
	catch (...)
	{
		assert(0);
	}
}

OperationManager* getOperationManager()
{
	static OperationManager manager;
	return &manager;
}

teamtalk 在线程操作闭包

你可能感兴趣的:(网络编程,c++,开发语言)