负数
关于负数,一般采用2的补码方式。为什么采用这种方式?
主要是考虑计算机通常是用加法计算器来做减法。
x - x =x + (-x) = 0
显然,计算机中x和-x均为2进制, x 与-x相加一般会大于0.
什么情况下会等于0呢? 取余数。对谁取余数? 2的N次方。
N是什么? 数据的大小。对于int来说,通常N=32.
这样我们便有了 -x = 2的N次方 - x
定义 y为 对x每个bit位取反,显然有 x + y = 111...1 (N个1) = 2的N次方 -1
这样 -x = 2的N次方 - (2的N次方 -1 -y) = y + 1
对于 -5 我们可以在32位int下这样表示:
5的二进制是 00000000 00000000 00000000 00000101
每位取反是 11111111 11111111 11111111 11111010
加1后为: 11111111 11111111 11111111 11111011
对应16进制为: 0xFF FF FF FB
可以写个代码测试下:
int testMinusInt()
{
int x = -5;
printf("-5 = 0x%8x\n", x);
}
深入理解2的补码表示,一般需要了解离散数学中的闭包概念。
详细分析可以参考:
Computer Systems--A Programmer_s Perspective 第2章第2节
深入理解计算机系统(程序员的观点)
无符号数与有符号数的转换
疑问1: 相互之间转换有数据丢失吗?
写一个简单的测试代码
int testSign2Unsign()
{
关于负数,一般采用2的补码方式。为什么采用这种方式?
主要是考虑计算机通常是用加法计算器来做减法。
x - x =x + (-x) = 0
显然,计算机中x和-x均为2进制, x 与-x相加一般会大于0.
什么情况下会等于0呢? 取余数。对谁取余数? 2的N次方。
N是什么? 数据的大小。对于int来说,通常N=32.
这样我们便有了 -x = 2的N次方 - x
定义 y为 对x每个bit位取反,显然有 x + y = 111...1 (N个1) = 2的N次方 -1
这样 -x = 2的N次方 - (2的N次方 -1 -y) = y + 1
对于 -5 我们可以在32位int下这样表示:
5的二进制是 00000000 00000000 00000000 00000101
每位取反是 11111111 11111111 11111111 11111010
加1后为: 11111111 11111111 11111111 11111011
对应16进制为: 0xFF FF FF FB
可以写个代码测试下:
int testMinusInt()
{
int x = -5;
printf("-5 = 0x%8x\n", x);
}
深入理解2的补码表示,一般需要了解离散数学中的闭包概念。
详细分析可以参考:
Computer Systems--A Programmer_s Perspective 第2章第2节
深入理解计算机系统(程序员的观点)
无符号数与有符号数的转换
疑问1: 相互之间转换有数据丢失吗?
写一个简单的测试代码
int testSign2Unsign()
{