本文研究Simulink中常用的按位运算的建模方法。
1 引入
在计算机的基础课中,学过把一个十进制数转换成二进制数。例如,十进制的63转换为二进制就是111111。系统自带的计算器工具选择程序员模式,就可以很方便地进行转换操作。
这里的二进制数,最右边就是第0位,往左一个就是第1位,再往左一个就是第二位,依次类推。后文中博主会介绍自己工作中常用的位运算建模方法。这里暂时只讨论正整数的位运算,因为在博主的工作中用到的正整数相关位运算比较多。
2 位运算模块
2.1 移位模块
在Simulink中,可以通过Shift Arithmetic模块,对输入的数字左移或右移若干个位。例如下图中,Direction中配置为Left,Number配置为3,也就是将输入的数值左移3位,得到的结果输出。
例如输入的数值是3(十进制),输出的数值就是24;
这里的计算过程如下,3转换成二进制得到"0011",将"0011"左移3位变成"0001 1000",再将"0001 1000"转换成十进制就变成了24。
或者,移位其实就是乘以2的n次方,所以out = 32^3 = 38 = 24;
2.1 按位逻辑运算
逻辑运算包括与或非等等,这个在门电路里面是非常常用的。在Simulink中有一种按位进行逻辑运算的模块Bitwise Operator,可以对整数的每一位进行逻辑运算,然后再输出。
这里以Bitwise And为例,下图中将Operator选为And,表示按位进行与运算,Bit Mask中是bin2dec(“11011001”),表示将输入的数值和"11011001"的每个对应的为进行与运算,再输出。
例如下图中,输入为19,经过Bitwise And后,输出为17.
这里的计算过程如下,首先,十进制的19转为2进制是"0001 0011",和"1101 1001"按位进行与运算,必须同样的位都是1才输出1,所以运算结果是"0001 0001",转换成十进制就是17了。
3 代码生成
上面讲的两种位运算生成代码也比较简单,这里就看一看。
例如做了两个简单的输入输出,分别接bitwise and模块和shift模块。
生成代码后就是对应C语言中的移位运算和AND运算。
4 位运算的应用
博主在做电控开发的经验中,有以下两种情况会用到位运算:DBC矩阵解析和bool信号打包。本节会简单讲讲应用的方法。
4.1DBC矩阵解析
关于DBC文件相关概念,博主在以前的博客中写过这里不再赘述,可以参考以下文章。
参考如下DBC矩阵,显示的是ID号为0x258的帧。DriverDoorWindow信号处于该帧矩阵的第2行和第3行。假设Byte Order属性是Intel格式,那么第2行的前4位就是该信号的低4位,第3行的后4位就是该信号的高4位。同时假设factor和offset分别为1和0,以便简化后面的计算演示。
假设我们的控制器接收到这一帧,可以通过如下方式解析出来。
1)首先通过底层软件可以解析出每一行的的8个位组成的数值,那么第2行和第3行就是Data_2和Data_3,作为port口引入模型;
2)通过Bitwise And,将第2行的前4位取出来,那么Data_2需要和"1111 0000"做一个Bitwise And,这样就将Data_2的低4位全部置为0,Data_2的高4位全部保留,然后再右移4位,就能将Data_2的高4位转换成DriverDoorWindow信号的低4位;
3)同理,通过Bitwise And,将第3行的后4位取出来,那么Data_3需要和"0000 1111"做一个Bitwise And,这样就将Data_3的高4位全部置为0,Data_3的低4位全部保留,然后再左移4位,就能将Data_3的低4位转换成DriverDoorWindow信号的高4位;
4)最后,把2)和3)步骤中的输出加起来,就得到了完整的DriverDoorWindow信号;
最后说明一下,通过应用层模块解析DBC文件已经不是很常见了,行业内基本上都是通过Autosar架构配置完成CAN信号的解析。
4.2 bool信号打包
在建模的过程中,可以将若干个bool信号打包成一个信号,用于后面的判断,或者采集观测。例如,ACC(自适应巡航)系统的激活条件要求如下条件都满足:
bit位 | 条件 | 信号名 |
---|---|---|
bit0 | 挡位处于前进档 | GearPos |
bit1 | 车门关闭 | DoorStatus |
bit2 | 安全带系上 | SeatBeltStatus |
bit3 | 车速小于150kmph | VehSpd |
bit4 | 制动踏板未踩下 | BrkPedStatus |
实际中的ACC激活条件不止这些。建模的过程中,可以将这些布尔信号通过移位相加组装成一个uint8的信号,每一位代表其中一个条件是否满足。可以建模如下:
通过这种建模方式,就可以用ACC_Enable信号的每个位来表示各个条件是否满足。
比方说ACC_Enable = 27,转为2进制就是"0001 1011",其中第0,第1,第3,第4位都是1,第2位是0。对应模型中左移两位的信号是SeatBeltStatus,所以就是安全带没系上,导致了ACC不激活。
5 总结
本文研究Simulink中常用的按位运算的建模方法,位运算的建模比较简单,可以很容易地掌握。