什么是整型提升?举个例子先
//输出什么?
#include <stdio.h>
int main()
{
char a= -1;
unsigned char b=-1;
printf("a=%d,b=%d\n",a,b);
printf("a=%u,b=%u",a,b);
return 0;
}
运行结果如图:
结果有没有符合你的预期呢?
如果有,说明你掌握了,这篇文章希望能得到你的指正或建议,谢谢
如果没有,下面我会解释原因和解题步骤
1、基础知识
* 整数是以补码形式存储在内存当中的,长度为四个字节,一个字节八个比特位。
* 不同的是,正数原码补码反码相同,而负数不是
* 负数的补码是在原码的基础上除符号位按位取反再加一得到的
例如 -5
原码 10000000 00000000 00000000 00000101
反码 11111111 11111111 11111111 11111010 //除了符号位其他位按位取反
补码 11111111 11111111 11111111 11111011//补码加一
例题讲解
-1在内存中是 11111111 11111111 11111111 11111111
变量a
- 把-1放入char型变量中时,由于char型的变量大小为一个字节,就会以缺省的形式放入变量a中,即变量a在内存中储存的是 1111 1111
- 当a要输出时,并不能以一个字节去输出,那么就要进行整型提升
- 由于变量a是char型,因此,他会在二进制序列的前24位补1 所以得到的数就是11111111 11111111 11111111 11111111 再以整形输出就是 -1。 注意:输出是按原码输出,这里会把补码转换成原码。
- 但是当以无符号整型输出时,由于就不存在符号位 因此就会原样输出 11111111 11111111 11111111 11111111 用十进制表示就是例子中显示的值。
变量b
- 把-1放入char型变量中时,由于char型的变量大小为一个字节,就会以缺省的形式放入变量b中,即变量b在内存中储存的是 1111 1111
- 当b要输出时,并不能以一个字节去输出,那么就要进行整型提升
- 由于变量b是unsigned char型,因此他会在而仅是序列前24位补0,所以得到的数就是00000000 00000000 00000000 11111111 再以整形输出就是255 注意:因为正数原码反码补码可以视为相同的,所以这里直接原样输出,不用补码转原码
- 当以无符号整形输出时,也是255
总结遇到此类问题的方法步骤
1、截断
顾名思义就是截掉一部分并把其断掉,这里截断的对象是整数的二进制序列。
当整数存入小于比他字节大小小的类型定义的变量中时,就会发生截断,例如,当存入char类型变量中会存储低八位的二进制数,当存入short类型变量中会存储低16位的二进制数,将其其余部分抛弃。
所以遇到此类问题时,我们第一步要分析的是这个变量中真正存储的是什么
2、提升
刚才我们谈到了截断,截断是把一个数的部分低位保留,但是当我们要使用这些数的时候,我们就要把他补全再使用,怎么补呢?看类型!如果这个变量类型是有符号的,则如果此时最高二进制位为1就补1,是0补0,即称之为整型提升。
第二步,提升的关键是看变量类型,决定了提升方法
3、表达式的注意
当要用%d整形输出时,我们需要对提升后的结果进行判断,如果它的符号位是1,就会将其减一取反然后表达,如果是0就直接表达。当要用%u输出时,就不会对符号位进行判断,直接原样表达。
第三步,看清输出类型,不同的输出类型对变量是不一样的表达。
同学,如果你看懂了 我会在下面给一些这方面的题目,你可以自己尝试一番。
unsigned int i;
for(i = 9; i >= 0; i--)
{
printf("%u\n",i);
}
#include <stdio.h>
unsigned char i = 0;
int main()
{
for(i = 0;i<=255;i++)
{
printf("hello world\n");
}
return 0;
}
如果你能看完这篇博客,诚信希望你给出建议~