因此如果char
是,1 byte
那么它是 8 位,对吗?
所以 2 ^ 8 = 256 并且 0 到 255 是 char 的范围?
有符号整数和无符号整数如何工作?一个整数有 4 个字节,即 32 位,因此2 ^ 32
. 2 ^ 31 - 1 给出了有符号整数的正范围,那么第 32 位会发生什么情况?它是用来表示符号的吗?符号如何存储在内存中?
答案1
如果将数据类型定义为有符号类型,则存在不同类型的表示 - 主要是有符号幅度表示和二进制补码表示。
对于有符号的数值表示,是的,符号位被存储为最高有效位 (MSB,即最左边的位)。MSB 为 0 表示正数,而 1 表示负数。示例:
7 = 00000111
-7 = 10000111
这很简单,并且(相对)易于阅读,但是整数类型通常不是以这种方式保存是为了解决两个问题:
(1)零有两种表示法,+0 和 -0。这会导致比较数字变得很麻烦,因为它会产生一种特殊情况。
(2)计算起来并不容易(加减就这么简单)。两个正数相加、正数加负数、负数加正数和两个负数相加是四种不同的用例。例如 7+6 很简单
1 Carry bit
7 = 00000111
6 = 00000110 (Logic for add)
.. ........
13 = 00001101
而计算 7+(-6) 则意味着要使用减法逻辑
7 = 00000111
-6 = 10000110 (Logic for subtraction)
.. ........
1 = 00000001
因此,8 位数字的范围是 -(2^7)+1 到 2^7-1(即 -127 到 +127,其中有两个零 +0 和 -0)。有符号幅度表示主要用于保存浮点数。
这就引出了二进制补码表示法。正数的表示方式与有符号数值表示法相同。更改符号位需要两个步骤:(1) 反转所有位(将所有 0 更改为 1,将 1 更改为 0)(2)加一。
例如,为了得到 -6 的表示,我们采取以下步骤
6 = 00000110
Invert all bits: 11111001
Add one: 11111010
因此 -6 表示为11111010
。使用二进制补码表示法,您仍然可以从 MSB 读取符号;而零只有一种表示法:00000000
。
使用二进制补码表示的二进制数进行计算也很容易 - 加法就是加法。让我们再看看如何计算 7+(-6):
1111111 Carry bit
7 = 00000111
-6 = 11111010 (Logic for add)
.. ........
1 = 00000001
因此,8 位数的范围是 -(2^7) 到 2^7-1(即 -128 到 +127)。请注意,范围与有符号的数值表示不同。