1

Currently, I do delayed function call with help of a timer and a stack. Something like that:

enum fnc_t {
    _FNC_1,
    _FNC_2,
    __MAX_FNC
};

typedef std::deque<fnc_t> calls_t;
calls_t _calls; 

void fnc1() {
    _calls.push_back( _FNC_1 );
}

void fnc2() {
    _calls.push_back( _FNC_2 );
}

void onTimer() {
    while ( _calls.front() ) {
        if ( _calls.front() == _FNC_1 ) {
           doFnc1();
        } else if ( _calls.front() == _FNC_2 ) {
           doFnc2();
        }

        _calls.pop_front();
    }
}

No I need to add arguments to my functions fnc1 and fnc2, i.e.

void fnc1( std::string a1 ){} 
void fnc2( int a21, void * a22 ) {}

and use them in my delayed calls, i.e.

...
doFnc1( a11 );
...
doFnc( a21, a22 );

What is the best way to achieve this ? I can implement this task with some struct instead of fnc_t which will be contain some additional space for common params, for example:

struct fnc_call_t {
  fnc_t fnc;
  void * p[5];
}

In my opinion this way is not so convenience. Any other solutions?

sim
  • 756
  • 6
  • 18
  • What about using (member) function pointers instead of the `enum` and dispatch? – πάντα ῥεῖ Jun 28 '14 at 11:28
  • 4
    Use [`std::function`](http://en.cppreference.com/w/cpp/utility/functional/function) and [`std::bind`](http://en.cppreference.com/w/cpp/utility/functional/bind) – Captain Obvlious Jun 28 '14 at 11:29
  • 1
    Related: You may find [this answer interesting](http://stackoverflow.com/a/7858971/1322972), if nothing else than for some alternative ideas (note, the accepted answer really is the cat's whiskers). – WhozCraig Jun 28 '14 at 11:32
  • @Captain is it c++11? I can not use it. – sim Jun 28 '14 at 11:39
  • `` header is part of c++03 afair. – didierc Jun 28 '14 at 11:46
  • 2
    Alternatively you can use [`boost::function`](http://www.boost.org/doc/libs/1_55_0/doc/html/function.html) and [`boost::bind`](http://www.boost.org/doc/libs/1_55_0/libs/bind/bind.html). – Captain Obvlious Jun 28 '14 at 11:46

1 Answers1

1

Unfortunately I can not use boost or C++11 so I've done it in the following way

class Call {
public:
    virtual void run() = 0;

public:
    virtual ~Call(){
    }
};

class CallFnc1: public Call {
public:
    void run() {
        doFnc1(a,q);
    }

public:

    CallFnc1( int a, std::string q ) : _a(a),_q(q){
    }

    ~CallFnc1(){
    }

private:
    int _a;
    std::string _q;
};

typedef std::deque<Call*> calls_t;
calls_t _calls; 

int fnc1( int a, std::string q) {
    _calls.push_back( new CallFnc1(a,q) );
}

void onTimer() {
    while ( _calls.front() ) {
         Call * q = _calls.front();
         q->run();
         delete q;
        _calls.pop_front();
    }
}
sim
  • 756
  • 6
  • 18