5.8.5 赋值处理的自动类型转换
在日常的赋值应用中,如果赋值运算符两边的数据类型不相同,那么系统将自动进行类型转换,即把赋值运算符右边的类型换成左边的类型。具体规则如下所示。
(1)实型赋值为整型:要舍去小数部分。
(2)整型赋值为实型:数值不变,但以浮点形式存放,即增加小数部分(小数部分的值为0)。
(3)字符型赋值为整型:因为字符型占用一个字节,而整型占用两个字节,所以要将字符的ASCII码放到整型变量的低8位中,高8位为零。整型赋值为字符型时,只把低8位赋值为字符量。具体来说有如下两种情况。
❑ 如果所用系统将字符处理为无符号变量或对无符号字符型变量赋值,则将字符的8位放到整型变量的低8位,高8位补零。
❑ 如果所用系统(如Turbo C)将字符处理为带符号的变量(即signed char),若字符的最高位为0,则整型变量的高8位补零;若字符的最高位为1,则高8位全补1。这称为“符号扩展”,这样操作的目的是使数值保持不变,如变量C(字符’\376')以整数形式输出为-2,所以i的值也是-2。
(4)双精度型数据赋值给单精度型数据:只截取其前面的7位有效数字,存放在单精度变量的存储单元中,但是数值不能溢出。例如下面代码将会产生溢出错误。
float f; double d=123.456111e100; f=d;
(5)当将单精度型数据赋值给双精度型数据:数值不变,有效位扩展到16位。
(6)将一个整型、长型、短型数据赋值给一个字符型变量:只将其低8位原封不动地送到字符型变量中(即截断)。例如下面的赋值:
int i=123; char c='a'; c=i;
(7)将带符号的整型数据(int型)赋给长型变量:这要进行符号扩展,将整型数的16位送到长型数的低16位中,如果整型数据为正值(符号位为0),则长型变量的高16位补0;如果整型变量为负值(符号位为1),则长型变量的高16位补1,以保持数值不变。
(8)将无符号整型数据赋给长整型变量:不存在符号扩展问题,只需将高位补0即可。
(9)将一个无符号类型数据赋值给一个字节数相同的整型变量:例如unsigned int=>int, unsigned long=>long,unsigned short=>short;将无符号型变量的内容直接送到有符号型变量中,但如果数据值超过了相应的整型范围,则会出现数据错误。例如下面的赋值代码。
unsigned int a=111111; int b; b=a;
(10)将有符号型数据赋值给长度相同的无符号型变量:也是直接赋值,原有的符号位也作为数值一起传送。例如下面的代码会将有符号数据传送给无符号变量。
int main(void){ unsigned a; int b=-1; a=b; printf("%u", a); }
因为“%u”是输出无符号数时所用的格式符,所以运行结果为a等于77777。但如果是下面的赋值,因为无符号整型数的范围是0~65535,整型数据-1超出了整型数的范围,所以结果发生错误。
int main(void){ unsigned int a; int b=-1; a=b; printf("%u", a); }