一种有限状态机的C语言实现

状态机的原理就不说了,先给出状态机的转换图,很简单
一种有限状态机的C语言实现


实现的思路是这样的:
1、用函数指针表示状态(状态函数)。
2、状态函数接受一个参数(event),并根据event决定下一个状态。
3、状态函数返回一个函数指针,此函数指针的类型也是状态函数指针。即状态函数返回一个指向下一个状态函数的指针。
4、由于返回值是和原函数相同类型的函数指针,要定义成这样
typedef func_ptr_t (*func_ptr_t)(int);
   但是C语言中不允许这样定义一个函数指针。所以只能寻找变通的方法,这个方法就是强制类型转换。我们可以按照以下方式定义
typedef void (*func_ptr_ret_t)(int);
typedef func_ptr_ret_t (*func_ptr_t)(int);
   使用的时候进行强制类型转换,将返回值转换为func_ptr_t,这样就实现了一个能够返回与原函数相同类型函数指针的函数。
func_ptr_t func;
func_ptr_t func2; 
func = (func_ptr_t)func2(参数);
   知道了这些后,就可以写一个简单的状态机了。
// 定义函数指针类型
typedef void (*state_ret)(int event);
typedef state_ret (*state)(int event);

// 申明状态函数
state_ret STATE1(int event);
state_ret STATE2(int event);
state_ret STATE3(int event);

// 事件列表
enum EVENT_NUM{
  EVENT1,
  EVENT2,
  EVENT3,
  EVENT4,
};

int main(void)
{
  int event;
  int i = 0;
  
  // 初始状态设置为STATE1
  state curState;
  curState = STATE1;
  while(1){
    
    // 每次循环改变一次event值,实际中一般由外部事件驱动
    switch(i%5){
      case 0: event = EVENT1; break;
      case 1: event = EVENT2; break;
      case 2: event = EVENT3; break;
      case 3: event = EVENT4; break;
      case 4: event = EVENT2; break;
      default: break;
    }

    // 运行当前状态函数,返回下一状态函数指针,并保存起来
    curState = (state)curState(event);
    i++;
  }
  return 0;
}

// 状态1函数的实现
state_ret STATE1(int event)
{
  // 设置当前状态
  state_ret curState = (state_ret)STATE1;

  // 根据event确定下一状态
  switch(event){
    case EVENT1: curState = (state_ret)STATE2; break;
    case EVENT3: curState = (state_ret)STATE3; break;
    default: break;
  }

  // 返回下一状态函数指针
  return curState;
}

// 状态2函数实现
state_ret STATE2(int event)
{
  state_ret curState = (state_ret)STATE2;
  switch(event){
    case EVENT2: curState = (state_ret)STATE1; break;
    default: break;
  }
  return curState;
}

// 状态3函数实现
state_ret STATE3(int event)
{
  state_ret curState = (state_ret)STATE3;
  switch(event){
    case EVENT4: curState = (state_ret)STATE2; break;
    default: break;
  }
  return curState;
}


  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
#include int main() { int state_key = 1; //钥匙状态 为1时钥匙区有钥匙,为时钥匙区 无钥匙 int state_hold = 0; // 钥匙持有状态 为1时持有钥匙,为时 未持有钥匙 int state_door = 0; //门状态 0:关闭 1:打开 int state_lock = 1; //上锁状态 1:上锁 0:解锁 int order; // 用于存放用户输入指令 printf("this is a game.\n"); printf ("if you want to OPEN THE DOOR ,input 1\n"); printf ("if you want to CLOSE THE DOOR ,input 2\n"); printf ("if you want to LOCK THE DOOR ,input 3\n"); printf ("if you want to UNLOCK THE DOOR,input 4\n"); // printf ("if you want to LOCK THE DOOR ,input 5\n"); printf("please input the order\n"); while(1) { scanf("%d",&order); // if(order!=(1||2||3||4)) // { // printf("worng input ,please input again.\n"); // continue; // } switch(order) { case 1 : if(state_door==1) { printf("the door has been opened before\n"); break; } if(state_lock==1) { printf("the door has been lock\n"); break; } state_door=1; break; case 2: if(state_door==0) { printf("the door has been closed before\n"); break; } if(state_lock==1) { printf("the door has been lock\n"); break; } state_door=0; break; case 3: if(state_door==1) { printf("the door has been opened before\n"); break; } if(state_lock==1) { printf("the door has been lock\n"); break; } state_lock=1; break ; case 4: if(state_door==1) { printf("the door has been opened before\n"); break; } if(state_lock==0) { printf("the door has not been lock\n"); break; } state_lock=0; break ; } } }

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值