状态机的理解与使用【开发实践】

一、基础概念

1.1 状态模式

状态模式(State Pattern)是一种行为型设计模式,它允许对象在内部状态发生变化时改变其行为。在状态模式中,一个对象的行为取决于其当前状态,而且可以随时改变这个状态。状态模式将对象的状态封装在不同的状态类中,从而使代码更加清晰和易于维护。当一个对象的状态改变时,状态模式会自动更新该对象的行为,而不需要在代码中手动进行判断和处理。

1.2 状态机图

使用UML状态机图能够简洁直观地描述出行为状态的转移,它包含七种元素:

  • 起始状态:用实心圆表示
  • 终止状态:内部实心的同心圆表示
  • 状态:用椭圆或圆角矩形表示,内部要填写状态名
  • 状态转移:用连接状态的箭头表示,指从箭头起点状态转移到箭头终点状态的状态转移
  • 事件:用箭头上的文字描述表示,指引起状态转移的原因,对应一种特定的状态转移规则
  • 条件:用事件名之后括号括起来的文字表示,指状态转换的条件(非必须)
  • 动作:转换激活时的操作(非必须)

状态机图的示例如下:(配图来源:设计模式:一目了然的状态机图
在这里插入图片描述

在当前状态的基础上,当发生事件时,会判断是否满足状态转移的条件,满足时就会转移到对应的状态,完成状态转移后可以执行预设的动作。

1.3 状态机(模型/引擎)

状态机,也就是 State Machine,不是指一台实际机器,而是指一个描述状态转移的数学模型。状态机是状态模式的一种应用,相当于上下文角色的一个升级版。在工作流或游戏等各种系统中有大量使用,如各种工作流引擎,它几乎是状态机的子集和实现,封装状态的变化规则。状态机帮助开发者简化状态控制的开发过程,让状态机结构更加层次化。

开源的状态机框架非常多,如Spring就提供了状态机组件,名称就是状态机(State Machine)。很多状态机框架虽然功能齐全,但是过于复杂,性能也较差。从功能足够用、使用起来足够简单、性能足够好的角度出发,推荐使用Cola Statemachine。本文以该Cola Statemachine为例介绍状态机引擎的使用。

二、状态机(Cola Statemachine)的使用

2.1 相关的核心概念

  • State:状态
  • Transition:流转
  • External Transition:外部流转,指两个不同状态之间的流转
  • Internal Transition:内部流转,同一个状态之间的流转
  • Event:事件,指引起状态流传的事件
  • Condition:条件,表示是否允许到达某个状态
  • Action:动作,指到达某个状态后触发的动作
  • StateMachine:状态机

2.2 状态机的的使用流程

  1. 注册状态机并定定义状态流转
  2. 获取状态机并使用

2.2.1 注册状态机并定义状态流转

需要注意的是,API的调用顺序只能遵循如下的顺序,包含三种transition方式。

由于该状态机的实现是无状态的,所以可以使用同一个状态机实例来定义多个状态流转。

StateMachineBuilder<States, Events, Context> builder = StateMachineBuilderFactory.create();

// 当发生Events.EVENT1事件,且满足checkCondition()条件时,状态States.STATE1将流转为状态States.STATE2,并触发doAction()动作
builder.externalTransition()
    .from(States.STATE1)
    .to(States.STATE2)
    .on(Events.EVENT1)
    .when(condition)
    .perform(action);

// 相当于多种from状态到同个终止状态的批量配置
// 状态流转的定义,可以同时定义多种起始状态在同一事件发生时转移到相同的状态,并执行相同的动作
// 即,对于某事件而言,起始状态可以多个,终止状态和行为对应一个
builder.externalTransitions()
    .from(States.STATE1, States.STATE2)
    .to(States.STATE3)
    .on(Events.EVENT1)
    .when(condition)
    .perform(action);

// 当发生Events.EVENT1事件,且满足checkCondition()条件时,状态States.STATE2将流转为状态States.STATE2,并触发doAction()动作
builder.internalTransition()
    .within(States.STATE2)
    .on(Events.INTERNAL_EVENT)
    .when(condition)
    .perform(action);

// 使用一个String类型的machineId来构建状态机实例
builder.build(machineId);
 
// 之后再使用machineId来获取指定的状态机实例
StateMachine<States, Events, Context> stateMachine = StateMachineFactory.get(machineId);
stateMachine.showStateMachine();

2.2.2 获取状态机并使用

	// 1.获取状态机
	StateMachine<States, Events, Context> stateMachine = getStateMachine();
	// 2.组装上下文 messageContext
	Context context = buildContext();
	// 3.使用状态机调用fireEvent来触发事件:源状态,事件,上下文(供checkCondition()和doAction()使用)
	stateMachine.fireEvent(States.STATE1, Events.EVENT1, context);

	// 补充:可以打印状态机中定义的状态转移信息
	String plantUML = orderOperaMachine.generatePlantUML();
	System.out.println(plantUML);

三、补充的详细说明

3.1 when(Condition<C> condition)

when(condition)会调用condition对象的boolean isSatisfied(C context)方法,根据上下文判断是否满足条件,满足条件时才会执行状态流转。

3.2 perform(Action<S, E, C> action)

perform(action)会调用action对象的public void execute(S from, S to, E event, C context)方法,在满足条件并执行了状态流转后,去执行相应的动作。

四、状态机的使用小结

我们先定义好状态转移规则和相应的触发动作,之后只需要调用状态机的方法来完成状态更新。状态机会根据源状态、事件来使用相应的状态转移规则,根据上下文中的信息判断是否满足转移的条件,满足时就会转移到目标状态并触发预设的动作。

参考博客推荐

设计模式:一目了然的状态机图
玩转 Spring 状态机 | 京东云技术团队
实现一个状态机引擎,教你看清DSL的本质
COLA中的cola-statemachine状态机理解与使用例

  • 29
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: "openscenegraph三维渲染引擎编程指南 源码" 是一本介绍了 OpenSceneGraph (OSG) 三维渲染引擎的编程指南,同时也提供了大量实用的源代码示例。OSG是一个强大的开源三维图形库,它提供了许多高级渲染功能,如光照、阴影、透明度和纹理等。 这本书主要分为两个部分:理论和实践。在理论部分,作者详细讲解了OSG的结构和主要概念,包括场景图、节点、渲染状态、相、几何体等。在实践部分,作者提供了丰富的示例代码,涵盖了从简单图形绘制到复杂应用程序开发的各个方面。其中包括利用OSG创建动画、设计虚拟现实环境、实现交互式选取等。 这本书的优点在于,它详细而且易懂地介绍了OSG的核心概念和应用,即使没有使用过该引擎的读者也能轻松理解。同时,该书的配套源代码示例也非常实用,读者可以直接借鉴和应用。此外,该书还包括了一些工具和技术,如脚本语言、纹理映射、场景管理、GPU编程等,以帮助读者更好地理解和应用OSG。 总之,“openscenegraph三维渲染引擎编程指南 源码”是一本挺好的学习OSG的参考书,适合开发人员、研究人员和学生使用。阅读该书可以让读者深入了解OSG,并且让他们能够快速掌握该引擎的使用技巧和开发方法。 ### 回答2: OpenSceneGraph是一款流行的三维渲染引擎,它提供了完整的渲染流程和丰富的应用接口帮助开发者快速开发可视化应用程序。《OpenSceneGraph三维渲染引擎编程指南》作为OpenSceneGraph开发者的必备参考书籍,全面介绍了OpenSceneGraph引擎的基础概念、编程接口和应用实践。本书随书附赠《OpenSceneGraph三维渲染引擎编程指南》源码,可以帮助读者通过实践深入理解OpenSceneGraph引擎的内部结构和工作原理,掌握在使用中遇到的各种问题的解决方法。 这份源码包括了丰富的OpenSceneGraph应用实例源码、引擎核心模块源码和数据加载、文本渲染、日志记录等常见工具源码。通过深入研究这份源码,读者可以深入理解OpenSceneGraph引擎中的各个模块的实现细节和工作原理,掌握OpenGL编程技巧和单元测试方法,了解OpenSceneGraph常用的第三方库和工具,并能在实践中运用这些知识和技能解决实际开发中遇到的问题。 总而言之,《OpenSceneGraph三维渲染引擎编程指南》源码提供了丰富的实践案例和宝贵的编程经验,对OpenSceneGraph引擎的学习和应用都具有重要意义。无论是从事科学计算、游戏开发还是虚拟现实和智能制造等领域的工程师和技术人员,都可以通过阅读本书并学习OpenSceneGraph的编程技巧和实践经验,提升自己的职业技能和创新能力。 ### 回答3: OpenSceneGraph是一个开源的跨平台三维图形渲染引擎,由于其强大的性能和易于使用的特点,成为了很多游戏、虚拟现实、仿真等领域的首选。《OpenSceneGraph三维渲染引擎编程指南》是一本详细介绍OpenSceneGraph使用方法及原理的书籍。 本书的源码提供了很多OpenSceneGraph的实现示例,方便读者快速学习和了解OpenSceneGraph的各种功能。源码中包含了很多场景的搭建、几何体的操作、纹理的应用、光照的设置、动画的实现等方面的示例,这些示例有助于读者更好地理解和掌握OpenSceneGraph。 另外,本书源码还包含了使用OpenSceneGraph的其他工具和库的示例代码,如osgUtil、osgDB、osgGA等。这些工具和库都是OpenSceneGraph中非常常用的组件,源码中的实现示例对于读者进一步学习和掌握这些组件有很大帮助。 最后,强调一点,本书源码的运行需要读者具备一定的C++编程基础,同时也要对三维图形及渲染技术有一定的了解。如果读者能够系统地学习本书中的例子,并结合OpenSceneGraph官方文档进行深入学习,相信一定能够深入掌握OpenSceneGraph的使用

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值