【计算机组成原理】有符号数多表示一位负数

简述

不管是数据库、还是开发语言对固定长度的有符号数据存储,都存在能够多表示一位负数的现象,解释这个现象必然绕不开补码。文章希望通过一些易于理解的白话来简答这个问题。

计算机组成原理

本节内容来自《计算机组成原理》第六章第一节,以及个人理解

原码

原码是最简单的一种表现形式。最高位作为符号位,0表示正数,1表示负数。数值位是数值绝对值

数值源码
20010
-31011

原码表示简单明了,并且容易和数值转换。但是使用原码做加减运算却不简单了。当两个正数(负数)相加时还能用简单的进位得到结果。但是正负数相加的时候,首先需要判断结果的正负,然后做减法运算才能得到最后的结果。这样的运算步骤即复杂又耗时,能不能让计算机只有简单的加法呢?聪明的科学家们使用补码解决这个问题(科学也是人类的赞歌)

补码

书中通过时钟的例子来讲补数的概念:时钟现在指向6点钟,如果想让时钟指向3点钟,需要顺时针走9个小时或者逆时针走3个小时。这在数学上称为,对模12而言,-3和+9互为补数。
表达式:6 + (-3) = 3 mod 12 = 6 + (12 - 3) = 15 mod 12 = 3

换句话说,在进位溢出运算中,加上一个负数等价于加上这个负数的正补数。负数(-3)的正补数通过模加上负数求得(12 + -3 = 9)。这样我们成功将减法运算转换为加法运算。

计算机中使用固定长度存储,进位会被舍弃,天然的适配进位溢出规则。我们将正数不变、负数使用正补数替代这套规则称为补码,并应用到计算机中,就只剩加运算且不需要关注符号位。

结论:
补码消除了负数,大大降低了计算量

补码的计算

刚刚提到补数是为了消除减法出现的,但是计算负数正补数的时候还是出现了减法运算。为了消除这里的减运算,计算机科学中出现了另一种计算负数正补数的思路:原码除符号位外每位取反,末位加1
符号太难搞,直接贴图,解释两点

  • 图中计算-1011的补数,数值位有4位,所以模是下一个进位2的4+1次方(这里可以类比时钟的最大是11点,模为11 + 1)
  • 求反加1的结论是通过式(6.3)和原码对比获得,计算过程都是无符号位,不要和原码混淆
    在这里插入图片描述

到这里,我们知道计算机系统中有一个很容易的计算负数正补数的方法(取反加1)

结论:

原码反码补码
正数0xxx本身本身
负数1xxx符号位外取反反码+1

多出来的负数

假设4位存储,我们已知能够存储的数值范围是-8 ~ 7,计算-8的补码
x = -8 = -1000
16 - 8 = 1 0000 - 1000 = 1000
-8补码为1000,这与4位存储相匹配

此外+0 和 -0的补码都是0000,所以补码会比原码多一个负数

我想说的

我之前只记住了负数补码的计算结论(取反加1),没有了解补码的计算过程。
认为1000符号位是1,一定是表示一个负数的结论,来证明1000表示-8的补码更合理。

数字原码反码补码
+80 10000 10000 1000(高位舍弃)
-81 10001 01111 1000(高位舍弃)
只是感觉这样理解不够严谨,也说不出哪里有问题,直到这次复习补码的知识,才真正了解,-8就在那里,只是我没有走进它

https://stackoverflow.com/questions/3621067/why-is-the-range-of-bytes-128-to-127-in-java

欢迎大家留言交流讨论,如果对你有帮助,请点个赞吧

  • 3
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值