8. 异步操作

对于游戏开发而言,经常使用到异步相关操作,因此在使用moduleframework之前应该提供一个异步操作的类。 以后相关的异步操作均继承这个类

AsyncOperation:

先贴出代码:

 

#ifndef __ASYNC_OPERATION_H__

#define __ASYNC_OPERATION_H__

#include <boost/function.hpp>



class AsyncOperation

{

public:

    typedef boost::function(void<AsyncOperation*>) TypeOnExecute;

    typedef boost::function(void<AsyncOperation*>) TypeOnComplete;

    typedef boost::function(void<AsyncOperation*>) TypeOnAborted;



    // 委托执行函数

    explicit AsyncOperation(TypeOnExecute onExecute)

        :_onExecute(onExecute)

    {

        if(!_onExecute) throw "onExecute is NULL";

    }



    virtual AsyncOperation(){}



    void Execute(TypeOnComplete onComplete, TypeOnAborted onAorted = NULL)

    {

        if (!_onComplete) throw "onComplete is NULL"

        _onComplete = onComplete;

        _onAborted = onAorted;

        _onExecute(this);

    }



    virtual void Abort()

    {



    }



    void Complete()

    {

        _onComplete(this);

    }



private:

    TypeOnExecute _onExecute;

    TypeOnComplete _onComplete;

    TypeOnAborted _onAborted;



};

#endif


真正的执行函数是Execute 另外提供了一个完成 和终止的接口。

 

这个类应该比较简单。

在此类的基础上构建一个异步队列。  AsyncQueue继承该类

 

#ifndef __ASYNC_QUEUE_H__

#define __ASYNC_QUEUE_H__



#include <glog/logging.h>

#include "AsyncOpertaion.hpp"

#include <boost/bind.hpp>

#include <deque>



using namespace std;



class AsyncQueue : public AsyncQueue

{

public:

    // 构造函数默认调用ExecuteNextChild来启动整个异步进程

    AsyncQueue(): AsyncOperation(boost::bind(&AsyncQueue::ExecuteNextChild, this, _1))

        , _abortFlag(false)

    {



    }

    ~AsyncQueue()

    {

        TypeOptQueue::iterator it = _queue.begin();

        for (; it != _queue.end(); ++it)

        {

            delete *it;

        }

    }



    // 加入队列

    void Push(AsyncOperation* operation)

    {

        _queue.push_back(operation);

    }



    // 终止执行

    void Abort()

    {

        if(_queue.empty()) return;

        _abortFlag = true;

        AsyncOperation* front = _queue.front();

        front->Abort(); // 终止队列首位的执行

    }



private:

    void ExecuteNextChild(AsyncOperation* operation)

    {

        if(_queue.empty())

        {

            LOG(ERROR) << "Async Queue is Empty!";

            return;

        }

        // 迭代执行_queue中的操作

        AsyncOperation* front = _queue.front();

        front->Execute(boost::bind(&AsyncQueue::OnChildComplete, this, _1));

    }



    void OnChildComplete(AsyncOperation* operation)

    {

        // 移除已执行的异步操作

        _queue.pop_front();

        delete operation;

        if (_queue.empty())

        {

            // 通知队列执行完成

            Complete();

            return;

        }



        if (_abortFlag && _onAborted)

        {

            _onAborted(this);

        }else

        {

            // 迭代执行

            ExecuteNextChild(0);

        }

    }



private:

    typedef deque<AsyncOperation*> TypeOptQueue; // 使用队列来包装

    TypeOptQueue _queue;

    bool _abortFlag; 

};



#endif


这里一个巧妙指出在于 如果迭代执行整个异步队列, 注意看 构造函数和OnExecuteNextChild 这两点 。  

 


至此我们构建了一个初步的异步队列。以后其他各个模块均继承他们。 比如模块的初始化等

 

你可能感兴趣的:(异步)