1、/10/101 C程序设计教学做一体化教学做一体化教程耿祥义 张跃平 编著清华大学出版社第1页/10/102第第3章章 运算符与表示式运算符与表示式 第2页/10/1033 3.1.1 算术运算符与赋值运算符算术运算符与赋值运算符 3 3.1.1.1.1 关键知识点关键知识点1 1算术运算符算术运算符算术运算符:+,-,*,/,%(加、减、乘、除、求余)都是连接两个操作元二目运算符。*,/和%运算符级别(3级)高于+和-(4级)。算术运算符结合方向是从左向右。按着ANSI C标准,求余(%)运算符操作元只能是整型数据。比如,12%7结果是5,即12除以7余数是5,-12%7结果是-5。不过,1
2、2.0%7是非法,因为其中左操作元12.0不是整数。2 2算算术术表示式表示式 用算术运算符(包含括号)连接起来符合C语言语法规则式子称为算术表示式。比如,假设x和y是整型变量,那么-2*x+7*y30+3*(y+15)就是一个算术表示式,而3x+5y就不是算术表示式,正确写法应该是3*x+5*y。运算精度规则以下:假如表示式中有浮点数,则按双精度进行运算。即计算结果是double型数据(保留1516位有效数字)。假如表示式中最高精度是long型整数,则按long精度进行运算,即计算结果是long型整数。假如表示式中最高精度低于int型整数,则按int精度进行运算,即计算结果是int型整数。比
3、如,5/2结果是2,而不是2.5(5.0/2结果是2.5)。第3页/10/1043 3赋值赋值运算符运算符 赋值运算符:“=”是二目运算符,赋值运算符作用是将赋值符号“=”右侧值赋给左侧变量,即“=”左面操作元必须是变量,不能是常量或表示式。在数学中,x=x+1是错误(数学中把=看作等号),不过在编程语言中“=”是赋值意思,x=x+1就是正确。比如变量x值是20,那么经过赋值运算x=x+1后,变量x值就是21了。赋值运算符级别在全部运算符中是比较低(14级,倒数2级),比如,x=x+1相当于x=(x+1)。4 4赋值赋值表示式表示式用赋值符号(包含括号)连接起来符合C语法规则式子,称为赋值表示
4、式。比如,假设x和y都是int型变量,那么x=12和y=20都是赋值表示式。赋值表示式值就是“=”左面变量得到值。比如,假如a和b是两个int型变量,那么赋值表示式a=-10和b=12值分别是-10和12。需要注意是“=”结合次序是从右向左,所以表示式a=b=100相当于a=(b=100),即将赋值表示式b=100值赋给变量a,所以赋值表示式a=b=100值是100。第4页/10/1055 5复合复合赋值赋值运算符运算符 允许在赋值运算符前面添加一个算术运算符组合出一个复合赋值运算符,比如(假设x是一个变量):x+=100;等价于x=x+100;一样,x*=100+x;等价于x=x*(100+
5、x);尽管,x+=100和x=x+100效果相同,但x+=100效率较高,即编译器在生成机器码时,x+=100产生机器码少于x=x+100产生机器码。第5页/10/1066 6简单简单示例示例 例子1计算了代数表示式:值。Example3_1.c#includeint main()double a,b,c,d,result;a=10;b=34.56;c=20.88;d=200.98;result=9*a*(b+c)/d;printf(%f,result);return 0;第6页/10/107 3 3.1.1.2 2 能力目标能力目标计计算算算算术术表示式表示式值值使用使用赋值赋值运算符将算运
6、算符将算术术表示式表示式值赋给变值赋给变量。量。第7页8 3 3.1.1.3 3 任务驱动任务驱动-正整数上各个位上数字正整数上各个位上数字 1 1任务主要内容任务主要内容在 main函 数 中 申 明 一 个 用 于 存 放 正 整 数 无 符 号 short型 变 量positiveInteger,以及用于存放正整数个位、十位、百位、千位和万位上数字char型变量a1,a2,a3,a4和a5。使用scanf函数让用户从键盘为positiveInteger输入值。依次求出positiveInteger中个位、十位、百位、千位和万位上数字,并将这些数字依次赋值给变量a1,a2,a3,a4和a5
7、。输出a1,a2,a3,a4,a5以及表示式a1+a2+a3+a4+a5值。将 表 示 式 a5*10000+a4*1000+a3*100+a2*10+a1值 赋 值 给 变 量positiveInteger,并输出positiveInteger值。将 表 示 式 a1*10000+a2*1000+a3*100+a4*10+a5值 赋 值 给 变 量positiveInteger,并输出positiveInteger值。2.2.任任务务模模板板:按着任务关键内容完成模板:将【代码】替换为程序代码。模板程序模板程序运行效果如图3.1。第8页/10/1093.3.任务小结或知识扩展任务小结或知识扩
8、展 模板参考答案:模板参考答案:【代码1】:a1=positiveInteger%10;【代码2】:positiveInteger=positiveInteger/10;【代码3】:printf(a1+a2+a3+a4+a5=%dn,a1+a2+a3+a4+a5);【代码4】:printf(a1*a2*a3*a4*a5=%dn,a1*a2*a3*a4*a5);(1)求商与求余求商与求余 为了计算某个整数个位上数字,只需计算该整数和10求余结果。那么为了计算十位上数字,先计算该整数除以10商,然后再计算该商和10求余结果,依这类推就能够计算出整数各个位上数字。整型数据进行除法运算结果依然是整型数
9、据,比如123/10结果是12,即123除以10商是12。123%10结果是3(123除以10余数),即123等于12乘以10加3。第9页10(2)注意乘号注意乘号 初学C语言一定要习惯这里乘法运算符号,初学者经常把6乘以x错误写成:6x,正确写法是6*x。(3 3)输出输出%假如准备在printf函数“输出模式”中输出%,在编写代码时需要键入两个连续%,比如:printf(你好%);输出结果是:你好%。第10页11 3 3.1 1.4 4 实实践步践步骤骤 编写程序输出以下表示式值:A1/2+3+6*4/6。B3+6*(4/6)。C10%3*9。D12+10%(3*9)。(参考代码见附录参考
10、代码见附录A)第11页/10/10123.2 自增、自减运算符 第12页/10/1013 3 3.2 2.1 1 关关键键知知识识点点 自增、自减运算符:+,-是单目运算符,能够放在操作元之前,也能够放在操作元之后,+,-操作元必须是变量。1 1前前缀缀自增、自减运算自增、自减运算 当+(-)出现在变量前面时,称+(-)是+(-)前缀运算。当+(-)前缀运算出现在一个表示式中时,其运算作用是:先自增(自减)后使用。假如+是前缀运算,就首先使变量值增加1(即执行x=x+1)、假如-是前缀运算,就首先使变量值降低1(即执行x=x-1),然后变量x值再参加该表示式计算。比如,假设申明了两个int型变
11、量x和n:intx,n=10;假如执行:x=+n+12;那么+前缀运算出现在算术表示式“n+12”中,所以变量n值首先自增1变成11,然后再参加表示式计算。x=+n+12;作用等价于以下:n=n+1;x=n+12;第13页/10/10142 2后后缀缀自增、自减运算自增、自减运算 当+或-出现在变量后面时,称+或-后缀运算。当后缀运算出现在一个表示式中时,其运算作用是:让变量x值先参加该表示式计算,在表示式值被计算完成之后,假如是+后缀运算,就使变量值增加1(即执行x=x+1),假如是-后缀运算,就使变量值降低1(即执行x=x-1),即所谓先使用后自增(自减)。3 3简单简单示例示例例子例子2
12、使用了自增、自减运算符,请注意程序注释输出结果。example3_2.c#include int main()int a=16,b=10,m,n;m=a+-b;n=+a-b;b-;printf(m=%d,n=%dn,m,n);/输出结果是:m=6,n=8 printf(a=%d,b=%dn,a,b);/输出结果是:a=18,b=9 return 0;第14页/10/1015 3 3.2 2.2 2 能力目标能力目标能能简单简单明了地使用自增、自减运算符。明了地使用自增、自减运算符。第15页16 3 3.2 2.3 3 任务驱动任务驱动编写程序,模拟冰块溶解于水。冰块放入盛有水容器中后,容器中物
13、质重量等于冰与水重量之和,但每隔1分钟后,冰重量降低一个单位,水重量增加一个单位。冰块放入盛有水容器3分种后,输出容器所盛物质重量,以及容器中冰块重量和水重量。1 1任务主要内容任务主要内容 在main函数中申明两个无符号short型变量:water和ice,其值分别表示水和冰块重量。在main函数中申明一个无符号short型变量weight,用于存放水和冰块重量之和。模拟1分钟后容器中冰块和水重量之和以及冰块重量和水重量,即计算water与ice和,并把结果存放到weight中,而且要确保计算结束后water值自动增加1、ice值自动降低1。继续模拟2分钟后、3分中后容器中冰块和水重量之和以
14、及冰块重量和水重量。2.2.任任务务模模板板:按着任务关键内容完成模板:将【代码】替换为程序代码。模板程序模板程序运行效果如图3.2。第16页/10/10173.3.任务小结或知识扩展任务小结或知识扩展 模板参考答案:模板参考答案:【代码1】:weight=water+ice-;【代码2】:weight=water+ice-;【代码3】:weight=water+ice-;防止在表示式中出防止在表示式中出现过现过多自增、自减运算符多自增、自减运算符 尽管自增、自减运算符有较高效率,但使用+和-运算符时,尽可能防止过于“聪明”地使用它们,不然不利于代码阅读。当前软件不但重视代码效率,也非常重视代
15、码维护。比如,假设申明了变量i和y:inti=2,y;假如执行:y=i+*i;那么,y值是4,i值是3(i先参加计算再自增)。显然,阅读:y=i+*i;难度大于:y=i*i;i=i+1;尽管y=i+*i;效率更高,不过,对于当前处理器,i+*i带来效率几乎能够忽略。编写C程序尽可能防止在表示式中出现过多自增、自减运算符,以简练、可读性强为最正确。第17页18 3 3.2 2.4 4 实实践步践步骤骤 编写程序,要求申明变量i和y:int i=2,y;执行:y=i+*i;输出y和i值。(参考代码见附录参考代码见附录A)第18页/10/10193 3.3 3关系与逻辑运算符 3 3.3 3.1.1
16、 关键知识点关键知识点1 1关系关系运算符运算符当程序需要比较两个数值大小关系时,就需要使用关系运算符。关系运算符意义以下:l=相等l!=不等l大于l=大于或等于l=小于或等于关系运算符是使用频率非常高一个运算符,基本信息见表3.1。第19页/10/10202 2关系表示式关系表示式 用关系运算符(包含括号)连接起来符合C语法规则式子称为关系表示式。比如,假设x和y都是int型变量,那么x=9都是关系表示式。关系表示式值要么是1、要么是0,当关系表示式表示关系成立时值为1,不然为0。比如,关系表示式:1 2 3值是1,因为关系运算符结合次序是从左到右,所以1 2 3计算次序相当于:(1 2)3
17、。关系表示式:-3 -2 -1值是0(注意不是1),因为-3 -2 -1计算次序相当于:(-3 -2)-2结果是0,因为“=”级别低于“”,-1=-1 -2计算次序相当于:-1=(-1 -2),而不是(-1=-1)-2。不要将相等关系运算符:“=”和赋值运算符:“=”相混同,比如,假设x是一个int型变量,其值是-10,那么关系表示式x=1值是0,而赋值表示式x=1值是1。第20页/10/10213 3逻辑逻辑运算符运算符 C语言分别使用“&”、“|”和“!”表示逻辑代数中“与”、“或”和“非”三种逻辑运算。C语言用非0数表示“真”,用0表示“假”。“&”、“|”是双目运算符,“!”是单目运算
18、符。逻辑运算符基本信息见表3.2。第21页/10/10224 4逻辑逻辑表示式表示式 当两个操作元都是非零数时,&运算结果是1,不然是0。当两个操作元都是零时,|运算结果是0,不然是1。当操作元是非零时,!运算结果是0,不然是1。比如:-5&3结果是1。5 4&9 4)&(9 3&1 3)&(1 12|19 12)|(19 8))。10 9|3 2结果是0(相当于(10 9)|(3 2))。!8结果是0。!8结果是1(!结合次序是从右向左)。逻辑运算符“&”和“|”也称作短路逻辑运算符。对于op1&op2,当op1值是“假”时(值是0),“&”运算符在进行运算时不再去计算op2值,直接就得出o
19、p1&op2结果是0(假);当op1值是“真”时,就需要继续计算op2值,才能最终计算出op1&op2结果。对于op1|op2,当op1值是“真”时,“|”运算符在进行运算时不再去计算op2值,直接就得出op1|op2结果是1(真);当op1值是“假”时,就需要继续计算op2值,才能最终计算出op1|op2结果。第22页/10/10235.5.简单简单示例示例例子3计算了几个关系和逻辑表示式值,请注意程序注释输出结果。example3_3.c#include int main()int a=1,b=5,c=5,x=0;int rusult;rusult=a+bc&b=c;printf(resu
20、lt=%dn,rusult);/result=1 rusult=-a&b+c|b-c;printf(result=%dn,rusult);/result=0 rusult=(x=10)&(x=100);printf(result=%d,x=%dn,rusult,x);/result=1,x=100 rusult=(x=-10)|(x=0);printf(result=%d,x=%dn,rusult,x);/:result=1,x=-10 return 0;第23页/10/1024 3 3.3 3.2 2 能力目标能力目标能使用关系运算符表示数据之能使用关系运算符表示数据之间间大小关系。大小关系
21、。能使用能使用逻辑逻辑运算符表示数据之运算符表示数据之间逻辑间逻辑关系。关系。第24页25 3 3.3 3.3 3 任务驱动任务驱动1 1任务主要内容任务主要内容 对于整型变量x,用关系和逻辑表示式表示下述内容:x是负数。x在-10和-20之间。x大于100或者x小于10。x20而且是3倍数。x能被3或5整除。x能被5整除但不能被3整除。输入x值,程序输出上述表示式值。2.2.任任务务模模板板:按着任务关键内容完成模板:将【代码】替换为程序代码。模板程序模板程序运行效果如图3.3。第25页/10/10263.3.任务小结或知识扩展任务小结或知识扩展 模板参考答案:模板参考答案:【代码1】:pr
22、intf(表示式x=-20&x=-20&x20)&(x%3=0)值:%dn,(x20)&(x%3=0);【代码3】:printf(表示式(x%5=0)&!(x%3=0)值:%dn,(x%5=0)&!(x%3=0);(1)(1)运算符级别和结合性运算符级别和结合性 对于32+22+24-102+22)+(2-1)结果是1)。(2)(2)防止逻辑错误防止逻辑错误 需要注意是,当我们要表示一个变量x值是否在某个范围时候,比如小于-1且大于-5时,不要使用表示式:-5x-1,因为,当x值是-3时候,表示式:-5x-1值是0(假),应该使用表示式:-5x&x-5&-1x,显然当x值是-3时,这两个表示式
23、值都是1(真)。(3)(3)增强代码可读性增强代码可读性在表示式中尽可能防止出现难以阅读计算次序,提倡使用小括号到达您计算次序目标,方便增强代码可读性。比如,对于3+710-1,尽管加减运算级别高于关系运算符,但(3+7)(10-1)可读性更加好。第26页27 3 3.3 3.4 4 实实践步践步骤骤 实践实践1 1 (参考代码见附录参考代码见附录A A)有如图3.4所表示意电路图。用整型变量表示一个开关状态,当整型变量值是非0时表示开关是“开”,当整型变量值是0时表示开关是“关”。程序使用scanf语句输入整型变量值,即输入各个开关状态。程序用逻辑表示式表示电路通,即逻辑表示式值是1表示电路
24、通。实践实践2 2:编写程序,在main函数中申明3个int型变量x,y,z,并使用scanf函数为这3个int型变量输入值,然后程序计算并输出以下表示式值:Ax+y&z-y。Bxyyz。Cx-x&y-y|z-z。D(x-x)&y-y。第27页/10/10283 3.4 4类型转换运算符 3 3.4 4.1.1 关键知识点关键知识点1 1类类型型转换转换运算符运算符 类型转换运算符格式是:(类型)类型转换运算符是单目运算符,操作元是数值型数据,比如:(float)12结果是12.0(保留67位有效数字)。(int)45.98结果是45。(double)(int)68.89结果是68.0(保留1
25、516位有效数字)。#include int main()int a=11;double b=12.98,c,d;printf(%f,%dn,(float)a,(int)b);/输出:11.000000,12 c=(int)b+0.5;printf(%fn,c);/输出:12.500000 d=(int)(b+0.5);printf(%fn,d);/输出:13.000000 return 0;3简单简单示例示例例例子子4中使用了类型转换运算符,请注意程序注释输出结果。2注意事注意事项项需要注意是,类型转换运算 符 级 别 是 2级,所 以,(int)15.9+0.1结 果 是 15.1,即相当
26、于:(int)15.9)+0.1,而(int)(15.9+0.1)结果才是16。第28页/10/1029 3 3.4 4.2 2 能力目标能力目标 使用类型转换运算符将一个基本类型数据转换为另一个基本类型数据。第29页30 3 3.4 4.3 3 任务驱动任务驱动对浮点数进行四舍五入1 1任务主要内容任务主要内容 输出浮点数对第1位小数实施四舍五入结果。输出浮点数对第2位小数实施四舍五入结果。输出浮点数对第3位小数实施四舍五入结果。2.2.任任务务模模板板:按着任务关键内容完成模板:将【代码】替换为程序代码。模板程序模板程序运行效果如图3.5。第30页/10/10313.3.任务小结或知识扩展
27、任务小结或知识扩展 模板参考答案:模板参考答案:【代码1】:result=(int)(number+0.5);【代码2】:result=(int)(number*10+0.5);【代码3】:(int)(number*100+0.5);(1)(1)关于四舍五入关于四舍五入 为了实现四舍五入,只需要将浮点数据加上0.5,再将结果进行int型转换运算即可。但需要注意是,类型转换运算符级别是2级,所以,(int)15.9+0.5结 果 是 15.5,即 相 当 于:(int)15.9)+0.5,而(int)(15.9+0.5)结果才是16。(2)(2)关于优先级别关于优先级别 C表示式就是用运算符连接
28、起来符合语法规则式子。运算符优先级决定了表示式中运算执行先后次序。比如,xy&!z相当于(xy)&(!z)。没有必要去记忆运算符优先级别,在编写程序时尽可能使用括号()运算符号(级别是最高级:一级)来实现想要运算次序,以免产生难以阅读或含糊不清计算次序。运算符结合性决定了并列相同级别运算符先后次序,比如,加减结合性是从左到右,8-5+3相当于(8-5)+3;逻辑非运算符!结合性是右到左,!x 相当于!(!x)。第31页32 3 3.4 4.4 4 实实践步践步骤骤 编写程序,模拟使用不一样交通工具托运行李费用。详细要求以下:用火车在托运行李时以千克为单位计算费用(12元/kg),忽略重量中小数
29、部分,即忽略不足1千克之部分。用汽车在托运行李时以千克为单位计算费用(22元/kg),将重量中小数部分百克部分进行四舍五入,即将不足1千克之部分进行四舍五入。用飞机在托运行李时以千克为单位计算费用(132元/kg),将重量中小数部分十克部分进行四舍五入,即将不足1百克之部分进行四舍五入。用double型变量weight存放用户行李重量,用charge存放托运费用,程序使用scanf语句输入weight值,该值被认为是以千克为单位行李之重量,然后程序将分别计算出用火车、汽车和飞机托运行李费用。(参考代码见附录A)第32页/10/10333 3.5 5 位运算符 3 3.5 5.1.1 关键知识点
30、关键知识点整型数据在内存中以二进制形式表示,比如一个int型变量在内存中占4个字节共32位,int型数据7二进制表示是:00000000 00000000 00000000 00000111左面最高位是符号位,最高位是0表示正数,是1表示负数。负数采取补码表示,比如-8补码表示是:111111111 111111111 1111111 11111000对于一个或多个字节组成数据,按从左向右次序,称左面第一位是最高位,右面第一位是最低位。为了表述上方便,从低位到高位依次编号。在许多文件中,将最低位编号为0,即从右向左,依次称作位0,位1,位2,位3。本书在叙述上也恪守这个习惯,比如,说某数据位0
31、是1,就是指该数据最低位值是1,说某数据位1是0,是指从右向左数,该数据第二位值是0。当然,有时候为了简化叙述,也会按从左向右(高到低)来叙述相关内容,比如,“数据从高至低第二位值是1”也是很清楚叙述。第33页 1 1“按位与按位与”运算运算 按位与运算符&是双目运算符,对两个整型数据a,b按位进行&运算,运算结果是一个整型数据c。运算法则是:假如a,b两个数据对应位都是1,则c该位是1,不然是0。假如b精度高于a,那么结果c精度和b相同。比如:a:00000000000000000000000000000111&b:10000001101001011111001110101011c:0000
32、00000000000000000000000000112“按位或按位或”运算运算 按位或运算符|是双目运算符,对两个整型数据a,b按位进行“|”运算,运算结果是一个整型数据c。运算法则是:假如a,b两个数据对应位都是0,则c该位是0,不然是1。假如b精度高于a,那么结果c精度和b相同。3“按位非按位非”运算运算“按位非”运算符“”是单目运算符,对一个整型数据a按位进行“”运算,运算结果是一个整型数据c。运算法则是:假如a对应位是0,则c该位是1,不然是0。/10/1034第34页4 4“按位异或按位异或”运算运算 “按位异或”运算符“”是双目运算符,对两个整型数据a,b按位进行“”运算,运算
33、结果是一个整型数据c。运算法则是:假如a,b两个数据对应位相同,则c该位是0,不然是1。假如b精度高于a,那么结果c精度和b相同。由异或运算法则可知:aa=0,a0=a。所以,假如ab结果是c,那么cb结果就是a,也就是说,“”逆运算依然是“”,即abb等于a。5左移位运算符左移位运算符左移位运算符号为。是双目运算符。左移位运算符左侧操作元称为被移位数,右侧操作数称为移位量,操作数必须是整型类型数据。比如:intx=7;x内存表示是:00000000 00000000 00000000 00000111 00000000 00000000 00000000 00000111能够对整x进行左移位
34、运算。比如(移位量是1),x1得到结果是:00000000 00000000 00000000 00001110 00000000 00000000 00000000 00001110设a是一个被移位整型数据,n是位移量。a,是双目运算符。假设a是一个被移位整型数据,n是位移量。an运算结果是经过将a全部位都右移n位,每右移一位,右边低阶位被移出丢弃,并用0或1填充左边高位。a是正数时用0填充,是负数时用1填充。/10/10367简单简单示例示例例例子子5中中利用“异或”运算性质,对几个字符进行加密并输出密文,然后再解密。第36页/10/1037 3 3.5 5.2 2 能力目标能力目标 能使
35、用位运算处理整型数据能使用位运算处理整型数据。第37页38 3 3.5 5.3 3 任务驱动任务驱动位清零。对于数据a:01100111想将数据a位1(右向左数第二位,加下划线数字)以以外外位清零,那么就能够让a与掩码MASK:00000010做“&”运算即可,即执行:a=a&MASK1 1任务主要内容任务主要内容 将63,3557位2以外位清零。然后再输出清零后数据值。取掩码MASK位2是 1,其 余 位 都 是 0(掩 码 MASK是 4)(对 于 整 数 n,假 如 表 示 式n&MASK=MASK为“真”,那么整数n位2是1)。2.2.任务模板:任务模板:仔细阅读模板代模板代码码,了解掩码MASK作用。3.3.任务小结或知识扩展任务小结或知识扩展 当需要将一个数据a一些位清零时,只要取掩码MASK满足:对应清零位是0,其余位是1即可。然后进行以下操作即可:a=a&MASK;第38页39 3 3.5 5.4 4 实实践步践步骤骤 将63,3557位2和位0以外位清零。然后再输出清零后数据值。(参考代码见附录(参考代码见附录A A)第39页/10/1040小结小结l 掌握各种运算符格式和运算法则。表示式就是用运算符连接起来符合语法规则式子。运算符优先级决定了表示式中运算执行先后次序。比如,xy&!z相当于(x12值都是不可预测。第40页