mirror of
https://github.com/Didnelpsun/CS408.git
synced 2026-02-13 23:55:58 +08:00
Update 1-data-representation-and-operation.md
This commit is contained in:
@@ -343,15 +343,230 @@ k|2|3|4|5|6|7
|
||||
+ 如-24-124=11,110 1000+11,000 0100=10,110 1100=108。下溢。
|
||||
+ 如15+124=00,000 1111+00,111 1100=01,000 1011=-117。上溢。
|
||||
+ 实际存储时只存储一个符号位,运算时会复制一个符号位。
|
||||
+ 符号扩展
|
||||
+ 符号扩展:防止溢出的一个方法就是将短数据扩展为长数据。
|
||||
+ 整数扩展,在原符号位和数值位中间添加新位,正数都填充0,对于负数:
|
||||
+ 原码:扩展补0。
|
||||
+ 反码:扩展补1。
|
||||
+ 补码:扩展补1。
|
||||
+ 小数扩展,在最后面添加新位,正数都填充0,对于负数:
|
||||
+ 原码:扩展补0。
|
||||
+ 反码:扩展补1。
|
||||
+ 补码:扩展补0。
|
||||
|
||||
#### 乘法运算
|
||||
|
||||
对于原码的乘数运算可以参考十进制的乘数运算,将乘数一位一位的乘被乘数然后再全部相加得到的就是答案。而使用二进制的一位位乘法显然比十进制的一位位乘更简单。
|
||||
|
||||
##### 原码一位乘法
|
||||
|
||||
一般使用原码一位乘法,即每次只乘一位的数据。
|
||||
|
||||
在原码乘法时,可以先符号位单独处理,将两个符号进行异或操作,得到的结果就是最后的结果的符号。然后对数据的绝对值(去除符号位)进行一位位的乘法(位积)然后相加。
|
||||
|
||||
在运算器的组成时出现一个表格,说明在进行乘运算时,ACC保存乘积高位,MQ保存乘数与乘积低位,X保存被乘数。
|
||||
|
||||
原码一位乘法机器实现时就是按照这种方式计算:
|
||||
|
||||
1. 字长若为n+1位,则ACC、MQ、X全部初始化为n位,将被乘数的绝对值放入X中,MQ放入乘数的绝对值,ACC初始化为全0。
|
||||
2. 将MQ的最右边的一位当做当前乘运算位,让其进行乘运算,运算规则是,若当前位是1,则ACC加上被乘数,即ACC+=X,若当前位是0,则ACC加上0(保持不变,跳过)。
|
||||
3. 将ACC和MQ的数据连接在一起,全部逻辑右移一位,ACC数据高位补0,ACC最后一个低位移到MQ的最高位。将MQ的最后一位抛弃。若是第i轮逻辑右移,则MQ的前i位是结果的后i个低位值。
|
||||
4. 从步骤二开始重复,字长若为n+1位,则重复n次,直到MQ的最后一位是符号位,则停止计算。此时ACC的全部和MQ的前n位都是结果。
|
||||
5. 定点小数的小数位隐藏在符号位后面第一位,定点正数的小数位隐藏在MQ符号位的前一位。
|
||||
6. 将两个符号位的异或结果赋值给积最高位。
|
||||
|
||||
**例题** 设机器字长为n+1=5位(含1位符号位),其中x的原码为1.1101,y的原码为0.1011,采用原码一位乘法求xy。
|
||||
|
||||
其中x就是-0.1101,而y就是+0.1011。先抛去符号位,就得到01101和01011两个数据。
|
||||
|
||||
将MQ、ACC、X都初始化为五位存储单元。X放入被乘数01101,MQ放入乘数01011,ACC为00000。
|
||||
|
||||
运算器结构:ACC与MQ相连,数据流是双向的,ACC与ALU相连,数据流是双向的,X的数据流向ALU。
|
||||
|
||||
此时MQ=01011,作为乘法单位的最后位为1,所以ACC+=X,从而=00000+01101=01101,这就是第一个的位积。
|
||||
|
||||
由于按照乘法规则,第二个位积计算时需要错位相加,计算机的处理方式是ACC和MQ的数据连在一起,全部逻辑右移一位(左边补0)。
|
||||
|
||||
所以ACC的数据由01101变为00110,最后的1移到MQ最高位,MQ由01011变为10101,最后的一位1溢出被抛弃,代表这一位的位积已经计算并相加完成,所以不用管了。此时结果的高位还在ACC中,而结果的低位从ACC移到了MQ中,在MQ的低位也不参与后面的运算,所以也不用管了。
|
||||
|
||||
然后计算下一个最低位的位积,此时MQ的最低位还是1,所以ACC+=X=00110+01101=10011。
|
||||
|
||||
同样计算完后再错位,进行逻辑右移,ACC由10011变成了01001,MQ由10101变成了11010,最低位的1被抛弃,此时MQ中已经有两个结果最低位。
|
||||
|
||||
此时MQ最低位为0,所以ACC保持不变,再逻辑右移一位,ACC由01001变为00100,MQ由11010变为11101,抛弃一位0,MQ有三个结果最低位。
|
||||
|
||||
此时MQ最低位为1,则ACC+=X=00100+01101=10001。
|
||||
|
||||
同样计算完后再错位,进行逻辑右移,ACC由10001变成了01000,MQ由11101变成了11110,最低位的1被抛弃,此时MQ中已经有四个结果最低位,此时MQ最低位是代表符号的0不参与运算。此时计算已经结束。
|
||||
|
||||
小数的小数点隐藏在第一位的后面,所以此时结果在ACC和MQ的前四位中,即0.10001111。最后加上符号异或结果,得到1.10001111。
|
||||
|
||||
##### 补码一位乘法
|
||||
|
||||
对于补码的乘法运算的逻辑也跟原码的类似,补码的计算就是使用Booth算法实现:
|
||||
|
||||
|原码|补码
|
||||
:----:|:--:|:--:
|
||||
计算流程|n轮加法、移位|n轮加法、移位,最后进行一次加法
|
||||
加法的值|+0、+x的原码|+0、+x的补码、+(-x)的补码
|
||||
判断加值的根据|MQ的最低位|MQ的最低位、辅助位
|
||||
判断关系|MQ的最低位=1时,ACC+x的原码;MQ的最低位=0时,ACC不变|辅助位-MQ中最低位=1时,(ACC)+x的补码;辅助位-MQ中最低位=0时,ACC不变;辅助位-MQ中最低位=-1时,ACC+(-x)的补码
|
||||
移位类型|逻辑右移|算术右移
|
||||
符号位|不参与运算|参与运算
|
||||
|
||||
辅助位其实就是在MQ最后再加上一位,辅助位初始为0。每次右移会使MQ的最低位顶替原本的辅助位(事实上MQ共n+2位)。
|
||||
|
||||
为了保证统一,所以ACC和X都会增加一位,变成n+2位,多出来的一位就可以实现双符号位补码运算,二MQ还是用原理的单符号位。
|
||||
|
||||
为了加快运算会有辅助电路实现(-x)的补码的运算。
|
||||
|
||||
最后一次不需要移位直接根据辅助位和MQ最后一位判断进行相加。从而让乘数的符号位也参数运算中来确定最后结果的符号。
|
||||
|
||||
#### 除法运算
|
||||
|
||||
进行除法操作时,都是为了找到一位能让商乘除数能最大即余数最小但大于0的值。若除数被除数都是小数,可以同时乘一个数变成整数再运算。
|
||||
|
||||
所以可以忽略小数点,每确定一位商进行一次减法,若机器字长为n位,则得到n-1位余数,在余数末尾补0,再确定下一位商0或1,直到确定n位商即可停止。
|
||||
|
||||
在运算器的组成时出现一个表格,说明在进行除运算时,ACC保存被除数和余数,MQ保存商,X保存除数。
|
||||
|
||||
##### 原码恢复余数法
|
||||
|
||||
原码使用恢复余数法进行除运算:
|
||||
|
||||
1. 字长若为n+1位,则ACC、MQ、X全部初始化为n位,将被除数的绝对值放入ACC中,X放入除数的绝对值,MQ初始化为全0。
|
||||
2. 将MQ的最右边的一位当做当前除运算位,让其进行除运算,运算规则是,默认商1,ACC-=X,即x的补码要加上除数的绝对值的负值的补码(减法都由补码的加法实现),判断是否有误。若结果高位为0则无误,高位为1则有误,错误则商改为0,并恢复余数,ACC加上X中除数的补码。
|
||||
3. 将ACC和MQ的数据连接在一起,全部逻辑左移一位,MQ数据低位补0,MQ最高位的0移到ACC的最低位。将ACC的最高一位抛弃。若是第i轮逻辑左移,则MQ的后i位是当前计算的商的结果。
|
||||
4. 从步骤二开始重复,字长若为n+1位,则左移n次,上商n+1次,直到MQ中全部是计算结果,则停止计算。此时MQ中保存商,ACC中保存左移n位的余数值,真正的余数应该是结果再乘上2的-n次方。
|
||||
5. 定点小数的小数位隐藏在符号位后面第一位,定点正数的小数位隐藏在最后一位后。
|
||||
6. 将两个符号位的异或结果赋值给商最高位。
|
||||
|
||||
**例题** 设机器字长为5位(含一位符号位),x=0.1011,y=0.1101,采用原码恢复余数法求x/y。
|
||||
|
||||
其中x就是+0.1011,而y就是+0.1101。先抛去符号位,就得到01011和01101两个数据。然后求出y绝对值的补码:01101和-y绝对值的补码:10011。
|
||||
|
||||
将MQ、ACC、X都初始化为五位存储单元。将被除数01011放入ACC中,将除数01101放入X中,商初始化为00000。
|
||||
|
||||
手算时每位商取0/1是通过判断当前余数和除数的大小确定的。而机器实现时就要通过ALU判断是ACC中的数更大还是X中的数更大,如果ACC的更大就商1,若X的更大就商0。
|
||||
|
||||
第一位默认商1,ACC-=X,ACC的01011和X的10011(X实际值的负值的补码)输入ALU进行加操作01011+10011=11110,返回给ACC,此时发现代表符号的最高位为1,代表出现了负数,就表明之前的商出错了,所以重新确定商为0,ACC要恢复余数,从而再加上y的补码:11110+01101=01011。
|
||||
|
||||
第一位的商计算完后需要进行计算,错位相除,所以同乘法一样,ACC和MQ的值都要逻辑左移一位,低位补0,所以MQ由00000还是变为00000,MQ的最高位的0移到ACC最低为,ACC最高位丢弃,由01011变成10110。
|
||||
|
||||
然后第二位默认商1,同样ACC-=X,10110+10011=01001,将这个值赋给ACC,发现符号位为0,代表正,商就没有问题,MQ为00001。
|
||||
|
||||
再次逻辑左移一位,MQ由00001变为00010,ACC由01001变为10010。
|
||||
|
||||
第三位默认商1,同样ACC-=X,10010+10011=00101,商没有问题,MQ为00011。
|
||||
|
||||
再次逻辑左移一位,MQ由00011变为00110,ACC由00101变为01010。
|
||||
|
||||
第四位默认商1,同样ACC-=X,01010+10011=11101,高位为1,商应该为0,MQ变为00110,ACC恢复余数:11101+01101=01010。
|
||||
|
||||
再次逻辑左移一位,MQ由00110变为01100,ACC由01010变为10100。
|
||||
|
||||
第五位默认商1,同样ACC-=X,10100+10011=00111,高位为0,商没有问题,MQ为01101。
|
||||
|
||||
此时计算结束,商为01101,余数为00111。
|
||||
|
||||
##### 原码加减交替法
|
||||
|
||||
因为恢复余数很麻烦,所以会考虑是否不用恢复余数,直接进行运算得到后面的结果。
|
||||
|
||||
假如令原始值为x,原始值加上-y绝对值的补码结果为a,y绝对值的补码为b,按恢复余数法,a这个余数是一个负值,所以要加上b即a+b变成原始值a+b=x,这时候商0,然后计算下一个商,余数a+b左移一位,即(a+b)×2=2a+2b,这时候商1看看结果是否正确,即2a+2b要减去y绝对值的补码(等价于加上-y绝对值的补码)2a+2b-b=2a+b。
|
||||
|
||||
所以如果得到了一个负的余数a,可以直接转换到2a+b这个结果,即直接左移一位余数再加上除数的补码就可以得到结果。
|
||||
|
||||
这就是加减交通法或不恢复余数法。
|
||||
|
||||
从而恢复余数法就是当余数为负时商0,并+|除数|,再左移,再-|除数|,而加减交替法是当余数为负时商0,并左移,再+[除数|,若余数为正时商1,并左移,再-|除数|。
|
||||
|
||||
值得注意的是,若在最后一步余数为负,需要商0,并加上除数的补码得到正确余数。
|
||||
|
||||
<span style="color:orange">注意:</span>在定点小数运算时,商只能是小数而不能是整数,所以被除数一定要小于除数,机器判断标准是看第一步计算的商,若第一步计算的商是1则代表结果大于1,机器就会报错。
|
||||
|
||||
##### 补码加减交替法
|
||||
|
||||
+ 符号位参与运算。
|
||||
+ 被除数/余数、除数采用双符号位。
|
||||
+ 被除数和除数同号,则被除数减去除数,异号则被除数加上除数。
|
||||
+ 余数和除数同号,商1,余数左移一位减去除数;
|
||||
+ 余数和除数异号,商0,余数左移一位加上除数。
|
||||
+ 重复n次。
|
||||
+ 最后一次计算时末位商横置为1,处理简单,而且精度误差也不会超过$2^{-n}$。
|
||||
|
||||
除法类型|符号位参与运算|加减次数|移位方向|移位次数次数|上商和加减原则|说明
|
||||
:------:|:------------:|:------:|:------:|:----------:|:-----------:|:---:
|
||||
原码加减交替法|否|N+1或N+2|左|N|余数的正负|若最终余数为负,需恢复余数
|
||||
补码加减交替法|是|N+1|左|N|余数和除数是否同号|商末位恒置1
|
||||
|
||||
#### 强制类型转换
|
||||
|
||||
+ 无符号数与有符号数:不改变数据内容,只改变解释方式。
|
||||
+ 长整数转短整数:高位截断,保留低位。
|
||||
+ 短整数转长整数:符号扩展。
|
||||
|
||||
#### 数据存储与排列
|
||||
|
||||
+ 数据最左边的高位就是最高有效字节MSB。
|
||||
+ 数据最右边的低位就是最低有效字节LSB。
|
||||
+ 大端模式:将MSB存到最低地址,LSB存在最高地址。便于人类阅读。
|
||||
+ 小端模式:将MSB存到最高地址,LSB存在最低地址。便于机器读取。
|
||||
+ 边界对齐:
|
||||
+ 现代计算机通常是按字节编址即每个字节对应一个地址通常。也支持按字、按半字、按字节寻址。
|
||||
+ 假设存储字长为32位,则1个字=32bit,半字=16bit。每次访存只能读/写1个字。
|
||||
+ 字地址转换为字节地址,只用逻辑左移两位就可以了,即乘以4,因为字长为32,而字节长8。
|
||||
+ 使用边界对齐方式会让每个数据都能一次性读完而不用跨行读取,多余的空间用0填充。
|
||||
|
||||
## 浮点数
|
||||
|
||||
指小数点的位置不固定,使用科学计数法,如9.694E2。
|
||||
指小数点的位置不固定,如使用科学计数法,如9.694E2。
|
||||
|
||||
### 浮点数表示
|
||||
|
||||
#### 阶码与尾数
|
||||
|
||||
+ 定点数能表示的数字范围有限,但我们不能无限制地增加数据的长度。
|
||||
+ 类似科学计数法,分为阶码和尾数两个部分,阶码反映数值大小、表示范围、小数点实际位置,尾数反映精度。
|
||||
+ 对于二进制的浮点数,阶码是常用补码或移码表示的定点整数,而尾数是常用原码或补码表示的定点小数。
|
||||
+ 若阶码的真值为$E$,尾数的真值为$M$,则浮点数的真值为$N=r^E\times M$,其中r为阶码的底,即基数,一般为2。
|
||||
|
||||
**例题** 若阶码和尾数都使用补码表示,求对应真值:a=0,01;1.1001。
|
||||
|
||||
a的阶码为0,01,是正数,所以补码与原码一样,从数值来看就是+1。而尾数1.1001代表负数,补码为反码加1,所以真值为1,0110+1=1,0111,即=-(0.25+0.125+0.0625)。所以a的真值就是2×(-0.0111)=-0.111=-0.875(相当于乘2左移一位)。
|
||||
|
||||
#### 尾数规格化
|
||||
|
||||
+ 左规:出现下溢需要左规,即若尾数的高位是无效值(即为0)则会丧失精度,所以我们需要尽可能将尾数多保存一些1,从而让最高位为1。所以需要让数值左移,让小数点右移,尾数算术左移n位,阶码减n,直到尾数最高位是有效值。
|
||||
+ 右规:出现上溢需要右规,规范要求小数点要在第一个非0的数据右边,如果小数点前有超过1个有效位,则需要将数值右移,小数点左移,尾数算术右移n位,阶码加n,直到小数点在尾数最高位的右边。
|
||||
|
||||
**例题** 若a=010;00.1100,b=010;00.1000,求a+b的值。
|
||||
|
||||
已知分号前面的是阶码,后面是尾数,所以a和b都是2的010=2次幂。
|
||||
|
||||
由尾数的00代表a和b都是双符号位表示且都是正数。
|
||||
|
||||
所以a=2×2×00.1100,b=2×2×00.1000,则a+b=2×2×00.1100+2×2×00.1000=2×2×(00.1100+00.1000)=2×2×01.0100。
|
||||
|
||||
因为使用双符号位表示时,00代表正号,11表示负号,01时,称为上溢,为10时,称为下溢,此时结果为01,表示出现了上溢,这时候就需要右规。
|
||||
|
||||
阶码加一,变成2的三次方,尾数右移一位=2×2×2×00.1010。最后结果就是011;01010。
|
||||
|
||||
规格化浮点数的特点:
|
||||
|
||||
1. 用原码表示的尾数进行规格化,最高位数值一定为1:
|
||||
+ 正数为0.1××...×的形式,其最大值表示为0.11...1;最小值表示为0.10...0。
|
||||
+ 尾数的表示范围为$\dfrac{1}{2}\leqslant M\leqslant(1-2^{-n})$。
|
||||
+ 负数为1.1××...×的形式,其最大值表示为1.10...0;最小值表示为1.11...1。
|
||||
+ 尾数的表示范围为$-(1-2^{-n})\leqslant M\leqslant\dfrac{1}{2}$。
|
||||
2. 用补码表示的尾数进行规格化,符号位与最高位数值一定相反:
|
||||
+ 正数为0.1××...×的形式,其最大值表示为0.11...1;最小值表示为0.10...0。
|
||||
+ 尾数的表示范围为$\dfrac{1}{2}\leqslant M\leqslant(1-2^{-n})$。
|
||||
+ 负数为1.0××...×的形式,其最大值表示为1.01...1;最小值表示为1.00..0。(负数的补码1.0xx...x取反后就是1.1xx...x)
|
||||
+ 尾数的表示范围为$-1\leqslant M\leqslant-(\dfrac{1}{2}+2^{-n})$。(补码中强制规定1.00...0就代表-1)
|
||||
|
||||
### IEEE 754标准
|
||||
|
||||
### 浮点数运算
|
||||
|
||||
## 算术逻辑单元
|
||||
|
||||
|
||||
Reference in New Issue
Block a user