有些场景下,状态机可以使得我们的程序代码变得简洁,可扩展,可维护。
先看下状态迁移图。
代码设计分为五个步骤完成状态机。
#include// 第一步:定义两个事件 typedef enum { STOP, PLAY_PAUSE, EVE_MAX } EVENT; // 第二步:定义三种状态 typedef enum { PLAY_STA, PAUSE_STA, STOP_SAT, STA_MAX } STA; typedef void (*func)(void *p); // 第三步:定义状态机结构体 typedef struct { EVENT evn; STA currentSta; STA nextSta; func handle; } M_TB; void func_1(void *p) {}; void func_2(void *p) {}; void func_3(void *p) {}; void func_4(void *p) {}; void func_5(void *p) {}; void func_none(void *p) {}; // 第四步:定义状态迁移表 const M_TB statFunc[STA_MAX][EVE_MAX] = { { {STOP, PLAY_STA, STOP_SAT, func_1}, {PLAY_PAUSE, PLAY_STA, PAUSE_STA, func_2}, }, { {STOP, PAUSE_STA, STOP_SAT, func_3}, {PLAY_PAUSE, PAUSE_STA, PLAY_STA, func_4}, }, { {STOP, STOP_SAT, STOP_SAT, func_none}, {PLAY_PAUSE, STOP_SAT, PLAY_STA, func_5}, }, }; typedef struct MP3 { STA sta; } MP3; // 第五步:定义事件驱动处理函数 void process(EVENT eve, MP3 *mp3, void *pmsg) { statFunc[mp3->sta][eve].handle(pmsg); mp3->sta = statFunc[mp3->sta][eve].nextSta; } int main() { int msg = 10; MP3 mp3 = {PAUSE_STA}; printf("%d n", mp3.sta); process(PLAY_PAUSE, &mp3, (void *)&msg); printf("%d n", mp3.sta); process(PLAY_PAUSE, &mp3, (void *)&msg); printf("%d n", mp3.sta); process(PLAY_PAUSE, &mp3, (void *)&msg); printf("%d n", mp3.sta); process(STOP, &mp3, (void *)&msg); printf("%d n", mp3.sta); return 0; }



