域名 网站,灯塔网站seo,懒人手机网站模板,企业计划书怎么写问题#xff1a;
我们每天用的钟表#xff0c;其实只有1~12这12个数字#xff0c;但我们日常会说13点、17点之类的。 问#xff1a;13点在钟表上哪个位置#xff1f; 答#xff1a;很简单嘛#xff0c;1点的位置。 你不觉得奇怪吗#xff0c;为啥13点会和1点在同一个位…问题
我们每天用的钟表其实只有1~12这12个数字但我们日常会说13点、17点之类的。 问13点在钟表上哪个位置 答很简单嘛1点的位置。 你不觉得奇怪吗为啥13点会和1点在同一个位置换言之13和1有啥关系17和5有啥关系计算机里为啥要用加法替代减法 当然是加法电路设计比减法电路设计简单了加法电路详见CPU之图解算数逻辑单元ALU 怎么用加法替代减法
一、基本概念
1.0、余数(remainder)
在算术中当两个整数相除的结果不能以整数商表示时余数便是其“余留下的量”。当余数为零时被称为整除。 即被除数 / 除数 商……余数用数学表示 a qd r, 0 r d其中a为被除数q为商(quotient)d为除数(divisor)r为余数(remainder)。 举例当除数为4时任何正数除以4时余数总在0, 1, 2, 3中
0 / 4 0 …… 0
1 / 4 0 …… 1
2 / 4 0 …… 2
3 / 4 1 …… 3
4 / 4 1 …… 0
5 / 4 1 …… 1
6 / 4 1 …… 2
7 / 4 1 …… 3
8 / 4 2 …… 0
……如上被除数从0开始递增时余数会在0, 1, 2, 3中一直循环下去这就是同余 现在我们考虑除数为10时则余数在0~9这10个数字中出现把这10个数字同样置于圆盘中如上图所示。 在0-9这10个数字的圆盘中再也不会有其它数字了也就是我们限定了我们的数字范围为0~9数字个数(记为模)为10。 给定圆盘上任一个数字作为起始点记为 src任一个数字为 终止点记为dest我们考虑从src出发如何到达dest可以 前进记为 可以后退记为 - 。 举例 src 3dest 4; 前进1步1即 3 1 4后退9步-9 即 3 - 9 4 src 3dest 3; 前进0步0即 3 0 3后退(91)步-(91) 即 3 - ( 9 1) 4// 因为我们限定了数字范围为0~9所以写成9 1 src 5dest 9; 前进4步4即 5 4 9后退6步-6 即 5 - 6 9 通过上面的例子发现了吗
对于确定的起止点如src 3dest 4不管前进或者后退我们都可以到达也就是说前进1步等价于后退9步前进步数和后退步数之和为模10模意味着啥模意味着走了一圈一个轮回起点走一圈又回到了起点
1.1、补数(complement)
定义对于给定的进位制相加后能使自然数 a 的位数增加 1 的最小的数。 说人话就是前面前进和后退的步数等价的组合如1和9、2和8、3和7、4和6也即可以组成模如10的组合。 即 当 a 1时a只有1位数字即个位要想将a变成211位数字10十位、个位需要增加9。 所以 9是1的补数当然1也是9的补数即1、9互为补数 同理2、8互为补数 3、7互为补数 4、6互为补数 问 36的补数是多少 答64
根据上面定义我们知道对于整数aa的补数 模 - aa0; 补数有啥用 还是回到之前我们0~9这10个数字的圆盘上来我们来算小学生都会的10以内的加减法 一顿操作猛如虎一看结果直呼OMG, 正如上图所示减掉一个数等价于加上这个数的补数。 这里有个重要的前提数字是有范围的上面我们限定了0~9这10个数字
1.2、减法
根据我们上面的结论当数字是有范围的则对于这个范围内的数字减掉一个数等价于加上这个数的补数我们可以用加法替代减法进一步减去一个正数相当于加上这个正数对应的负数。 还是回到我们前面提到的圆盘上来我们把这条结论实践下
我们先在坐标轴上标出0~9这10个数字范围然后移动这个范围框使框内正负数个数大致相等如下图所示数字范围变成了-5 ~ 4这10个数字。 将坐标轴上的数字范围同步映射到圆盘上。 此时圆盘上数字的运算可以用圆盘外相对应的数字进行替代即圆盘上的数字范围已经改变了由之前的0 ~ 9 变成了现在的 -5 ~ 4 。
1.3、补码
看到这里不知道你是否认可前面的推导结论 不认可不认可就对了。聪明的你一定发现了上面的计算的问题 1 - 5 -4在我们映射后变成了 1 5 6 但 -4 不等于 6虽然圆盘上6确实对应**-4**但我们需要的是正确的结果-4怎么将6转换成-4?
好了为了后面好叙述我们先给实际求值结果记为原码映射后的结果记为补码。我们先分析下实际的求值结果和映射后的结果 发现原码为0和正数时补码正确即原码为0和正数时原码等于补码原码为负数时补码错误即原码为负数时原码不等于补码。
问题来了原码为负数时补码如6怎么转换成原码如-4 答: 谜底就在谜面上你直接看圆盘不就好了圆盘上都标注了圆盘内外侧的数字就是我们原码和补码的映射表。 问题又来了圆盘上的映射怎么来的 答通过补数变换得到的即原码为负数时补码 |原码| 模也即原码为负数时补数 |原码| 模在1.1小节中我们提到了 a的补数 模 - aa0;
综上原码为负数时补码 |原码| 模
二、 二进制里的花花世界
宏观世界搞定了看看微观世界十进制搞完了看看二进制。 二进制我们以1Byte(8bit)研究1 Byte 可以表示256个数28即模为256
2.1 原码
1 Byte 范围的内数字为0~255这256个数字。将其置于圆盘上如下
2.2 补码
调整数字范围使其映射到 -128~127 这256个数字 调整圆盘范围即原码写到圆盘上补码写到圆盘外如下
2.3 补码和原码转换
原码和补码怎么转换呢 通过1.3节我们知道如下结论
原码为0和正数时原码等于补码原码为负数时补码 |原码| 模 还记得我们在1.3 小节 文末得到的结论吗原码为负数时补码 |原码| 模我们变换下这个等式即原码为负数时补码 模 - |原码|按照公式我们计算下 至此二进制的原码和补码转换我们也已搞定即原码为0和正数时原码等于补码原码为负数时补码 模 - |原码|
2.4 反码
不知道你绕晕了吗还记得我们的初心吗怎么用加法替代减法 2.3 节说原码为负数时补码 模 - |原码|这玩呢前面这么多推理就是想用加法替代减法结果搞了半天回到了原点还使得计算减法自己替代自己吗替代了个寂寞……
不急稍安勿躁且听下面道来。
2.4.1 模
细想下 补数的定义使得当前数的位数增加1位
假设二进制下当前为8位问要使得增加的数最小时怎么才能使得位数增加1位呢即由原来的8位变成9位 答增加的数为1时最小此时当前8位数达到了最大那就是0b 1111 1111即0b 1111 1111 0b 0000 0001 0b 1 0000 0000 所以我们找到了二进制8位数即将跳变成9位的临界值即当前8位数的最大值0b 1111 1111二进制时一个数变成最大的最快方式当然是加上该数按位取反后的值。即 0b 1111 1111 - 0b 0000 0001 0b 1111 1110看到了吗0b 1111 1110正好等于0b 0000 0001按位取反的值那就叫它反码吧即原码为负数时反码为原码数据位按位取反注意这里是数据位最高位为符号位“为使得定义一致和完整我们补充原码为0和正数时原码等于反码。 我们来求下 模 如上图所示原码为负数时模 (256) 8bit最大值 1 8bit最大值 原码的绝对值 反码结合之前的 原码为负数时补码 模 - |原码| 得到 至此1 Byte 的数据我们通过补码的形式用加法替代了减法。计算机语言内的整数类型比如java的 int (4Byte)、long(8Byte) 都是如此。
三、总结
为了使用加法替代加法我们先后引入了补数、模、原码、补码、反码等概念
圆盘代表数字是有范围的该范围的大小即为模并且会首尾相连。计算机1 Byte、4Byte、8Byte天然会限定数据的范围。数据范围限定后数据一直累计下去一定会产生数据溢出即进位丢失从而结束当前轮回开始下一轮回圆盘内的数字是原码圆盘外的数字是补码补码也是模内的无符号整数。注意反码 1只是求得补码的一种方式并非补码的定义原码为0和正数时原码等于反码等于补码原码为负数时反码为原码数据位按位取反。