我得到的东西是:
C中的signed char
以8位表示:00000000
0000 0000
=> 0 0000 0001
=> 1 0111 1111
=> 127 所以我认为第8位是符号位。 所以我想:
1000 0000
=> 0 1000 0001
=> -1 但不!
试试这个:
int main(int argc, const char *argv[])
{
int i;
for (i = 0; i < 256; i++) {
printf("%3d = %d\n", i, (signed char)i);
}
return 0;
}
你得到:gcc -o tt tt.c ; ./tt | more
126 = 126
127 = 127
128 = -128
129 = -127
130 = -126
254 = -2
255 = -1
怎么来的?
答案 0 :(得分:7)
这称为有符号整数的2的补码表示,用于所有整数类型。
这个想法是这样的:CPU中的加法器只是在溢出发生并且环绕时忽略,所以你实际上在计算模数环上。因此,如果从零中减去1,则得到
00000000 = 0
-00000001 = 1
--------------
11111111 = -1
等等。
这样,您的计算机可以在计算时忽略符号。对于乘法,这甚至是正确的,如本例中3和-2的乘法(为简洁起见,4位算术):
0011 * 1110
-----------
0000
0011
0011
0011
-----------
101010
truncated to 4 bits: 1010
1010
是0110
的否定值,为6,因此结果应为-6。
只需要很少的点需要考虑签名,比如比较,划分和转换为更大的整数类型。比较相对简单,演员表的工作方式如下:
00000001 -> 0000000000000001
10000000 -> 0000000010000000 (unsigned extension 128 -> 128)
10000000 -> 1111111110000000 (sign extension, the sign bit is copied into all new bits, preserving the value of negative numbers -128 -> -128)
答案 1 :(得分:5)
这是因为8位2的补码编码。符号字符范围是-128到127.
EDIT1:对@Grijesh评论的回应
-128和+128具有相同的表示形式:10000000。因此,为了避免混淆并制定规则All bit-patterns with 1 in higher-order bit represent negative numbers
,决定将其视为-128,其范围为-128到127而不是-127 .. + 128。
答案 2 :(得分:4)
在二进制补码中,最左边的位是负数,其他位是正数,所以
1000 0000
=&GT; -128
和
1000 0001
=&GT; -128 + 1 = -127
因此最大数字是0111 1111(127),最小数字是1000 0000(-128)
答案 3 :(得分:2)
您可以将signed datatypes
视为时钟。它会在12小时后达到12点钟。
Char
范围为-128
到+127
。因此,当您根据我的时钟规则点击127
时,下次点击将为-128
。
我建议你做一些二进制计算。
答案 4 :(得分:1)
在c char中,唯一的1字节内存分配意味着总共8位。 这是因为8位2的补码编码。符号字符范围是-128到127 因为你用过。
printf("%3d = %d\n", i, (signed char)i);