Dean
Dean

Reputation: 138

c++ - other way of implementing function calls in switch cases

I've got code below:

void CashFlow::execute (int cmd)
{
    switch(cmd):
    {
        case BUY:
            BuyProc ();
            break;
        case SELL:
            SellProc ();
            break;
         ......
    }
}

What I'm thinking of doing is maybe create a map like std::map <int, void (CashFlow::*)()> CashflowProcs;

Then maybe use mCashFlowProcs = boost::assign::map_list_of (BUY, &CashFlow::BuyProc)(...etc)(..Etc.);

Then I can call it like (this->(mCashFlowProcs [cmd]))();

How do I turn this into template so it can be reused? Could there be issues with this implementation?

Note that I am not using C++11

Upvotes: 1

Views: 140

Answers (1)

quantdev
quantdev

Reputation: 23803

Could there be issues with this implementation?

Yes, it is hard to maintain, as adding/removing Command would need a lot of maintenance, would be error prone, and difficult to test. So I suggest a design change before trying to just improve this particular code.

1 - If you can change your design:

Use a class to represent a Command

class Command
{
    public:
        virtual void Execute() = 0;
        virtual ~Command() {};;
};

class BuyCommand : public Command
{
    public:
        virtual void Execute() { cout << "BUY"; }
};

class SellCommand : public Command
{
    public:
        virtual void Execute() { cout << "SELL"; }
};

// ...
Command* bc = new BuyCommand();
// ...
bc->Execute();

2 - If (unfortunately) you cant change design that way

If the cmd enumeration is known at compile time, and has a limited size, you can use an array of boost::function, and you should definitely regroup your command in an enum instead of using an int.

enum { BUY = 0; SELL = 1; NB_CMDS= 2 };
...
boost::array<NB_CMDS, boost::function<void()>>  // N is the number of commands.

indexing your array with, cmd, you simply call the function that has the index cmd in this array.

If you don't know at compile time how many commands/functions you will need, you might need to replace the array by a std::vector.

If one day you can use C++11, replace boost:: by std:: in the above snippets.

Upvotes: 1

Related Questions