计算机为何要设计补码,而不是绝对值?

2024-11-07

我之所有有这个疑问,是发现Java中的8字节(32位)的整型long,为什么只能代表$-2^{31}$ ~ $2^{31}-1$?

为什么正数这边要-1呢?不是1个符号位,剩下31个代表数字(取绝对值正反值)就好了?

不过,我的第一个想法是,那么0怎么办?正负0有两个呀,那个才是0呀。

当然,不只我想到的这个问题,还有其他问题,都可以用补码去解决。

符号-绝对值表示法(Sign-Magnitude Representation),在这种表示法中:

  这种方法在理论上是可行的,但补码表示法有几个关键的优势,使得它在计算机系统中更适合:  

  1. 简化了加减运算
  1. 唯一的零表示
  1. 符合二进制溢出的规则  
  1. 硬件设计方便

结论

  虽然符号-绝对值表示法在直观上更简单,但补码表示法的这些优点使得它在计算机系统中成为首选。补码的表示方式不仅有效地解决了符号问题,还简化了计算、硬件设计以及处理逻辑,这也是为什么现代计算机体系结构广泛采用补码的原因。

为什么127+1=-128?

补码的角度

带符号的运算,计算机底层都是用补码来存储的。两者的补码形式如下:

complement-code

计算的角度

由于01111111是127,127+1是10000000

以上都是补码。

由于补码的最高位可以参与运算,即又代表符号,又能运算。

因此,

$$ -1\times2^7+0\times2^6+...=-128 $$

补码的快速运算

补码的最高位参与运算。例子:

1001 1001

简单算法

直接计算。

-128 + 16 + 8 + 1 = -103

复杂算法

取反码,再取原码,再转换。

减一得反码

1001 1000

取反得原码

1110 0111

算数

-(64+32+4+2+1)=-103