我最近遇到了这个问题,以及@chux-Reinstate Monica给出的答案。
在他的回答中引述以下行:“这是实现定义的行为。分配的值可能是0或1或2 ...通常,通过将值加/减256直到在范围内,将值包装(“修改”)100 + 100 -256 --> -56
。 ”
码:
#include <stdio.h>
int main(void)
{
char a = 127;
a++;
printf("%d", a);
return 0;
}
输出: -128
在大多数C编译器中,char
type占用1 Byte
大小,严格来说,我假设其为16位系统,并且char
take 1 Byte
。
当a = 127
,其在计算机内部的二进制表示为时,将其0111 1111
增加1应得出该值
0111 1111 + 0000 0001 = 1000 0000
等于-0
(考虑到,带符号的数字表示,其中最左边的位表示0 = + and 1 = -
),那么为什么输出等于-128
?
是因为“ INTELGER PROMOTION RULE”吗?我的意思是,对于此表达式a + 1
,在操作之前将其a
转换为,然后其在内存中的二进制表示形式就等于输出并且对输出有意义。但是,后来我的这种假设与Chux-Reinstate-Monica的有关包装值的引用行发生冲突。int (2 Bytes)
+
1111 1111 1000 0000
-128
-128
1000 0000等于-0 ...
用二进制补码表示法,最左边的位表示,-(coefficient_bit * 2^N-1)
即您的情况,1000 0000
最左边的位表示-(1 * 2^8-1)
等于-128
,这就是为什么输出相同的原因。
您char
是一个8位有符号整数,在这种情况下1000 0000是-128。我们可以使用允许二进制常量的GNU扩展方便地测试1000 0000 。
char a = 0b10000000;
printf("%d\n", a); // -128
char
在此实现中,是一个带符号的8位整数。将1加到127会导致整数溢出到-128。
整数促销呢?在计算过程中会发生整数提升,但结果仍为char
。128无法容纳在我们签名的8位字符中,因此溢出到-128。
此示例演示了整数提升。
char a = 30, b = 40;
char c = (a * b);
printf("%d\n", c); // -80
char d = (a * b) / 10;
printf("%d\n", d); // 120
char c = (a * b);
是-80,但是char d = (a * b) / 10;
120。为什么?不应该是-8吗?答案是整数提升。数学运算是作为本机整数完成的,但结果仍必须填充为8位char。(30 * 40)
是1200,即0100 10110000。然后必须将其填充回8位带符号整数;那是1011 0000或-80。
对于其他计算,(30 * 40) / 10
== 1200 / 10
== 120非常合适。
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句