表达式由运算对象和运算符组成。普通的算式和函数调用都被叫做表达式
从c语言的角度看,表达式的主要目的是得出一个值。c语言通过优先级和结合律(从左到右或从右到左)决定运算顺序。
优先级排序:符号运算符==递增和递减运算符>sizeof运算符>乘除、求模运算符>加减运算符>赋值运算符。
运算符一元与二元的差别在于涉及几个运算对象。
=运算符在c语言中是赋值的意思。=的左边叫做左值,右边叫做右值。
右值又被称为表达式的值。是将要赋给左值的东西,计算完毕后就被丢弃。
通常来说,左值具有两个特点:
1.可指代一个对象,引用内存中的地址
2.可用在赋值运算符的左侧(可以修改)
然而,被const限定符限定的变量是个怪胎,它满足1,不满足2。
所以,把我们现在把满足1、2的叫做可修改的左值。
表达式还有副作用,这个副作用就是除了计算出值以外的其他作用。很多时候我们使用表达式就是看中它的副作用。
例如:
printf("我是你爹"); //副作用:打印 我是你爹
a=3+4; //副作用:把7赋给a
对c来说,它们的主要目的如前文所说,都是求值。
printf返回的值是待显示字符的个数,a=3+4返回的值是7(赋值符“=”不改变返回值)
++的副作用是使原有的值+1,它有前缀表示和后缀表示,前缀和后缀决定+1的时机。
前缀,即++放在变量前面,先+1,然后再其他;
后缀,即++放在变量后面,正好相反,先其他,再+1。
那么什么其他才算结束呢?当程序运行到序列点的时候一定结束。
序列点保证所有的副作用在进入下一步前发生,通常在
1.分号
2.任何一个完整表达式(指它不是更大表达式的子表达式)的结束
在副作用应该结束的时候没有出现序列点,会导致副作用结束的不确定性,使同一个程序的结果不确定。
int main(void)
{
int num=2;
printf("%d %d",num,num*num++);
return 0;
}
比如这段代码,printf()里面的两个参数先用哪个是不确定的,其中第二个参数中最右边的num使用后先+1还是先与左边的num相乘也是不确定的。
运算中的数据类型转换
在进行混合运算时,数据类型常常会进行升级,即变成一个更高级别的数据类型,比如short和char在进行计算时,常常被当做int;float在运算时被转换成double
升级往往不会出问题,而降级很有可能出问题,因为较低级别的可能放不下整个数字。
语句
语句是C程序的基本构建块,一条语句相当于一条完整的计算机指令。
在c中,大部分语句都以 ; 结尾
一条或多条语句被花括号给框起来,形成一个“块”,也被称为复合语句。整个复合语句被视为一条语句。
带参数的函数
函数在程序开头要写个函数原型。
函数原型括号里的声明创建了被称为形式参数(parameter)的变量,它是函数私有的,可以其他地方取的变量名一致。形式参数点明了需要参数的数据类型。
函数实际调用传递的值被称作是实际参数(argument)。如果给一个不符合形参要求的实参,数据会发生相应的转化。