目录
前言
我们前边详细的讲解了数据在内存中的存储,今天我们就是在数据存储的基础上来讲解数据的隐式类型转换。
整型提升
C 的整型算术运算总是至少以缺省整型类型的精度来进行的。为了获得这个精度,表达式中的字符和短整型操作数在使用之前被转换为普通整型,这种转换称为 整型 提升 。如在我们进行表达式计算时,操作数为字节较小的整型时,如char,short类型时,应该先提升为int型,如果int类型不足应该提升为unsigned int 类型,然后再执行表达式的计算。
整型提升的意义
表达式的整型运算要在 CPU 的相应运算器件内执行, CPU 内整型运算器 (ALU) 的操作数的字节长度一般就是int 的字节长度,同时也是 CPU 的通用寄存器的长度。因此,即使两个 char 类型的相加,在 CPU 执行时实际上也要先转换为 CPU 内整型操作数的标准长度。通用 CPU (general-purpose CPU)是难以直接实现两个 8 比特字节直接相加运算(虽然机器指令中可能有这种字节相加指令)。所以,表达式中各种长度可能小于 int长度的整型值,都必须先转换为int或unsigned int ,然后才能送入 CPU 去执行运算。
通俗来说,两个char类型相加,cpu会将char类型提升为整型,本来是8个比特直接相加,但是在32位环境下cpu也会转化为32个比特位的int型进行计算。
char a,b,c;
...
a = b + c;
这种情况就是将a,b提升为整型再计算。
在计算过程中,char类型或者short类型,先提升为整型计算,得到的结果再截断成短字节数据类型储存。
如何进行整体提升呢?
整形提升是按照变量的数据类型的符号位来提升的
正数的整型提升
// 正数的整形提升char c2 = 1 ;原码:0000 0000 0000 0000 0000 0000 0000 0001正数的原码反码补码相同补码: 0000 0000 0000 0000 0000 0000 0000 0001变量 c2 的二进制位 ( 补码 ) 中只有 8 个比特位:0000 0001因为 char 为有符号的 char所以整形提升的时候,高位补充符号位,即为 0提升之后的结果是:0000 0000 0000 0000 0000 0000 0000 0001
负数的整型提升
// 负数的整形提升char c1 = - 1 ;原码:1000 0000 0000 0000 0000 0000 0000 0001反码:1111 1111 1111 1111 1111 1111 1111 1110补码:1111 1111 1111 1111 1111 1111 1111 1111变量 c1 的二进制位 ( 补码 ) 中只有 8 个比特位:1111111因为 char 为有符号的 char所以整形提升的时候,高位补充符号位,即为 1提升之后的结果是:11111111111111111111111111111111
无符号整形提升,高位补0
//无符号数 的整形提升char c2 = 1 ;原码:0000 0000 0000 0000 0000 0000 0000 0001正数的原码反码补码相同补码: 0000 0000 0000 0000 0000 0000 0000 0001变量 c2 的二进制位 ( 补码 ) 中只有 8 个比特位:0000 0001因为 char 为有符号的 char所以整形提升的时候,高位补充 0提升之后的结果是:0000 0000 0000 0000 0000 0000 0000 0001
整型提升的实例
//实例1
int main()
{
char a = 0xb6;
short b = 0xb600;
int c = 0xb6000000;
if(a==0xb6)
printf("a");
if(b==0xb600)
printf("b");
if(c==0xb6000000)
printf("c");
return 0;
}
我们来一个一个分析
char a =0xb6,转化为二进制数为1011 0110,由于在if判断时需要进行表达式计算,只要进行判断就会进行整型提升,由于a和b都是字节数小于int型,所以要提升为int型,而c本来就是int型不用进行整型提升,所以打印出的结果只有c。
//实例2
int main()
{
char c = 1;
printf("%u\n", sizeof(c));
printf("%u\n", sizeof(+c));
printf("%u\n", sizeof(-c));
return 0;
}
我们先来分析,三个表达式,sizeof操作符中,后两个通过+和-操作符进行了计算,所以我们判断,后两个会进行整型提升,在32位环境下,应该是四个字节,第一个是一个字节,我们来运行检验一下。
总结
今天讲解了内存存储中的整型提升,希望以后大家在表达式处理中注意到整型提升这个知识点。