首页 > 技术文章 > 原码,反码,补码

liuconglin 2016-10-08 16:59 原文

基础概念

原码, 反码, 补码是机器存储一个具体数字的编码方式

机器数: [00000001]原码,用最高位0表示正、1表示负, 这种正负号数字化的表示形式就称为“机器数”

真值:[00000001]原码,可以转化为一个具体的数字,这个数字称为真值

编码:将一个真值表示成二进制字串的机器数的过程就称为编码。

为什么要有原码

计算机可以有三种编码方式表示一个数,原码才是被人脑直接识别并用于计算表示方式,但是在计算机系统中,数值一律用补码来表示(存储)

为了使计算机运算的更简单,机器可以只有加法,而没有减法

原码计算:

例如: 0 =  1 - 1 = 1 + (-1) = [00000001]原 (1) + [10000001]原(-1) = [10000010]原 = -2      结果显然是不对的 

为什么要用反码

为了解决原码做减法的问题, 出现了反码:

反码计算:

1 - 1 = 1 + (-1) = [0000 0001]原 + [1000 0001]原= [0000 0001]反 + [1111 1110]反 = [1111 1111]反 = [1000 0000]原 = -0  

真值部分是正确的,但是会有[0000 0000]原和[1000 0000]原两个编码表示0,因为+0和-0是一样的

为什么要用补码

解决了0的符号以及两个编码的问题

补码计算:

1-1 = 1 + (-1) = [0000 0001]原 + [1000 0001]原 = [0000 0001]补 + [1111 1111]补 = [0000 0000]补=[0000 0000]原 = 0

这样,不会出现用补码计算时值为-0

8位二进制的最小值问题:

补码表示最小值:

(-1) + (-127) = [1000 0001]原 + [1111 1111]原 = [1111 1111]补 + [1000 0001]补 = [1000 0000]补 = -128

但是

-128 =  [1000 0000]补 = [0111 1111]反 = [0000 0000]原 = 0 = [1000 0000] = -0   显然是错误的

得出结论: -128 并没有原码和反码表示

因此,使用补码, 不仅仅修复了0的符号以及存在两个编码的问题, 而且还能够多表示一个最低数,这就是为什么8位二进制, 使用原码或反码表示的范围为[-127, +127], 而使用补码表示的范围为[-128, 127].

原码,反码,补码如何计算

反码的表示方式:  正数的反码是其本身;负数的反码是在其原码的基础上, 符号位不变,其余各个位取反

[+1] = [00000001]原 = [00000001]反

[-1] = [10000001]原 = [11111110]反

补码的表示方法:  正数的补码就是其本身 ; 负数的补码是在其原码的基础上, 符号位不变, 其余各位取反, 最后+1. (即在反码的基础上+1)

[+1] = [00000001]原 = [00000001]反 = [00000001]补

[-1] = [10000001]原 = [11111110]反 = [11111111]补

从补码推出原码,需要复习一下二进制减法运算, 借1当2, 如下图

 

 

推荐阅读