编程语言学习笔记:C语言 (2) 类型、运算符和表达式
const char msg[] = "info: ";?上面的等号后面的表达式称为初始化表达式。如果变量不是自动变量,则只能进行一次初始化操作,且初始化表达式必须为常量表达式,自动变量没有这些限制。默认情况下,外部变量和静态变量会被初始化为0,而自动变量为未定义值。运算符
运算符可以分为算术运算符、关系运算符、逻辑运算符、自增自减运算符、按位运算符赋值运算符等等。按操作数的数目还可以分为一元运算符、二元运算符和三元运算符。
算术运算符包括 + 、 - 、 * 、 / 、 % ,用于数值运算, % 不能用于浮点型。表达式的结果值为运算结果。
关系运算符包括 > 、 >= 、 < 、 <= ,相等性运算符包括 == 、 != ,用于关系比较。关系为真,结果为1;关系为假,结果为0。
逻辑运算符包括 && 、 || 、 ! ,用于逻辑运算。结果值和关系运算符同理。逻辑运算在确定结果的情况下,提前结束计算,如: ((a == 5) || (b = a)) && (c = a) ,当a = 5时,不对b赋值,c赋值为5;当a = 0时,b赋值为0,不对c赋值。
自增自减运算符包括 ++ 、 -- ,分别使操作数递增1和递减1。它们有作为前缀和后缀两种用法,用在变量前面时,先增减,表达式结果为增减后的值;用在变量后面时,表达式的结果为当前值,然后再增减。
按位运算符包括 & 、 | 、 ^ 、 ~ 、 << 、 >> ,它们对整型数进行按位运算。使用 >> 向右移位时,某些机器对有符号值用符号位填补(算术移位),有些则用0填补(逻辑移位)。对于左移和无符号值的右移,用0填补。
赋值运算符包括 = 、 += 、 -= 、 *= 、 /= 、 %= 、 &= 、 |= 、 ^= 、 <<= 、 >>= 。赋值语句具有值,它的类型为左操作数的类型,值为赋值操作后的值。
类型转换运算符的操作数类型不同时,存在一定的规则将它们转成相同的类型以进行运算。有两种类型转换方式,一是自动转换,表达式计算时会自动把“范围较小的”操作数类型转为“范围较大的”操作数类型,这种转换不丢失信息。这种转换的规则可以概括为“提升”: long double > double > float > unsigned long int > long int > unsigned int > int ,注意如果 long int 无法表示全部 unsigned int ,则两者同时提升为 unsigned long int 。另一种方式是强制类型转换, (type) expr ,函数的参数在函数被调用时也会进行自动强制转换。
运算符优先级下表总结了所有运算符的优先级和结合性。
运算符结合性() [] -> .从左至右! ~ ++ -- + - * & (type) sizeof从右至左* / %从左至右+ -从左至右<< >>从左至右< <= > >=从左至右== !=从左至右&从左至右^从左至右|从左至右&&从左至右||从左至右?:从右至左= += -= *= /= %= &= ^= |= <<= >>=从右至左,从左至右表达式通过运算符连接起来的变量和常量构成表达式,此外函数调用也属于表达式。事实上前面对运算符的介绍就已经包含了表达式。表达式的结果具有类型和值。
一个特别的表达式是条件表达式:
expr1 ? expr2 : expr3
它根据expr1的值是否为真来决定计算expr2或expr3。
?
原文