原码、反码、补码、与无符号数(C语言)
一、原码
将最高位作为符号位(0代表正,1代表负),其余各位数组代表数值本身的绝对值。
打个比方
+7的原码是0000 0111
-7的原码是1000 0111
最高位决定了这个数是正数还是负数,其余位数就是该数的二进制。
二、反码
如果一个数为正,那么它的反码和原码相同。
如果一个数为负,那么符号位为1,其他个位与原码相反。
+7的反码0000 0111 与原码相同
-7的反码1111 1000 首先最高位要为1,其次其他的位数要与原码相反
三、补码
正数的原码、反码、补码都相同
负数最高位为1,其余个位于原码取反,最后+1,也就是说先反码再+1就是补码
+7的补码 0000 0111
-7的补码 1111 1001 1111 1000是-7的反码,再在最后+1就变成了补码
在计算机里,负数都是按照补码存放的,原码和反码都不利于计算机的运算,假如7 - 7还需要判断符号位,如果使用补码,减法可以用加法来实现。
0000 0111 + 1111 1001 = 1 0000 0000 再进行截取,因为这是九位,已经超出了最大值,截取出来的全是0,所以结果就是0了。
再打个比方-7 + 6 = -1
1111 1001 + 0000 0110 = 1111 1111 = -1
注意:这里的结果1111 1111是补码,-1的原码是1000 0001,反码是1111 1110,变为补码后就成了1111 1111
在c语言中验证这个结果
#include
int main(int argc, char const *argv[])
{
//结果为:FFFFFFF9
//前面F的是为了补齐位数,为了方便从F9开始算
//F9 = 1111 1001
printf("%X\n", -7);
//结果为:6
//这个是正数,不需要补码
//6 = 0000 0110
printf("%X\n", 6);
//结果为:FFFFFFFF
//截取一下最后的FF
//FF = 1111 1111(补码形式)= -1
printf("%X\n", -7 + 6);
return 0;
}
四、无符号数
无符号数指的是二进制里的最高位也可以表示这个数的大小,而不是表示这个数的正负,有符号数的最高位代表了这个数是正数还是负数。
unsigned int a = 0;无符号数使用unsigned关键词定义
假如说一个char类型变量,char类型的最大值是0111 1111 = 127,最小值是1111 1111 = -127,如果无符号数那么它的最大值为:1111 1111 = 255,为什么?最高位的1不再表示正负数了,这也代表着使用无符号数就没有负数了,所以它的取值范围是0-255。