一、综述
在生活中,常常会遇到状态的转换。比如水,在低温0度以下会结冰。用一个状态转换图就是
此等例子比比皆是,这就是最基本的状态转换图。此图应用广泛,比如工业制造领域跟踪设备的状态。本节内容就是用python去模拟各种状态的转换过程。
二、准备
1. python解释器
2. 安装transition库
pip install transitions
3. 源码网址
https://pypi.org/project/transitions/
三、状态机的使用
1.以下是一个综合代码,不过不用着急,我会慢慢讲解的。主要体现一下整体性
from transitionsimport Machinefrom transitions.extensions.statesimport add_state_features, Timeout, Tagsimport random
TASK_EXE_TIME=0.1# 任务执行时间 单位:秒
PROBABILITY=0.8# 扫描成功的概率值
@add_state_features(Tags, Timeout)classCustomStateMachine(Machine):passclassPLC(object):"""plc状态机"""# 'initial' 初始态,一片空白# 'load' 物料到位# 'scanfinish' 扫描完成# 'exe_task' 执行任务# 'taskfinish' 任务完成# 'unload' plc出站完成状态
states=['initial','load','scanfinish',{'name':'exe_task','timeout': TASK_EXE_TIME,'on_timeout':'go'},'taskfinish','unload']
transitions=[['supplies_ready','initial','load'],{'trigger':'scan','source':'load','dest':'scanfinish','conditions':'is_scan_success'},['manual_scan','load','scanfinish'],['task_release_finish','scanfinish','exe_task'],{'trigger':'mes_finish','source':'taskfinish','dest':'unload','before':'read_ps'},['reset_signal','unload','initial']]def__init__(self, plc_name):
self.plc_name= plc_name# Initialize the state machine
self.machine= CustomStateMachine(model=self, states=PLC.states, initial='initial', transitions=PLC.transitions)
@propertydefis_scan_success(self):"""
以一定的概率返回扫描成功还是失败,成功的概率,自定义
:return: True ,False
"""return random.random()<= PROBABILITYdefgo(self):"""超时,从exe_task,自动转换到taskfinish"""
self.to_taskfinish()defread_ps(self):print("读取P+S码")
2. 快速掌握
from transitionsimport Machine# 导入状态机import randomclassWater():"""定义一个水类内部可空白"""pass
water= Water()
states=['gas','liquid','solid']# 定义状态 气态、液态、固态# 状态机的模型设为water对象, 状态设为气态、液态、固态,初始状态为液态
machine= Machine(model=water, states=states, initial='liquid')# 设定转换过程# trigger为触发条件(本质是一个函数的引用,该函数自动生成) , source是原状态 ,dest为目标状态。应把各种状态转换过程完善。这里仅举几例。
machine.add_transition(trigger='heat', source='liquid', dest='gas')
machine.add_transition(trigger='cool', source='liquid', dest='solid')
machine.add_transition(trigger='sublimation', source='solid', dest='gas')# add_transition函数还指定before, after参数,分别表示状态装换之前和之后执行的函数# 还可以指定 conditions=,表示当条件函数返回为True时,才执行状态转换。# water.state查询水的状态# water.heat() 将液态转换为气态
3. 详细内容
1. States
状态可根据自己的需求定义
from transitionsimport State
states=[
State(name='solid'),'liquid',{'name':'gas'}]
2. 回调函数
states=[
State(name='solid', on_exit=['say_goodbye']),'liquid',{'name':'gas'}]
machine.on_enter_gas('say_hello')
两种方式为状态添加回调函数。
1 通过on_exit字段,表示离开该状态时,执行该函数
2 machine.on_enter_gas(‘say_hello’) 通过函数方式添加
4. Enumerations
transitions=[['heat','liquid','gas'],['cool','liquid','solid'],['sublimation','solid','gas']
通过枚举出所有的状态,若需要精确定义,可将内层列表部分改成字典来指定。
5. Logging
Transitions includes very rudimentary logging capabilities. A number of events – namely, state changes, transition triggers, and conditional checks – are logged as INFO-level events using the standard Python logging module. This means you can easily configure logging to standard output in a script:
转换包括非常基本的日志功能。使用标准Python日志模块将许多事件(即状态更改、转换触发器和条件检查)记录为info级事件。这意味着你可以很容易地配置日志到标准输出在一个脚本:
# Set up logging; The basic log level will be DEBUGimport logging
logging.basicConfig(level=logging.DEBUG)# Set transitions' log level to INFO; DEBUG messages will be omitted
logging.getLogger('transitions').setLevel(logging.INFO)# Business as usual
machine= Machine(states=states, transitions=transitions, initial='solid')
6. Adding features to states 添加新特性
from timeimport sleepfrom transitionsimport Machinefrom transitions.extensions.statesimport add_state_features, Tags, Timeout# 定义一个新的机器,继承Machine,并添加Tags, Timeout的装饰器
@add_state_features(Tags, Timeout)classCustomStateMachine(Machine):pass# 有了新机器,就可以在states中添加timeout和on_timeout字段。# timeout 指定超时时间,单位是秒# on_timeout 指定时间超时后应该执行什么函数
states=['initial','load','scanfinish',{'name':'exe_task','timeout':2,'on_timeout':'go'},'taskfinish','unload']# 类似的 还可以指定标签值。标签值就是:若在当前状态,则machine.get_state('preparing').is_busy 会返回True,否则,False
states=[{'name':'preparing','tags':['home','busy']},{'name':'waiting','timeout':1,'on_timeout':'go'},
machine=CustomStateMachine(model=hero,states=states,transitions=transitions, initial='preparing')
7. 更多内容请查阅源网址,见2.3。
有问题可私信。