汇编(注)二、二进制运算

源码、反码、补码

  • 数字在自然界中抽象出来的时候,是没有正数和负数的概念的(一个人,两个人,而没有负一个人);
    计算机保存最原始的数字,也是没有正负概念的,叫无符号数;
    我们在内存中分配8位(一个字节)去存放无符号数字,是下面这样的:


  • 后来生活中为了表示“欠别人钱”这个概念,从无符号数中,划分了正数和负数;
    为了表示正与负,在计算机中,人们发明了源码,把生活中的正负概念表示出来;

把二进制左边的第一位,用来表示符号,正用0来表示,负用1来表示;

  • 但是使用原码的方式,方便了我们人类,却苦了计算机;
    我们希望(+1)+(-1)=0,但是计算机只能算出0001+1001=1010(-2)
    为了解决“正负相加等于0”的情况,在“原码”的基础上,人们发明了“反码”

反码表示方式是用来处理负数的,符号位不变,其余位数取反(0变为1,1变为0);


当“原码”变成“反码”时,完美解决了“正负相加等于0的情况”;
(+1)+(-1)=0001+1101=1111=-0

  • 还有一个问题,在正数与反码中,有两个0:+0和-0;为了解决这一个问题,又发明了“补码”;

“补码”的意思是,在原来“反码”的基础上,再补充一个新的代码,即加+1;

我们要处理“反码”中的-0,当1111补上一个1之后边城了10000,丢掉最高位就是0000,搞好就是正数中的0;这样就解决了+0和-0同时存在的问题;
另外正负相加等于0也解决了;
同时我们失去了-0,也多了一个-8;

  • 结论:补码就是保存正负数最好的方案。

八位的有符号数

十进制 二进制 十进制 二进制
0 0000 0000 -1 1111 1111
1 0000 0001 -2 1111 1110
2 0000 0010 -3 1111 1101
3 0000 0011 -4 1111 1100
.. .... .... .. .... ....
124 0111 1100 -125 1000 0011
125 0111 1101 -126 1000 0010
126 0111 1110 -127 1000 0001
127 0111 1111 -128 1000 0000

算数运算

符号位参与运算,接受来自低位的进位,永远能忠实的表示结果的正负;

正数 + 正数 = 正数

120 + 5 = 125


计算结果01111101就是125,所以没有溢出

正数 + 正数 = 负数

120 + 10 = 130


计算结果10000010是-126,计算结果明显不正确,所以产生了溢出;

负数 + 负数 = 负数

(-120) + (-3) = (-123)


计算结果10000101是-123,计算结果正确,所以没有溢出;

负数 + 负数 = 正数

(-120) + (-9) = (-129)


计算结果01111111是127,计算结果不正确,所以产生了溢出;

正数 + 负数

(-127) + 3 = (-124)


计算结果10000100是-124,计算结果正确,没有产生溢出;

溢出与进位

处理器内部以补码表示有符号数,8个二进制位能表达的正数范围是+127-128,16位表达的范围是+32767-32768,如果运算超出了这个范围,就产生了溢出;有溢出,表明有符号数的运算结果不正确;
例如:

3AH + 7CH = B6H ; 58 + 124 = 182
182已经超出了127~-128这个范围,所以产生溢出;另外补码B6H的值是-74,显然运算结果也不正确;

溢出标志和进位标志是两个意义不同的标志;

  • 进位标志:表示无符号数运算结果是否超出范围,运算结果仍然正确;
  • 溢出标志:表示有符号数运算结果是否超出范围,运算结果不正确;
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容