使用动作定义图行为
状态和转移动作是您在状态或转移旁编写的指令,用于定义 Stateflow® 图在仿真过程中的行为。有关详细信息,请参阅对有限状态机建模。
状态和转移动作示例
下图中的动作定义了一个以实验方式验证 Collatz 猜想实例的状态机。对于给定的数值输入 ,该图通过迭代以下规则来计算冰雹序列
:
如果
为偶数,则
。
如果
为奇数,则
。
Collatz 猜想指出,每个正整数都有一个最终达到 1 的冰雹序列。
该图由三个状态组成。在仿真开始时,Init
状态初始化图数据:
局部数据
n
设置为输入u
的值。当
n
除以 2 时,局部数据n2
设置为余数。输出数据
y
设置为false
。
根据输入的奇偶性,图转移到 Even
或 Odd
状态。当状态活动在 Even
和 Odd
状态之间切换时,图会计算冰雹序列中的数字。当序列达到 1 值时,输出数据 y
变为 true
,并触发 Simulink® 模型中的 Stop Simulation (Simulink) 模块。
状态动作类型
状态动作定义当状态被激活时 Stateflow 图的动作。最常见的状态动作类型是 entry
、during
和 exit
动作。
状态动作的类型 | 缩写 | 描述 |
---|---|---|
entry | en | 当状态被激活时,动作在时间步上发生。 |
during | du | 当状态已激活并且图未转移出该状态时,动作在时间步上发生。 |
exit | ex | 当图转移出状态时,动作在时间步上发生。 |
您可以通过状态动作的完整关键字(entry
、during
、exit
)或其缩写(en
、du
、ex
)指定状态动作的类型。您还可以使用逗号组合各状态动作类型。例如,组合类型 entry,during
当状态被激活时在时间步上发生,并且在状态保持激活时在每个后续时间步上发生。
下表列出了冰雹图中每个状态动作的结果。
状态 | 动作 | 结果 |
---|---|---|
Init |
entry: n2 = rem(n,2); y = false; | 在仿真开始,Init 被激活时,确定 n 的奇偶性并将 y 设置为 false 。 |
exit: y = isequal(n,1); | 当经过一个时间步后转移出 Init 时,确定 n 是否等于 1。 | |
Even |
entry,during: n = n/2; n2 = rem(n,2); | 计算冰雹序列的下一个数字 (
|
Odd |
entry,during: n = 3*(n-y)+1; n2 = rem(n,2); | 计算冰雹序列的下一个数字 (3
在整个仿真过程的大部分阶段, |
转移动作的类型
转移动作定义当转移出激活状态时 Stateflow 图执行的动作。最常见的转移动作类型是条件和条件动作。要指定转移动作,请使用采用以下语法的标签:
[condition]{conditional_action}
condition
是布尔表达式,用于确定是否发生转移。如果不指定条件,则假定采用一个计算结果为 true 的隐含条件。
conditional_action
是在判断转移的条件为 true 时执行的指令。条件动作发生在条件后,但在任何 exit
或 entry
状态动作之前。
下表列出了冰雹图中每个转移动作的结果。
转移 | 动作 | 动作类型 | 结果 |
---|---|---|---|
到 Init 的默认转移 |
n = u | 条件动作 | 在仿真开始时,将输入值 u 赋给局部数据 n 。 |
从 Init 到 Even 的转移 |
n2 == 0 | 条件 | 当 n 为偶数时,发生转移。此转移起始处的数字 1 表示此转移将先于指向 Odd 的转移进行计算。 |
从 Init 到 Odd 的转移 | 无 | 当 n 为奇数时,发生转移。此转移起始处的数字 2 表示此转移将在指向 Even 的转移之后进行计算。 | |
从 Odd 到 Even 的转移 |
n2 == 0 | 条件 | 当 n 为偶数时,发生转移。 |
从 Even 到 Odd 的转移 |
n2 ~= 0 | 条件 | 当 n 为奇数时,发生转移。 |
y = isequal(n,1) | 条件动作 | 在发生转移时,确定 n 是否等于 1。 |
检查图行为
假设您要计算从 9 开始的冰雹序列。
在 Constant (Simulink) 模块中,输入值
9
。在仿真选项卡中,点击运行
。
图用下列动作予以响应:
在时间 t = 0 处,发生到
Init
的默认转移。转移动作将
n
的值设置为 9。Init
状态被激活。Init
中的entry
动作将n2
设置为 1 且将y
设置为false
。
在时间 t = 1 处,条件
n2 == 0
为 false,因此图准备转移到Odd
。Init
中的exit
动作将y
设置为false
。Init
状态变为非激活。Odd
状态被激活。Odd
中的entry
动作将n
设置为 28,将n2
设置为 0。
在时间 t = 2 处,条件
n2 == 0
为 true,因此图准备转移到Even
。Odd
状态变为非激活。Even
状态被激活。Even
中的entry
动作将n
设置为 14,将n2
设置为 0。
在时间 t = 3 处,条件
n2 ~= 0
为 false,因此图不会发生转移。Even
状态保持激活。Even
中的during
动作将n
设置为 7,将n2
设置为 1。
在时间 t = 4 处,条件
n2 ~= 0
为 true,因此图准备转移到Odd
。转移动作将
y
设置为false
。Even
状态变为非激活。Odd
状态被激活。Odd
中的entry
动作将n
设置为 22,将n2
设置为 0。
该图继续计算冰雹序列,直到它在时间 t = 19 处达到
n
= 1 的值。在时间 t = 20 处,图准备从
Even
转移到Odd
。在
Even
状态变为未激活之前,转移动作将y
设置为true
。Odd
状态被激活。Odd
中的entry
动作不会修改n
或n2
。连接到输出信号
y
的 Stop Simulation (Simulink) 模块停止仿真。
在仿真选项卡中的 查看结果下,点击数据检查器
。
要查看冰雹序列的值,请在仿真数据检查器中,选择记录的信号
n
。
冰雹序列在 19 次迭代后达到值 1。