补码反码

原码

正数的源码是他本身(0+其他位),负数的源码是1+其他位, 如图 在4位二进制中,第一位表示符号,其他位表示数的二进制

正数 二进制 负数 二进制
0 0000 - -0 1000
1 0001 - -1 1001
2 0010 - -2 1010
3 0011 - -3 1011
4 0100 - -4 1100
5 0101 - -5 1101
6 0110 - -6 1110
7 0111 - -7 1111

当两个值相加时

普通数字相加 二进制数字相加
(+1)+(+2)=(+3) 0001+0010=0011
(+0)+(-0) = (-0) 0000+1000 =1000
(+1) + (-1) = (-0) 0001+1001 = 1010

存在问题

  1. 0分正负
  2. 相反数相加为-0
  3. 如果存在(+2) + (-3) = -1
普通数字相加 二进制数字相加 实际值 正常二进制
(+2)+(-3)=(-1) 0010+1011=1101 -5 1001

因此在计算时

  1. 两位数相加,先判断符号,同号加法,异号减法

反码

  1. 正数的反码,仍是本身,负数的反码,对真值取反,符号位保持不变
正数 反码:二进制 负数 反码:二进制 负数 源码:二进制
0 0000 - -0 1111 - -0 1000
1 0001 - -1 1110 - -1 1001
2 0010 - -2 1101 - -2 1010
3 0011 - -3 1100 - -3 1011
4 0100 - -4 1011 - -4 1100
5 0101 - -5 1010 - -5 1101
6 0110 - -6 1001 - -6 1110
7 0111 - -7 1000 - -7 1111
  1. 当两数反码相加
普通数字相加 二进制数字相加
(+1) + (-1) = (-0) 0001+1110=1111 正确
(-1)+(-3)=-5 1110+1100=1010 错误

所以:反码不能用于运算

补码

正数的补码等于它的原码;负数的补码等于反码+1

正数 补码:二进制 负数 补码:二进制
0 0000 - -0 0000
1 0001 - -1 1111
2 0010 - -2 1110
3 0011 - -3 1101
4 0100 - -4 1100
5 0101 - -5 1011
6 0110 - -6 1010
7 0111 - -7 1001
-8 1000

补码中不存在 0 应为 1111 + 1 = 10000为五位,溢出。 -8 = 1000

普通数字相加 二进制数字相加
(+1) + (-1) = (-0) 0001+1111=10000 = 0000 正确
(-1)+(-3)=-5 1111+ 1101 = 11100 = 1100 正确

实际计算机中,多用补码运算

原理解析

在时钟运算中,一圈为12小时,当在6点时 减去 3小时 为 3点,那么加上 (12 - 3)小时 也是 15点,也是3点,也就是说(12-3)为6的同余数

则称 12 为 模, 3 与 9 互补

这样就将 -3 的减法变成了 +9的加法

同样将 二进制中,如果数值位数为 4位,第一位代表符号,那么 模 就为 2^3 也 就是 8

-3 的 同余数为 (8 - 3) = 5, 源码为 0101,再补上符号位 1101
-1 的 同余数为 (8 - 1) = 7 ,源码为 0111, 再补上符号位 1111

两数相加为 11100,取四位 1100,

其他基础计算

n & ( n -1 ) 可以消掉最后一个1

n & 1 可以判断最后一个位是0还是1