数字信号处理篇之浮点数与定点数的转换(MATLAB)
数字信号处理篇之浮点数与定点数的转换(MATLAB)
一、写在前面
对于计算机等数字信号处理器件,数字和信号变量都是用二进制进行表示的。在本文中,我们学习了定点数的概念、浮点数与定点数的转换以及在MATLABZ中实现浮点数与定点数的转换。
二、十进制与二进制
对于二进制数,大家应该都很熟悉,在学习数电的过程中,我们知道,十进制转二进制,我们一般采用 “除2取余,逆序排列” 法,而二进制转十进制,我们一般采用“乘2累加”法(具体的转换过程可以参考阎石的《数字电子技术基础》第五版)。那么,任意一个十进制浮点数,均可以用B位整数位和b位小数据进行表示。假设二进制数为aBa_BaBaB−1a_{B-1}aB−1…a1a_1a1a0a_0a0Δ\\DeltaΔa−1a_{-1}a−1a−2a_{-2}a−2…a−ba_{-b}a−b,其中,Δ\\DeltaΔ表示小数点的位置,aB−1a_{B-1}aB−1为最高有效位(Most Significant Bit,MSB),a−ba_{-b}a−b为最低有效位(Least Significant Bit,LSB)。那么该二进制数与十进制浮点数的关系可以由下面的公式给出:
D=∑i=−bB−1ai2iD= \\sum_{i=-b}^{B-1} a_i{2^i} \\quad D=i=−b∑B−1ai2i
其中,aia_iai的值为0或1,D表示十进制浮点数数值。
在这里,对于不同大小的浮点数数值,其二进制表示的位宽是不一致的。例如:浮点数7.5可以用二进制数原码111Δ\\DeltaΔ 1进行表示,所需的位宽为4bit,再比如浮点数1.25,可以用二进制数原码1Δ\\DeltaΔ 01进行表示,所需的位宽为3bit。这里,我们可以看到,对于不同的数值,所需的二进制表示位宽也不一致,那么,如果要在硬件中实现简单的加减法,我们需要确保小数点对齐,才可保证计算结果的正确性,如下:
111Δ11Δ01\\begin{matrix} 111\\Delta1\\quad \\\\ \\ \\ 1\\Delta01 \\end{matrix} 111Δ1 1Δ01
此时计算得到结果1000Δ111000\\Delta111000Δ11,计算结果正确。如果小数点不对齐,则无法得到正确计算结果,如下:
111Δ11Δ01\\begin{matrix} 111\\Delta1 \\\\ \\ \\ 1\\Delta01 \\end{matrix} 111Δ1 1Δ01
此时计算得到结果101001010010100,计算结果错误,且无法确定小数点Δ\\DeltaΔ的位置。
那么,有没有什么办法能够保证任意不同数值的二进制表示之间的小数点是对齐的呢?我们可以通过固定小数点Δ\\DeltaΔ的位置,来确保任意数值的二进制表示是对齐的。于是,我们在这里引入定点数。
二、定点数的概念
那么在前面定点数(fixed-point number)就是小数点在数中位置是固定不变的二进制数,也就是说,小数点在数值的二进制表示中位置是固定的。以8bit的定点数为例,其符号位为1bit,整数位为3bit,小数位为4bit,那么小数点的位置就固定在第4bit和第5bit中间(从左往右数,即_ _ _ _ Δ\\DeltaΔ_ _ _ _ )。
下面,我们给出几个按照8bit(符号位1位,整数位3位,小数位4位)进行浮点数—定点数转换的例子:
(−2.78)float=(1010Δ1100)fixed(+7.19)float=(1111Δ0011)fixed\\begin{matrix} (-2.78)_{float}=(1010\\Delta1100)_{fixed} \\\\ \\\\(+7.19)_{float}=(1111\\Delta0011)_{fixed} \\end{matrix} (−2.78)float=(1010Δ1100)fixed(+7.19)float=(1111Δ0011)fixed
在这里,由于定点数表示所给的位宽不足,导致存在一定的精度误差。这里1010Δ11001010\\Delta11001010Δ1100所表示的数值实际上是-2.75,相比于原来的-2.78,存在0.03的误差。而1111Δ00111111\\Delta00111111Δ0011所表示的值实际上为+7.1875,与原来的+7.19存在0.025的误差。这里可以看到对于-2.78,符号位为负,即为1;整数位为2,用二进制表示即10,但是由于我们规定了其整数位位3bit,而这里只有2bit,所以在前面补0,即010;小数位为0.78,用二进制表示为Δ11\\Delta11Δ11,但是由于我们规定了其小数位为4bit,所以需要在后面补0,即1100,于是,就得到了-2.78的定点数表示1010Δ11001010\\Delta11001010Δ1100,实现了所有按照该标准进行转换的定点数小数点Δ\\DeltaΔ必然是对齐的。
三、定点数的几种表示方法
定点数有三种表示方法:原码、反码、补码。在上面,我们举例都是以原码为例,下面降对这三种表示方法展开讲解。
3.1 原码表示
原码表示法就是指符号位加绝对值的表示方法。对于一个(B+b)位的定点数aB−1a_{B-1}aB−1…a1a_1a1a0a_0a0Δ\\DeltaΔa−1a_{-1}a−1a−2a_{-2}a−2…a−ba_{-b}a−b,其对应的十进制表示为:
D=(−1)aB−1∑i=−bB−2ai2iD= (-1)^{a_{ B-1}}\\sum_{i=-b}^{B-2} a_i{2^{i}} \\quad D=(−1)aB−1i=−b∑B−2ai2i
其中,aB−1a_{B-1}aB−1为符号位,aB−2a_{B-2}aB−2为整数位的最高位,a0a_0a0为整数位的最低位,a−1a_{-1}a−1为小数位的最高位,a−ba_{-b}a−b为小数位的最低位。
以-2.75和2.75为例,其浮点数-定点数转换如下:
(−2.75)浮点数=(1010Δ1100)定点数−原码(2.75)浮点数=(0010Δ1100)定点数−原码\\begin{matrix} (-2.75)_{浮点数}=(1010\\Delta1100)_{定点数-原码} \\\\ \\\\ (2.75)_{浮点数}=(0010\\Delta1100)_{定点数-原码} \\end{matrix} (−2.75)浮点数=(1010Δ1100)定点数−原码(2.75)浮点数=(0010Δ1100)定点数−原码
3.2 反码表示
正数的反码与正数的原码相同,而负数的反码可以通过将负数的原码除符号位以外的所有位取反得到。
(−2.75)浮点数=(1101Δ0011)定点数−反码(2.75)浮点数=(0010Δ1100)定点数−反码\\begin{matrix} (-2.75)_{浮点数}=(1101\\Delta0011)_{定点数-反码} \\\\ \\\\ (2.75)_{浮点数}=(0010\\Delta1100)_{定点数-反码} \\end{matrix} (−2.75)浮点数=(1101Δ0011)定点数−反码(2.75)浮点数=(0010Δ1100)定点数−反码
3.3 补码表示
正数的补码与原码、反码均相同,而负数的补码可以通过在负数反码的最低有效位LSB处加1得到。
(−2.75)浮点数=(1101Δ0100)定点数−补码(2.75)浮点数=(0010Δ1100)定点数−反码\\begin{matrix} (-2.75)_{浮点数}=(1101\\Delta0100)_{定点数-补码} \\\\ \\\\ (2.75)_{浮点数}=(0010\\Delta1100)_{定点数-反码} \\end{matrix} (−2.75)浮点数=(1101Δ0100)定点数−补码(2.75)浮点数=(0010Δ1100)定点数−反码
四、浮点数转定点数的MATLAB实现
在MATLAB中,对于十进制转二进制,提供了函数dec2bin,但其只支持整数转二进制,如下。
所以,我们需要在进行进制转换前对齐进行放大处理,乘以2b2^b2b,其中,b为定点数设置的小数部分占用的位数。比如前面我们讲到的8bit(符号位1位,整数位3位,小数位4位),那么对2.75进行放大2b=162^b=162b=16倍以后,得到的数值为44,那么再使用函数dec2bin对其进行转换,同时设置转换后的位宽8bit,即可得到转换以后的定点数,如下。
这里乘以2b2^b2b实际上是对原来的数值进行移位处理。
上面是对正数求其定点数原码,那么如果要求负数的定点数原码,直接使用dec2bin则会出错,dec2bin会给出其补码形式的二进制结果,如下:
在这里,我们需要将其符号位与数值位进行分开,对其数值的绝对值进行定点数转换,然后与符号位进行拼接,即可得到定点数原码,如下:
五、写在后面
在本文中,我们学习了定点数的概念以及在MATLAB中如何将浮点数转换为定点数。如果有疑义的地方欢迎评论区友好探讨学习!!!!!(浮点数转定点数MATLAB代码!!!!)