Частенько я программу для контроллера описываю в виде графа состояний. Имеется одна глобальная переменная STATE, в зависимости от значения которой вызываются соответствующие подпрограммы, например вот так:
while(1)
{
int res;
int cmd = getCommand();
switch(STATE)
{
case STATE_1:
res = sub_prog1(cmd);
break;
case STATE_2:
res = sub_prog2(cmd);
break;
...
..
case STATE_N:
res = sub_progN(cmd);
}
STATE = res;
}
В этот раз состояний оказалось многовато, более 20 штук (а точнее - 22). Возможно, я что-то не то сделал, и все это можно было как-то иначе описать, но... пока не хочется, думаю что и так все будет фурыкать. Другое дело, что неохота было такой громадный оператор switch расписывать. Тут я вовремя вспомнил про указатели на функции. Хорошая штука, только на работе, млин, ни одной книжки по Сям не оказалось, а я, как на зло, забыл, как оно называется. Искал в инете по словам "процедурный тип", "функциональный тип" и т.п, и ессно, ничего нужного мне не нашел. На скорую руку написал по памяти:
typedef int (*StateHandler)(int);
По моим представлениям, такое объявление дает понять компилятору, что StateHandler - это указатель на функцию, возвращающую тип int и принимающую один параметр тоже типа int. Как потом оказалось, правильно я его все-таки объявил :) После этого приведенный в начале поста код можно переписать уже вот так:
StateHandler handlers[] = {sub_prog1, sub_prog2, ... sub_progN};
while(1)
{
cmd = getCommand();
STATE = (*(handlers[STATE]))(cmd);
}
По-моему, получается короче, да и работать наверняка будет побыстрее. Главное, чтобы значения переменной STATE шли по-порядку, но имхо, это как раз не проблема.