Я бы наверное сделал, что-то типа такого:
typedef void (*HandlerFunction)(<params>); // or typedef std::function<void (params)> HandlerFunction;
struct HandlerKey { int m; int n; } // реализуем так же операторы для сравнения, конструктор ...
typedef std::map<HandlerKey, HandlerFunction> HandlerMap;
void init(HandlerMap & m)
{
m[HandlerKey(m1, n2)] = HandlerFunction1;
m[HandlerKey(m1, n2)] = HandlerFunction2;
m[HandlerKey(m2, n1)] = HandlerFunction1;
m[HandlerKey(m2, n2)] = HandlerFunction3;
...
}
void process(const HandlerKey & key, <params>)
{
HandlerMap::iterator it = handlerMap.find(key);
if (it == handlerMap.end())
std::runtime_error("No handler for key " + key.toString());
it->second(<params>);
}
Я сделал callback стайл, но если активно используется ООП, то наверное лучше что-то типа функтора сделать, т.к. скорее всего хендлеры используют схожий функционал, который можно расшарить через базовые классы.