整型转换规则及注意事项

原理:

术语解释:整型提升属于类型提升的一部分。当操作符两边的类型的等级都小于整型(int)的范围时,默认情况下会把该类型提升为整型(int)进行计算。例如:对于char类型的计算,就会提升为对应的整型的计算。最终结果再转为char返回。


整型提升
当对小于int的整数类型执行操作时,将提升它们,如果该原始类型的所有值都可以用int类型来表示,那么该小类型将会转换为int的类型。否则的话,它将被转换为unsigned int。整数提升作为通常算术转换的一部分,用于某些参数表达式,常用的算术预算符号:一元运算符:(+,-,~,以及位操作符)。
下面的代码片段展示了该整型提升

char c1, c2;
c1 = c1 + c2;

整型提升的优点

整型提升要求每一个变量都提升为int类型(c1和c2)。两个变量的int值进行相加,然后结果被截断为char类型。整型提升避免了中间值的溢出。

signed char cresult, c1, c2, c3;
c1 = 100;
c2 = 3;
c3 = 4;
cresult = c1 * c2 / c3;

这个例子中,结果值为c1c2然后除以c3。假设signed char有8个位组成,c1c2的结果值(300)无法被表示,(8位最大值为256)。由于整型提升原则,他们的值就可以被保存,最终结果转为char类型,而不会丢失数据。


整型提升的缺点

位操作符一般是作用与整型类型上,当在比整型类型小的类型上使用位操作符时,如果不注意,可能会产生问题。


不合法操作
这个例子中,代码的本意是先对port取反,然后向右移动四位。如果这两个操作符都作用在8字节的unsigned integer上时,最终的结果将会是0x0a,但是,操作过程中,port首先会升级为signed int类型,然后可能会产生下面图表中的结果。

uint8_t port = 0x5a;
uint8_t result_8 = ( ~port ) >> 4;
表达式 类型 备注
port uint8_t 0x5a
~port int 0xffffffa5
~port >> 4 int 0x0ffffffa 值是否为负由实现定义
result_8 uint8_t 0xfa 截取8字节作为unsigned

合法的操作

在下面的例子中,port的位实现被转换为8个字节。下面的结果是希望的结果0x0a

uint8_t port = 0x5a;
uint8_t result_8 = (uint8_t) (~port) >> 4;

附录:不同类型转换规则
1、隐式转换
C在以下四种情况下会进行隐式转换:
1、算术运算式中,低类型能够转换为高类型。
2、赋值表达式中,右边表达式的值自动隐式转换为左边变量的类型,并赋值给他。
3、函数调用中参数传递时,系统隐式地将实参转换为形参的类型后,赋给形参。
4、函数有返回值时,系统将隐式地将返回表达式类型转换为返回值类型,赋值给调用函数。

2、算数运算的隐式转换
算数运算中,首先有如下类型转换规则:
1、字符必须先转换为整数(C语言规定字符类型数据和整型数据之间可以通用) 。
2、short型转换为int型(同属于整型) 。
3、float型数据在运算时一律转换为双精度(double),以提高运算精度。
类型转换规则

附录引用:http://blog.csdn.net/miaouu/article/details/5213042
翻译自:卡耐基梅隆大学 软件研究院

猜你喜欢

转载自blog.csdn.net/akakakak250/article/details/89954405