独立日记 2015年12月26日 day5 有限状态机 FSM
来源:互联网 发布:亿次元 淘宝 编辑:程序博客网 时间:2024/05/01 09:59
独立日记 2015年12 月26日 day5 有限状态机 FSM
今天的流水账:
2:00 入睡
11:40 起床
14:00~20:00 跑酷游戏
今天是高产出的一天。
有限状态机实现:
跑酷游戏中的主角有很多状态,跑、跳、二段跳、死亡。如果全部都用if/switch来切换状态,那代码就会有坏味道了,稍微多添加一个状态, 那么代码就会指数级增长。所以就实现了一个有限状态机来管理主角的状态。基本思路是,实现一个状态类和一个跳转类,状态类中用一个字典来存储跳转事件的名称和对应的跳转对象。跳转类充当一个结构体,负责存储源状态对象、目标状态对象、和跳转事件名称、和一个做为回调的函数指针。 上图。
然后实现一个状态机类来管理状态和跳转。贴上全部代码。
using UnityEngine; using System.Collections; using System.Collections.Generic;public class FSM { // 定义函数指针类型 public delegate void FSMTranslationCallfunc(); /// <summary> /// 状态类 /// </summary> public class FSMState { public string name; public FSMState(string name) { this.name = name; } /// <summary> /// 存储事件对应的条转 /// </summary> public Dictionary <string,FSMTranslation> TranslationDict = new Dictionary<string,FSMTranslation>(); } /// <summary> /// 跳转类 /// </summary> public class FSMTranslation { public FSMState fromState; public string name; public FSMState toState; public FSMTranslationCallfunc callfunc; // 回调函数 public FSMTranslation(FSMState fromState,string name, FSMState toState,FSMTranslationCallfunc callfunc) { this.fromState = fromState; this.toState = toState; this.name = name; this.callfunc = callfunc; } } // 当前状态 private FSMState mCurState; // 状态 Dictionary <string,FSMState> StateDict = new Dictionary<string,FSMState>(); /// <summary> /// 添加状态 /// </summary> /// <param name="state">State.</param> public void AddState(FSMState state) { StateDict [state.name] = state; } /// <summary> /// 添加条转 /// </summary> /// <param name="translation">Translation.</param> public void AddTranslation(FSMTranslation translation) { StateDict [translation.fromState.name].TranslationDict [translation.name] = translation; } /// <summary> /// 启动状态机 /// </summary> /// <param name="state">State.</param> public void Start(FSMState state) { mCurState = state; } /// <summary> /// 处理事件 /// </summary> /// <param name="name">Name.</param> public void HandleEvent(string name) { if (mCurState != null && mCurState.TranslationDict.ContainsKey(name)) { Debug.LogWarning ("fromState:" + mCurState.name); mCurState.TranslationDict [name].callfunc (); mCurState = mCurState.TranslationDict [name].toState; Debug.LogWarning ("toState:" + mCurState.name); } }}
测试代码
// Idle, // 闲置// Run, // 跑// Jump, // 一段跳// DoubleJump, // 二段跳// Die, // 挂彩 // 创建状态 FSM.FSMState idleState = new FSM.FSMState("idle"); FSM.FSMState runState = new FSM.FSMState("run"); FSM.FSMState jumpState = new FSM.FSMState("jump"); FSM.FSMState doubleJumpState = new FSM.FSMState("double_jump"); FSM.FSMState dieState = new FSM.FSMState("die"); // 创建跳转 FSM.FSMTranslation touchTranslation1 = new FSM.FSMTranslation(runState,"touch_down",jumpState,Jump); FSM.FSMTranslation touchTranslation2 = new FSM.FSMTranslation(jumpState,"touch_down",doubleJumpState,DoubleJump); FSM.FSMTranslation landTranslation1 = new FSM.FSMTranslation(jumpState,"land",runState,Run); FSM.FSMTranslation landTranslation2 = new FSM.FSMTranslation(doubleJumpState,"land",runState,Run); // 添加状态 PlayerModel.Instance ().fsm.AddState (idleState); PlayerModel.Instance ().fsm.AddState (runState); PlayerModel.Instance ().fsm.AddState (jumpState); PlayerModel.Instance ().fsm.AddState (doubleJumpState); PlayerModel.Instance ().fsm.AddState (dieState); // 添加跳转 PlayerModel.Instance ().fsm.AddTranslation (touchTranslation1); PlayerModel.Instance ().fsm.AddTranslation (touchTranslation2); PlayerModel.Instance ().fsm.AddTranslation (landTranslation1); PlayerModel.Instance ().fsm.AddTranslation (landTranslation2); PlayerModel.Instance ().fsm.Start (runState);
写给女票的:
原型模式:使用原型实例指定创建对象的种类,并通过赋值原型创建新的对象。上图上图上图!
什么时候用?
要实例化的类是在运行时决定的。
不同类的实例间的差异仅是状态的若干组合。因此肤质更加方便。
对象不容易创建,赋值一个对象仅改些属性比重新创建一个对象方便。
深拷贝与浅拷贝 :
一句话概括浅拷贝;拷贝过程中新的对象中指针类型的成员,只赋值原型对象的指针值,不复制指针所指向的实际的内存资源。
深拷贝:拷贝内存,新的对象中指针成员之向新的内存。
实现:
在Cocoa Touch中使用NSCopying协议实现深拷贝。
//// CommonClass.h// Prototype//// Created by 凉鞋 on 15/12/26.// Copyright © 2015年 凉鞋. All rights reserved.//#import <Foundation/Foundation.h>@interface CommonClass : NSObject <NSCopying>@property CommonClass *member;- (id)copyWithZone:(NSZone *)zone;@end//// CommonClass.m// Prototype//// Created by 凉鞋 on 15/12/26.// Copyright © 2015年 凉鞋. All rights reserved.//#import "CommonClass.h"@implementation CommonClass@synthesize member;- (id)copyWithZone:(nullable NSZone *)zone{ CommonClass *retObj = [CommonClass allocWithZone:zone]; retObj.member = [self.member copy]; return retObj;}@end//// main.m// Prototype//// Created by 凉鞋 on 15/12/26.// Copyright © 2015年 凉鞋. All rights reserved.//#import <Foundation/Foundation.h>#import "CommonClass.h"int main(int argc, const char * argv[]) { @autoreleasepool { // insert code here... CommonClass * protoObj = [CommonClass new]; protoObj.member = [CommonClass new]; NSLog(@"%@",protoObj.member); CommonClass * newObj = [protoObj copy]; NSLog(@"%@",newObj.member); } return 0;}
转载请注明地址:独立日记
微信公众号:QWERTeam
0 0
- 独立日记 2015年12月26日 day5 有限状态机 FSM
- 独立日记 2015年12月24日 day3 平安夜
- 独立日记 2015年12月25日 day4 圣诞节
- 独立日记 2015年12月27日 day6
- 独立日记 2015年12月31日 day10
- 独立日记 2015年1月2日 day12
- 独立日记 2015年12月23日 day2 小练习
- 独立日记 2015年12月29日 day8 第一周总结
- 独立日记 2016年1月1日 day11
- 独立日记 2016年1月3日 day13
- 独立日记 2015年8月19日 quick 3.5 + sublime环境搭建
- 独立日记 2015年9月13日 提交到appstore后的总结
- 独立日记 2015年10月3日 变量名的力量
- FSM 有限状态机
- 有限状态机(FSM)
- 有限状态机/FSM
- FSM有限状态机
- 日记2009年12月2日
- CLHLock
- Cyclic Nacklace
- Mac常用工具
- android混合动画实现
- Java 用Servlet+JDBC 结合Sqlsever 实现用户注册
- 独立日记 2015年12月26日 day5 有限状态机 FSM
- [iOS程序启动与运转]- RunLoop个人小结
- 北京市街へ
- POJ-3258 River Hopscotch
- 欢迎使用CSDN-markdown编辑器
- 802.11概述及帧结构分析
- Jsp+MySQL+Tomcat做的小服务器测试
- Extjs:getValue()、getRawValue()、getValues()、getFieldValues()区别
- sed(part 1)