资源描述
第二章数据类型、运算符与表达式,授课:东南大学郑雪清E_mail:snow6789,VC+语言程序设计,第2章数据类型、运算符与表达式,学习内容和基本操作:VC的数据类型基本运算符表达式语句、空语句及自增、自减运算符考试大纲要求:常量表示法;各种类型的变量说明及其初始化;运算符和表达式。,重点与难点:数据类型运算符表达式时间和安排:,2.1VC+的数据类型一个程序应包括两个方面的内容:数据的描述。操作步骤,即动作的描述。数据是操作的对象,操作结果会改变数据的状况。程序设计必须认真考虑和设计数据结构和操作步骤(即算法)。著名计算机科学家沃思(NiklklausWirth)提出一个公式:数据结构十算法=程序,程序算法十数据结构十程序设计方法十语言工具和环境程序中的四个方面是程序设计人员所应具备的知识。在本书中不可能全面介绍这些内容,它们都属于有关的专门课程范畴。本书主要介绍VC+语言本身。VC+语言提供的数据结构是以数据类型形式出现的,VC+的数据类型如下:,本节介绍组成C程序的基本单位(C词法记号:关键字、标识符、标点符号分隔符,运算符,空白符及基本数据类型)。,字符型整型基本数据类型实型(单精度)实型(双精度)无值型数据类型数组类型指针类型导出数据类型结构体类型共用体类型枚举类型类,2.1.1关键字(保留字)C系统预定义的、由小写英文字母组成的单词、词头或词组。在C语言中,已有特殊含义和用途。在程序中不得将它们另作它用。预处理命令中,虽不算C关键字,但最好把它们看作为C的关键字,不要使用它们作为其他用途,如(include、define等)。VC的关键字:P1011:表21(43)和20个双下划线新关键字。,2.1.2标识符以字母或下划线开始的字母、数字以及下划线组成的字符序列称为标识符。标识符的第一个字符必须是字母或下划线。以大写字母、小写字母或下划线(_)开始。可以由大小写字母、下划线(_)或数字0-9组成。大写字母和小写字母代表不同的标识符。不能是C+关键字。例如:Rectangle,Draw_line,_No1都是合法的标识符,,不合法的标识符:No.1,a3.5/不能使用小数点。this/这是关键字,不能用作标识符$ab/不能使用符号$6ab/不能以数字开头说明:标识符的有效长度:1-247个字符标识符的命名方法:,2.1.3标点符号9个:#、(、)、,、:、;、2.1.4分隔符运算符、空格、标点符号、回车键和Tab键,用得最多的是空格键。,布尔常量(逻辑常量bool)只有两个:false(假或0)和true(真或1)字符型(char)可以有signed,unsigned整型(int)可以有short,long,signed,unsigned实型(float)双精度型(double)可以有long,基本数据类型:,2.1.5C+的基本数据类型字符型(char)占用1个字节数;取值范围:char128127、signedchar128127、unsignedchar0255;在VC中无修饰词的char,编译程序认为是有符号的;char型从本质上说也是整数类型,长度为1个字节,通常用来存放字符的ASCII码。,整型(int)短整型(shortint):占用2个字节数;取值范围:shortint、3276832767signedshortint、3276832767unsignedshortint;065535。,整型(int):占用4个字节数;取值范围:Int231(2311)signedint231(2311)unsignedint0(2321)长整型(longint)占用4个字节数;取值范围:longInt231(2311)signedlongint231(2311)unsignedlongint0(2321),注意:用signed、unsigned、long、short来修饰int时,关键词int可以省略,在VC中无修饰词的int和char,编译程序认为是有符号的。二进制形式存储中,其最高位为符号位,“1”表示负;“0”表示正。,实型(float)占用4个字节数;取值范围:3.410383.41038;无修饰词。双精度型(double)占用8个字节数;取值范围:double1.7103081.710308longdouble1.7103081.710308。,无值型(void)占用字节数为:0;取值范围为:无值。例:类型修饰符unsigned修饰类型是错误的A.charB.intC.longintD.float答:D,2.1.6常量字面常量在程序中不要任何说明就可直接使用的常量。整型常量十进制整数:若干个09的数字;八进制整数:0(数字0开头)若干个07的数字;十六进制整数:0 x若干个09的数字及AF的字母(大小写均可);长整型与无符号整型常数:以后缀字母L(或l)表示长整型数;以后缀字母U(或u)表示无符号整型数;后缀字母L和U同时组合(大小写无关、顺序无关)表示无符号长整型数;没有后缀字母时,编译系统根据常数的大小自动进行识别。,例:下列十六进制的整型常数表示中,是错误的A.0 xafB.0 x1bC.2fxD.0 xae答:C实型常量一般形式(定点表示):它由一个符号(正号可以省略)后接若干个十进制数字09和一个小数点组成。,指数形式(浮点表示,科学表示法):它由一个十进制整数或定点数后接一个字母e(大、小写均可)和一个13位的十进制整数所组成,字母e之前的部分称为该浮点数的尾数,之后的部分称为该浮点数的指数,该浮点数的值就是它的尾数乘以10的指数幂。注意:在字母e之前必须有数字。例:下列double型常量表示中,是错误的A.E15B.35C.3E5D.3E-5答:A,字符型常量一般形式:用单引号括起来的单个字符。转义序列:就是以转义符“”开始,后跟一个字符或一个整型常量(字符的ASCII编码值)的办法来表示一个字符。详见:P15,表25,段中的描述;P401,附录AASCII码表注意:单引号、反斜杠必须使用其它方法表示,双引号括起来的字符不是字符型常量,例1.在C语言中,合法的字符型常量是_A.tB.AC.65D.A答案:A例2.在C语言中,合法的字符型常量是_A.84B.x43C.abD.0答案:B(假设A的答案是74会怎样?),“转义字符”,意思是将反斜杠()后面的字符转变成另外的意义。如n中的“n”不代表字母n而作为“换行”符。例#includevoidmain()coutabctgden;couthtjkn;程序的运行结果:abcgdehjk,例3.在c+语言中,char型数据在内存中的存储形式是_A.ASCII码B.补码C.反码D.原码(4)字符串常量:用双引号括起来的若干个字符。存放形式是:按串中字符的排列次序顺序存放,每个字符占一个字节,并在末尾添加0作为结束标记。区别a和“a”。(5)布尔常量(逻辑常量)只有两个:false(假)和true(真),2.标识符常量例/*example*/#include#definePI3.1415926/使用编译预处理指令constfloatPII=3.1415926/使用C+常量说明符voidmain()floats,r,i;r=10.;i=2.*PI*r;s=PII*r*r;couti=in;couts=sn;,程序中用#define命令行定义PI代表常量3.1415926,此后凡在此文件中出现的PI都代表3.1415926,可以和常量一样进行运算.这种用一个标识符代表一个常量的,称为标识符常量,即标识符形式的常量,注意标识符常量不同于变量,它的值不能改变,也不能再被赋值。如再被赋值语句赋值是错误的。习惯上,标识符常量名用大写,变量用小写,以示区别。标识符常量必须先定义后使用.,2.1.7变量(P16)其值可以改变的量称为变量。一个变量应该有一个名字,在内存中占据一定的存储单元。在该存储单元中存放变量的值。请注意区分变量名和变量值这两个不同的概念。注意,大写字母和小写字母被认为是两个不同的字符。因此,和是两个不同的变量名。习惯上,变量名用小写字母表示,以增加可读性。,在给变量名和其它标识符命名时,应注意做到“见名知意”。有两种种命名方法:标准命名法和英文单词或汉语拼音法。在V+中,要求对所有用到的变量作强制定义,也就是“先定义,后使用”,否则,在编译时会指出有关“出错信息”。在VC+中,已有特殊含义和用途的英文单词称为关键字(也称保留字)(见P10.表2-1、表2-2),关键字不能作为变量名或标识符使用。,(1)变量说明语句,.,;分别为:Char、short、int、long、float、double例如:charc0,c1;inti,j;longlen;floateps,f0,f15;doubleweight;,(2)变量初始化变量初始化就是给变量赋初值;有两种形式:先定义,再赋初值例如:intsum,fac;sum=0;fac=1;定义时赋值例如:charc=A;intcount=0注意:inta=3;inta(3);是等价的。常量和变量是计算机语言中数据的两种基本形式,初始化不是在编译阶段完成的(只有在第六章中介绍的静态存储变量和外部变量的初始化是在编译阶段完成的),而是在程序运行时执行本函数时赋以初值的。相当于有一个赋值语句,例如inta=3;相当于:inta;/指定a为整型变量a=3;/赋值语句,将3赋予a又如inta,b,c=5;相当于:inta,b,c;/指定a、b、c为整型变量c5;/将5赋给c,例子字符型数据(一),字符常量单引号括起来的一个字符,如:a,D,?,$字符变量用来存放字符常量例:charc1,c2;c1=a;c2=A;字符数据在内存中的存储形式以ASCII码存储,占1字节,用7个二进制位,Page32,字符数据的使用方法字符数据和整型数据之间可以运算。字符数据与整型数据可以互相赋值。字符串常量例:CHINAaa所以:charc;c=a;,Page33,例子字符型数据(二),例子布尔型数据,布尔型变量的说明:例:boolflag;布尔型数据的取值:只有false和true两个值,例子变量初始化,例:inta=3;doublef=3.56;charc=a;intc(5);,Page35,程序例子常量与变量,#includeusingnamespacestd;intmain(void)constintPRICE=30;intnum,total;floatv,r,h;num=10;total=num*PRICE;couttotalendl;r=2.5;h=3.2;v=3.14159*r*r*h;coutvinti;i=(int)x;coutxxn;coutii=,=,!+。关系运算符用来比较两个操作数的数值大小,其运行结果为一整数,关系成立时(为真时),结果为整数1,否则为0(为假时)。例如:floata=2.5,b=10.7,x;inti;x=20.5;i=a=x=b;结果i为1。六个关系运算符的优先级是不一样的,前四个高于后两个。关系运算符的优先级低于算术运算符,但高于赋值运算符。由于对实数进行运算时,计算机会产生误差,因此,在判断两个实数是否相等时,不应直接用“=”进行比较,应为:fabs(x-y)=1e-6fabs()是C+的一个库函数。,四、逻辑运算符和逻辑表达式在C+中,逻辑运算符有三种:!(逻辑非),则:!x为1,!y为0。,(2)逻辑与仅当两个操作数的值都为非0时,其与运算的结果才为真(值为1);否则为假(值为0)。如:对于上述的x和y,xunsignedshortinti,j;intx,y;a=376;b=176;i=a;x=a;j=b;y=b;couta=atb=bn;couti=itj=jn;coutx=xty=yn;,(4)将unsignedint型数据赋给longint,不存在扩展问题,只需将高位补即可。将一个unsignedint型数据赋给一个占字节数相同的整型变量(例如unsignedintint,unsignedlonglong,unsignedshortshort)将unsigned型变量的内容原样送到非unsigned型变量中,但如果数据范围超过相应整型的范围,则会出现数据错误。如:unsignedinta=65535(216-1);intb;b=a;,unsigneda1111111111111111intb1111111111111111将a整个送到b中,由于b是int型,第1位是符号位,成了负数。(-1的补码).可以用coutb=”bn;来验证一下(5)将非unsigned型数据赋给长度相同的unsigned型变量,也是原样照赋(连原有的符号位也作为数值一起传送)。如:,#includevoidmain()unsigneda;intb=-1;a=b;couta=a=,=,=,|=C采用这种复合运算符,一是为了简化程序,使程序精练,二是为了提高编译效率,有利于编译,能产生质量较高的目标代码。)。,八、逗号运算符和逗号表达式C+语言提供一种特殊的运算符逗号运算符。用它将两个表达式连接起来。如3+5,6+8称为逗号表达式。逗号表达式的一般形式为:表达式1,表达式2逗号表达式的求解过程是:先求解表达式1,再求解表达式2。整个逗号表达式的值是表达式2的值。例如,上面的逗号表达式3+5,6+8的值为14。又如,逗号表达式,a=3*5,a*4先求解a=3*5,得a的值为15,然后求解a*4得60,整个逗号表达式的值为60。一个逗号表达式又可以与另一个表达式组成一个新的逗号表达式,如:(a3*5,a*4),a5先使a的值等于15,再进行a*4(但a值未变),再进行a5得20,即整个表达式的值为20。,逗号表达式的一般形式可以扩展为:表达式1,表达式2,表达式3,表达式n它的值为表达式n的值。逗号运算符是所有运算符中级别最低的。因此,下面两个表达式的作用是不同的:x(a3,6*3)x=a=3,6*a第个是一个赋值表达式,将一个逗号表达式的值赋给x,x的值等于18。第个是逗号表达式,它包括一个赋值表达式和一个算术表达式,x的值为3。,其实,逗号表达式无非是把若干个表达式串联起来。在许多情况下,使用逗号表达式的目的只是想分别得到各个表达式的值,而井非一定需要得到和使用整个逗号表达式的值,逗号表达式最常用于循环语句(for语句)中。逗号运算符又称为顺序求值运算符。请注意并不是任何地方出现的逗号都是作为逗号运算符。例如函数参数也是用逗号来间隔的。,2.14sizeof()运算符sizeof()运算符是一元运算,用于计算某一操作数类型的字节数。如:sizeof(int)/其值为2或4sizeof(float)/其值为4,2.2.2各类数值型数据间的混合运算整型、单精度型、双精度型数据可以混合运算。前已述及,字符型数据可以与整型通用,因此,整型、实型(包括单、双精度)、字符型数据间可以混合运算。例如10+a+1.5-8765.1234*b是合法的。在进行运算时,不同类型的数据要先转换成同一类型,然后进行运算。,图中横向向左的箭头表示必定的转换,如字符数据必定先转换为整数,short型转为int型,float型数据在运算时一律转换成双精度型,以提高运算精度(即使是两个float型数据在加化成double型,然后再相加)。,doublefloatlongunsignedintchar,short,纵向的箭头表示当运算对象为不同类型时转换的方向。例如int型与doub1e型数据进行运算,先将int型的数据转换成图double型,然后在两个同类型(double型)数据进行运算,结果为double型。注意箭头方向只表示数据类型级别的高低,由低向高转换,不要理解为int型先转成unsigned型,再转成1ong型,再转成double型。如果一个Int型数据与一个double型数据运算,是直接将int型转成double型。同理,一个int型与一个Long型数据运算,先将int型转换成1ong型。,换言之,如果有一个数据是float型或double型,则另一数据要先转为double型,结果为double型。如果二个数据中最高级别为1ong型,则另一数据先转为1ong型,结果为1ong型。其它依此类推。假设已指定i为整型变量,f为float变量,d为double型变量,e为1ong型,有下面式子:10十ai*f-d/e运算次序为:进行10a的运算,先将a转换成整数97,运算结果为107。进行i*f的运算。先将i与f都转成double型,运算结果为double型。整数107与i*f的积相加。先将整数107转换成双精度数(小数点后加若干个0,即10700000),结果为double型。将变量e化成double型,d/e结果为double型。将10十ai*f的结果与d/e相减的结果为double型。上述的类型转换是由系统自动进行的。,2.2.3逻辑表达式优化的副作用,在C+中,在求逻辑表达式的过程中,一旦能确定逻辑表达式的值时,就不必再逐步求值了。这就是逻辑表达式的优化。例如:假设inta=0,b=4,c=5;acout+i;输出“4”。若改为couti+;则输出“3”。,注意:(1)自增运算符(+),自减运算符(-),只能用于变量,而不能用于常量或表达式,如5+或(a+b)+都是不合法的。(2)+和-的结合方向是“自右至左”。见附录。前面已提到,算术运算符的结合方向为“自左而右”,这是大家所熟知的。如果有-i+,i的左面是负号运算符,右面是自加运算符。如果i的原值等于3,若按左结合性,相当于(-i)+,而(-i)+是不合法的。对表达式不能进行自加自减运算。自增(减)运算符常用于循环语句中使循环变量自动加1。也用于指针变量,使指针指向下一个地址。这些将在以后的章节中介绍。,自增(减)运算符有关表达式使用中的问题说明C运算符和表达式使用灵活,利用这一点可以巧妙地处理许多在其它语言中难以处理的问题。但另一方面,有时会出现一些令人容易搞混的问题,因此务必要小心谨慎。1在表达式中包含自加或自减运算时,很容易出错。i+或i-什么时候进行自加或自减呢?如果有以下赋值语句,若i原值等于3,ki+;显然先将i的原值赋给以k(k的值等于3),然后i进行自加,执行完此语句后,i的值等于4。如果有以下表达式:,k=(i+)+(i+)+(i+)表达式的值是多少呢?有人认为相当于3+4+5,即12。事实上它等于9。即先把i的原值(3)取出来,作为表达式中i的值;因此先进行三个i相加,得9。然后再实现自加,i的值变为6。而k(+i)+(+i)+(+i)有人以为从左到右使i增值,相当于k=456,得15。事实上k=16。原因是:+i的自加是在表达式求解一开始时最先进行的是前两位加法,即对表达式扫描时,先对i进行两次自加,i得5,再进行相加得10,然后进行k=556的运算,故得16。如果是k(+i)+(+i)+(+i)+(+i)?,2C语言中有的运算符为一个字符,有的运算符由两个字符组成,在表达式中如何组合呢?如i+j,是理解为(i+)+j呢?还是i+(+j)?C编译在处理时尽可能多地(自左而右)将若干个字符组成一个运算符(在处理标识符、关键字时也按同一原则处理),如i+j,将解释为(i+)+j,而不是i+(+j)。如有兴趣可验证:intx=3,y=4,z;z=x+y;z是7还是8?或者x是4还是3,y是4还是5?,C+语言表达能力强,其中一个重要方面就在于它的表达式类型丰富,运算符功能强,因而C使用灵活,适应性强。在后面几章中将会看到这一点。作业P30-31第3,7,10,14题,
展开阅读全文