计算机组成原理——原码、反码、补码的表示范围是如何得到的?
原码
首先说原码,原码是有符号数中最简单的编码方式。原码表示法在数值前面增加了一位符号位(即最高位为符号位):0表示为正数,1表示为负数,其余为数值位,表示数值大小。
纯整数的原码
原码的范围是 – (2n–1) ≤ x ≤ 2n–1(n是整数位数)
这是如何得到的呢?
以机器字长为8为例,符号位占1位,那么剩下有7位的数值位,如果不考虑整数的符号,那么这7位数最大的时候为全1,即111 1111,转换为十进制为27–1。
当符号位为0,即0111 1111,此时该数最大,为27–1;
当符号位为1,即1111 1111,此时该数最小,为 – (27–1) 。
即当数值位有n位时(机器字长为n+1位),
纯整数的原码的范围是 – (2n–1) ≤ x ≤ 2n–1。
纯小数的原码
原码的范围是 – (1–2–n) ≤ x ≤ 1–2–n(n是数值位数)
同样以机器字长为8为例,即有7位的数值位,如果不考虑小数的符合,那么这7位数最大的时候为全1,即0.1111 111,那这该怎么计算?难道要用2-1+2-2+……+2-n吗?如下图所示:即当符号位为0,即0.1111111,此时该数最大,表示为1–2–7;
当符号位为1时,即1.1111111,此时该数为负数,且为最小负数,表示为 – (1–2–7)。
即当数值位有n位时(机器字长为n+1位),
纯小数原码的范围是 – (1–2–n) ≤ x ≤ 1–2–n(n是数值位数)。
反码
反码通常用来作为由原码求补码或由补码求原码的中间过渡。
正数的反码与原码是相同的,而负数的反码是将数值位按位取反,就可以得到。
纯整数的反码
以8为机器字长为例,由于正数的反码与补码相同,因此对于最大正数的由来这里不多赘述,同上。那么最小负数如何得来?
其实与原码也是同一个道理,但是由于反码要按位取反,数值位的全1会变成全0,同样,如果真值的数值位为全0,那么反码表示则会为全1,加上符号位的1,
即真值为1000 0000,反码则表示为1111 1111,即反码可表示的最小负数–(27–1)。
故当机器字长为n+1时,
纯整数的反码表示范围是 – (2n–1) ≤ x ≤ 2n–1,与原码是相同的。
纯小数的反码
纯小数的反码与上述纯整数的反码是类似的,这里不多赘述,它的表示范围与纯小数的原码是相同的,最关键的就是记住按位取反。
故纯小数反码的范围是 – (1–2–n) ≤ x ≤ 1–2–n(机器字长为n+1位)。
补码
由于正数的原码、反码和补码都是相同的,故在这里我们就只讨论负数,而最大值(即最大正数)都是同原码相同的。
补码是在反码的基础上(按位取反),末尾再加1。
纯整数的补码
我们还是以8为机器字长为例, 如果不考虑符号位,只要在反码的基础上加1即能得到最大值,由于反码表示为全1的时候,最大,那么当该值加上1,也应该是最大值,故数值位的1111111+1=1000 0000,即27,明显范围比反码更大一些了。再把符号位1加上,即1 1000 0000,为 –27。
由此可知,当数值位为n时(机器字长为n+1),
纯整数的补码的范围是 – 2n ≤ x ≤ 2n–1
纯小数的补码
对于小数,负数的补码是反码的数值位再加1得到,而用反码表示的最小的负数用二进制表示为1.11…11,在此基础上再末尾加1,其实相当于是在不考虑符号的情况下,用0.11…11+1=1.00…00(注意:这是二进制,逢二进一,同时是在末尾加1,不等于1.11…11)。故得,最小负数为 -1。
因此,纯小数补码的范围是 – 1 ≤ x ≤ 1–2–n。
综上可发现,原码和反码的表示范围是相同的,记住一个,另一个也就记住了,而补码的表示范围中,最大正数是与原码反码相同,但是负数就有区别了。对纯小数来说,补码可表示的最小负数是 – 1;对于整数来说,补码可表示的最小负数是 – 2n。