菜鸟笔记
提升您的技术认知

原码补码反码的范围

原码、反码、补码的表示范围是如何得到的

原码
    纯整数的原码
    纯小数的原码
反码
    纯整数的反码
    纯小数的反码
补码
    纯整数的补码
    纯小数的补码

原码

首先说原码,原码是有符号数中最简单的编码方式。原码表示法在数值前面增加了一位符号位(即最高位为符号位):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为机器字长为例,由于正数的反码与补码相同,因此对于最大正数的由来这里不多赘述,同上。那么最小负数如何得来?
其实与原码也是同一个道理,但是由于负数的反码要按位取反,数值位的全0会变成全1,同样,如果真值的数值位为全1,那么反码表示则会为全0,加上符号位的1,
即最小负数用原码可表示为1,1111111,反码则表示为1,0000000,即反码可表示的最小负数–(27–1)。
故当机器字长为n+1时,
纯整数的反码表示范围是 – (2n–1) ≤ x ≤ 2n–1,与原码是相同的。
纯小数的反码

纯小数的反码与上述纯整数的反码是类似的,这里不多赘述,它的表示范围与纯小数的原码是相同的,最关键的就是记住按位取反。
故纯小数反码的范围是 – (1–2–n) ≤ x ≤ 1–2–n(机器字长为n+1)。
补码

由于正数的原码、反码和补码都是相同的,故在这里我们就只讨论负数,而最大值(即最大正数)都是同原码相同的。
补码是在反码的基础上(按位取反),末尾再加1。
纯整数的补码

要正确理解补数,必须要知道补码就是同余。机器字长为8位时,只能表示256个数,但我还想表示一些负数怎么办?就用该负数同余的正数来表示。例如-1=255,-2=254。它的模就是28=256,而负数的补码为模与该负数绝对值的差值,则 – 128 = 256 – 128 = 128,所以–128的补码是10000000。无符号正数从0到255,补码表示的有符号正数从-128到127,其实刚好都是一个相互对应的。
由此可知,当数值位为n时(机器字长为n+1),
纯整数的补码的范围是 – 2n ≤ x ≤ 2n–1
纯小数的补码

对于小数,补码的最小负数是最让人难以理解的,为什么补码的1.000 0000对应的真值是-1呢?
如果我们采用对补码取反加一的方法,可以发现结果根本就不是这个值,而结合前面纯小数原码的取值范围,我们发现,在纯小数中,原码和反码都不能表示-1, 他们都只能表示纯整数的-1。从纯小数补码的定义可知,-1.0的补码为2–1.0=1.000 0000。有没有发现这跟上述的纯整数的补码非常相似,只不过纯整数的补码模取的是2n+1,而纯小数补码中,模取的是2,这样我们对于负数的补码就可以清晰的理解了。

因此,纯小数补码的范围是 – 1 ≤ x ≤ 1–2–n(机器字长为n+1)。

综上可发现,原码和反码的表示范围是相同的,记住一个,另一个也就记住了,而补码的表示范围中,最大正数是与原码反码相同,但是负数就有区别了。对纯小数来说,补码可表示的最小负数是 – 1;对于纯整数来说,补码可表示的最小负数是 – 2n。