C语言复习全.docx
《C语言复习全.docx》由会员分享,可在线阅读,更多相关《C语言复习全.docx(10页珍藏版)》请在冰豆网上搜索。
C语言复习全
C语言复习参考
说明:
本复习参考不作为C语言考试的重点,不代表C语言考试的范围,只是总结出来的感觉需要同学们引起注意的一些知识点。
复习时,可作为辅助参考资料。
建议在全面复习完教材一遍后再参考该资料。
复习建议:
教材+课件+课后习题+实验书+平时实验报告和作业+复习参考。
预祝:
复习充分,考取好成绩!
第1章C语言程序基础
1.C语言程序的基本结构
(1)C语言由函数组成,有且只有一个main函数。
(2)每个语句和数据定义的最后必须有一个分号;分号是C语句的必要组成部分。
(3)可以用/*······*/对C程序的任何部分作注释。
2.标识符
(1)标识符:
给程序中的实体所起的名字。
(2)标识符的命名规则。
(3)运算符:
注意:
①1/3=0,1.0/3=0.3333;②i++和++i的区别;③a+=5;a=a+5;i=1,j=2,k=3逗号表达式的值为3
3.数据类型
(1)符号常量定义:
#defineM5
(2)变量必须先定以后使用,不能与关键字、函数名等重名。
(3)进行变量声明后,计算机系统会为声明的变量分配相应大小的存储空间,用以存放数据。
单精度实型(float,%f):
4个字节,双精度实型(double,%lf):
8个字节,字符型(char,%c):
1个字节,整型(int,%d):
4个字节(TC中整型占2个字节)。
(4)字符常量——单引号(如:
’a’),字符串常量——双引号(如:
”student”)。
(5)自动类型转换,如:
inta;则a=3.2的值为3
4.数据的输入/输出
(1)printf语句中格式控制符的类型和个数必须与后面变量的类型和个数一一对应。
(2)附加格式说明符。
(3)scanf语句中双引号里面的内容尽量简单,不要多加’\n’等字符,双引号里有什么输入时就必须输入什么,普通的变量前面应加&,表示地址的概念(注意如果是数组名,则不加&)。
(4)使用scanf()函数应注意的问题。
5.算法
(1)算法:
为解决一个问题而采取的方法和步骤。
(2)算法+数据结构=程序
(3)算法的五大特性。
(4)算法的表示方法:
自然语言、传统的程序流程图、N-S流程图。
6.结构化程序设计的三种基本结构:
顺序结构、分支(选择)结构、循环结构。
7.程序设计语言:
机器语言、汇编语言、高级语言。
8.高级语言翻译成机器语言的两种方式:
编译方式、解释方式。
第2章C语言程序的基本结构
1.关系运算符和逻辑运算符
(1)字符数据按其ASCII码值进行比较;
(2)应避免两个实数作==或!
=的比较;
(3)注意等号“==”和赋值号“=”的区别;
(4)关系表达式的值只能是1或0,当表达式成立即为“真”时,值为整数1;否则为“假”,值为整数0。
(5)表示x∈[-1,1]区间,应写为:
x>=-1&&x<=1,不能写为:
-1<=x<=1。
2.如果if、while、for的语句体中有多条语句,必须用大括号括起,构成复合语句。
3.if、while、for中的表达式,一般是逻辑或关系表达式,也可以是任意类型表达式。
如while(a=5)……。
4.else只能与if配对使用。
仅else本身不能单独作为一个语句使用。
5.switch语句中case后面只能是常量值;若执行完某case后的语句没遇到break,则继续执行下一个case语句。
6.循环程序:
注意循环变量的初值、修正值、循环条件等,以及循环中用到的某些变量赋初值,如求累加和变量。
7.一般是先判断条件,再执行循环体;但do—while语句是先执行一遍循环体,再判断条件。
8.内外层循环的循环控制变量不能重名。
9.break、continue语句。
第3章模块化程序设计
1.函数
(1)一个较大的程序常分为若干模块,每个模块实现一个特定的功能。
C语言中用函数来实现模块的功能。
(2)一个C语言源程序文件通常由一个main函数和若干个其它函数组成。
(3)C程序的执行从main函数开始,由主函数调用其它函数,其它函数也可以相互调用,程序流程最后回到main函数,在main函数中结束整个程序的运行。
(4)一个函数(主调函数)可以多次调用多个函数(被调函数)。
同一个函数也可以被一个或多个函数调用任意多次。
但不能调用main函数。
(5)函数不能嵌套定义,但可以相互调用。
2.函数的三大组成要素:
函数定义、函数调用、函数声明。
3.函数调用的过程:
(1)遇到函数调用语句出来找函数;
(2)进行参数传递,形参传给实参,分两种:
传值和传地址;
(3)执行函数;
(4)结果返回,取代函数调用语句;
(5)接着执行下一条语句。
4.函数定义:
函数首部+函数体
(1)函数首部:
函数的类型+函数名+函数的参数,如:
intfunc(inta,inty)
(2)函数的类型为函数返回值的类型,如果函数没有返回值,即没有return语句,则类型为void。
如果定义时没指明函数类型,如:
fun(inta),默认是int型,返回值不确定。
(3)函数名为标识符,最好起能代表函数实现功能的名字。
(4)函数定义中的参数为形参,每个参数都要定义类型,用逗号隔开,形参个数和类型必须与函数调用中的实参一一对应。
只有在函数被调用时系统才给形参分配空间,函数执行完空间释放。
(在函数中用static定义变量时,变量空间不释放。
)
(5)函数体用花括号括起,函数中除了形参其它用到的变量在函数体中定义,函数返回值用return语句返回。
函数中定义的变量只在该函数中起作用(除了形参为地址的情况)。
(6)函数定义的关键是函数首部,先看该函数有没有返回值,即需不需要返回结果,返回值的类型是什么,再确定函数的参数,即看需要告诉函数哪些值才能实现函数的功能。
5.函数调用:
函数名+一对括号的形式。
如:
max(a,b);
(1)如果函数有返回值,一般要将函数调用的结果赋值给一个变量。
如:
c=max(a,b);
(2)括号中的参数为实参,实参和形参个数和类型一一对应。
(3)只有在主函数中有能直接或间接调用到该函数的函数调用语句,该函数才被执行,否则,函数即使定义也不被执行。
6.函数声明:
将函数首部抄一遍,加一个分号。
函数定义在前,使用(被调用)在后,可省略函数声明,反之需要在使用前声明。
7.函数可嵌套调用,不可嵌套定义。
8.使用库函数时,应在文件开头用#include命令将有关头文件包含进来。
9.从作用域角度,变量分为:
全局变量、局部变量。
(1)全局变量:
在函数外部定义,作用域从定义开始到本文件结束。
其间的所有函数都可以使用它,可在各函数间传递值,但容易带来副作用,降低模块独立性。
(2)局部变量:
在函数内部定义,只能在该函数中使用,包括函数的形参和复合语句中定义的变量,main函数中定义的变量也是局部变量,不能被其它函数使用。
(3)不同函数内定义的同名变量,互不影响,因其作用域不同,内存空间独立。
10.变量的存储类别:
auto、static、register、extern。
(1)全局变量的存储类别:
static、extern。
u
(2)全局变量总是存放在静态存储区间,生存期是整个程序运行期间,只赋一次初值,在程序运行前初始化,默认初值为0。
(3)用extern对全局变量加以声明,可以将其作用域扩充到整个文件或其它文件。
定义全局变量时加上static,可将其作用域限制在本文件中,不能被其它文件使用。
(4)局部变量的存储类别:
auto、static、register。
(5)auto型的生存周期时函数被调期间,两次调用之间不保留值。
(6)static型的生存期是整个程序运行期间,保留上一次调用后的值,且只赋一次初值(在程序运行前初始化,默认初值为0)。
11.函数的作用域是全局的,可被其它函数调用。
u
(1)函数存储类别:
static、extern。
默认为extern型。
(2)如:
staticintfunc(inta);则函数不被其它文件使用,所以两文件中的同名静态函数,互不干扰。
12.指针:
就是地址。
(1)内存地址:
在计算机中,把内存区划分为一个一个的存储单元,每个单元为一个字节(8位),它们都有一个编号,这个编号就是内存单元的地址。
(2)一定义变量,系统就在内存中给它分配空间,数据所占有的存储单元个数是由其类型决定的。
如:
实型数据占4个字节。
首地址:
第一个单元的地址。
(3)直接访问:
从内存单元中取出变量的值,或将变量的值存入对应的内存单元中。
间接访问:
先从一个内存单元中获得变量的地址,再根据这个地址找到变量的内存单元,进行数据的读写。
(4)存放地址的变量称为指针变量,变量的地址称为指针,此时,指针变量和指针有了指向关系。
13.指针变量的定义,如:
inta,*p=&a;“*”为指针的标志。
必须给指针变量赋地址值。
指针变量定义时必须指定其所指向的变量的数据类型,而且使用过程中只能指向同一种类型的变量。
14.*p为指针变量p所指向的变量的内容,反映了指针变量的引用方法:
(1)将变量的地址赋给指针变量(p1=&a1)
(2)将一个指针变量赋给另一个指针变量(p2=p1)
(3)通过指针变量间接访问它所指向的变量(*p1)
15.p++表示指针指向了下一个元素。
16.指针作为函数的参数,传递的是实参变量的地址,如:
voidfunc(int*p)。
调用时用某变量的地址常量,或指向该变量的指针作为实参,如主调函数中有定义inta,*q;q=&a;则可用&a或q作为实参进行调用,即func(&a);或func(q);都是将变量a的地址传递给形参指针p,使指针p指向变量a,函数中使用*p就是对a的间接访问。
就可以改变a的值,或者将结果放入a中。
第4章简单构造数据类型
1.数组:
由相同类型的具有固定个数的元素组成的集合。
数组中的所有元素都属于同一个数据类型。
每个数组元素都是一个变量,其类型为数组的类型。
与相同类型的普通变量完全一样。
数组元素在数组中的序号称为下标。
通过数组名和下标来唯一的确定每一个元素。
2.数组定义:
inta[10];或inta[N];数组长度必须是常量值,不能是变量,可以是在程序开始前定义的符号常量,进行长度定义。
3.数组名表示数组所占内存区域的首地址(即第1个元素的地址);
4.数组元素的下标从0开始;如:
数组a包含10个元素:
a[0],a[1],a[2],…,a[9]。
不存在数组元素a[10]。
5.整个数组占用一段连续的内存单元,各元素按下标顺序存放。
6.数组不能整体赋值。
数组中各元素值的输入/出,应使用循环程序逐个输入/出;如:
for(i=0;i<=9;i++)scanf("%d",&a[i]);字符数组例外(gets、puts)。
7.数组中的两种排序方法:
u
(1)冒泡法:
外循环为i=0;iu
(2)选择法:
外循环为i=0;i8.二维数组可以看作是一个矩阵,在内存中按行存放。
(1)可以将二维数组看作是一种特殊的一维数组,它的每一个元素又是一个一维数组。
(2)二维数组中各元素值的输入输出一般用两重for循环实现,如:
for(i=0;i<3;i++)
for(j=0;j<4;j++)
scanf("%d",&a[i][j]);
9.用来存放字符型数据的数组叫字符数组。
(1)字符数组的每个下标变量中只能存放一个字符。
如:
charstr[20];
(2)用"%c"格式控制符实现逐个字符的输入输出。
如:
for(i=0;i<20;i++)printf("%c",str[i]);
10.字符串是由双引号括起来的字符序列,例如:
“HelloWorld!
”。
C语言中没有字符串变量,而使用一维字符数组来存放一串字符。
(1)字符数组:
通常定义较长长度,如:
chars[50];通常用于存放字符串,结束标志为‘\0’。
(2)可用字符串常量为其初始化,如:
chars[]=“sdkhg”;也可由键盘输入,如gets(s);输出用puts(s);
(3)注意:
chars[5]={‘a’,‘d’,‘f’,‘g’,‘w’};此种形式不是字符串,无字符串结束标志,仅仅是普通一维字符数组,不能用puts输出,只能用%c格式逐个输出。
(4)字符数组的输入/出有两种形式:
%c、%s。
11.字符串数组:
字符串数组就是数组中的每一个元素是一个字符串,因为存放字符串的本身是一个字符数组,所以字符串数组实际上是一个二维字符数组。
该二维字符数组的第一维表示字符串的个数,第二维表示每个字符串的存储的长度。
如:
charstr[5][10];表示数组str[5][10]可以存储5个字符串,每个字符串可以存储9个字符,
12.字符串处理函数:
strcpy(s1,s2)、strcat(s1,s2)、strcmp(s1,s2)、strclen(s)、strupr(s)、strlwr(s)。
13.数组与函数
(1)数组元素作为函数参数,与参数之间是值传递,与普通变量作为函数参数用法一样。
(2)数组名作为函数参数,传递的是地址,实参的数组名是指针常量,形参的数组名是指针变量,形参可以定义为数组或指针。
实参数组和形参数组占同一段内存单元,即表示同一个数组,因此形参数组的变化等同于实参数组的变化
14.数组与指针
(1)数组元素的指针就是数组元素的地址。
数组名是一个指针常量,不能改变。
可以用数组名来将数组的首地址赋给指针变量,找到了数组的首地址,就相当于找到了数组中的每一个元素。
(2)如:
inta[10],*p=a;则a代表数组首地址,是指针常量。
元素的表示方法:
a[i]、*(a+i)、p[i]、*(p+i);元素地址:
&a[i]、a+i、&p[i]、p+i。
u(3)区别:
a实指针常量,只不能变,而p是指针变量,可进行增减运算;所以常通过p的增减运算来快速访问数组a,如:
while(pu(4)理解(*p)++、*p++、*(p++)、p++的含义。
执行p++后指针拨动的单元数(由元素类型决定)。
15.字符串与指针
(1)用字符指针指向一个字符串。
如:
char*s="IloveChina!
";程序在定义字符指针变量s时,把字符串首地址(即存放字符串的字符数组的首地址)赋给s。
(2)对字符串中字符的存取,可用下标方法,也可用指针方法。
如:
下标法:
for(i=0;a[i]!
='\0';i++)b[i]=a[i];b[i]='\0';指针法:
for(;*pa!
='\0';pa++,pb++)*pb=*pa;*pb='\0';
(3)字符指针与字符数组的区别。
(4)字符指针作为函数参数:
将一个字符串从一个函数传递到另一个函数,可以用地址传递的方法,即用字符数组名作参数或用指向字符串的指针变量作参数。
在被调用的函数中可以改变字符串的内容,在主调函数中可以得到改变了的字符串。
第5章复杂构造数据类型
1.当要存储表格形式的数据时(表格中的每一项类型可能不一致),可以定义为结构体类型。
2.结构体:
struct
(1)注意,在结构体类型的定义后面有分号。
可理解为一个学生的信息。
(2)结构体变量定义的三种形式:
先定义结构体类型,再定义结构体变量;再定义结构体类型的同时定义结构体变量;省略结构体名,缺点:
以后不能再定义该结构体类型的变量。
(3)结构体类型的定义可放在函数内或者函数外,一般放在所有函数的前面,再它定义后的所有函数都可以使用。
(4)结构体的成员可以是任何类型,成员引用:
结构体变量名.成员名。
(5)结构体变量占用内存大小为:
各成员占用内存之和。
(6)不能将一个结构体变量作为一个整体进行输入输出;只能对结构体中的各个成员分别进行输入输出。
3.结构体数组即基类型是结构体的数组,数组中的每个元素都是结构体变量。
可理解为40名学生的信息。
同普通数组一样使用。
初始化时注意双重括号。
4.结构体变量的指针就是该变量所占据的内存段的起始地址。
u
(1)结构体指针:
(*p).成员名或p->成员名
(2)只能用结构体变量地址赋值,不能赋某成员的地址,如:
p=&stu.name;是错误的。
5.共用体:
所谓“共用体(union)”是指使几个不同的变量共占同一段内存的数据类型。
(1)定义形式同结构体。
成员引用:
共用体变量名.成员名。
(2)占用内存大小为:
共用体中较长的成员的长度。
(3)某一时刻只有一个成员起作用,最后一个存放的成员值有效。
(4)结构体类型与共用体类型可互相嵌套使用,即结构体成员的类型也可以是共用体类型,反之亦然。
6.枚举类型:
将变量的所有取值一一列举出来,变量的值只限于列举出来的值的范围内
(1)如:
enumweek{sun,mon,tues,wen,thur,fri,sat}day;
(2)枚举元素就是枚举变量的可能取值,如:
day=mon;
(3)枚举元素视为常量,其值就是序号(0~n-1)。
也可以在定义时改变其值,如:
enumweekday{Sun=7,Mon,Tue,Wed=0,Thu,Fri,Sat};则Mon的值为8,Thu的值为1。
第6章磁盘数据存储
1.文件的类型:
ASCII码文件(文本文件)、二进制文件。
2.文件的基本操作:
读和写,使用有关文件函数来完成,需包含头文件stdio.h。
3.文件操作的四大步骤:
(1)定义文件类型指针;
(2)打开文件;
(3)向文件写入数据,或从文件读取数据;
(4)关闭文件。
4.文件的打开方式:
r(只读,要求文件必须存在)、w(只写,文件存在重新写,不存在新建一个)、a(追加)、r+(读写,先读后写,要求文件必须存在)、w+(读写,先写后读,文件不存在新建)、a+(读写,先追加再读),如果读写对象是二进制文件,则在后面加’b’,即rb、wb、ab、rb+、wb+、ab+。
5.fopen与fclose需配对出现!
6.文件读写分类函数:
fgetc(fp)、fputc(ch,fp)、fread(*p,size,n,fp)、fwrite(*p,size,n,fp)、fgets(*str,n,fp)、fputs(*str,fp)、fscanf(fp,“格式控制符”,地址列表)、fprintf(fp,“格式控制符”,输出列表)。
7.文件定位函数
(1)rewind函数
(2)位置指针随机移动函数fseek
(3)求文件位置指针当前位置的函数ftell
补充:
如何写出函数定义?
(函数体包括函数首部和函数体)
例如:
1、将指定的字符打印n次。
思考:
首先考虑函数首部怎么写,函数首部三个要素:
函数类型(即返回值的类型)、函数名、函数参数(形参)。
(1)这个函数有没有结果需要返回?
没有,只要在函数里把字符打印n次工作就结束了,因此,函数类型(没有返回值)为void。
(2)函数名可取与功能相关的名字,如print。
(3)函数的参数,要告诉这个函数哪些信息,函数才能执行?
一个需要知道指定的字符是什么,第二个需要知道打印多少次,即n的值为多少。
因此参数就可以定义出来了:
(charch,intn)。
这样,函数首部就可以写出来了:
voidprint(charch,intn)。
下面考虑函数体:
函数体主要是实现函数的功能,在本例中即如何实现将字符ch打印n次。
可用循环实现:
for(i=0;i因此,完整的函数定义可参考如下:
voidprint(charch,intn)
{inti;
for(i=0;iputchar(ch);
putchar('\n');
}
进一步考虑,这样的函数定义,对应的函数调用语句怎么写?
还是三个要素:
函数返回值、函数名、函数参数(实参)。
这个函数没有返回值,在函数调用时不需要赋值;函数名,为函数定义时取的函数名print;函数参数为函数定义中形参的具体的值,如(‘*’,20),即将*打印20次。
因此完整的函数调用语句为:
print(‘*’,20);
例如:
2、求整数x的n次幂(n>0)
函数首部:
(1)函数类型,求完整数x的n次幂后有个结果,而且需要将这个结果返回给主调函数,这个结果比较大,一般将这个结果定义为float类型,即这个函数有返回值,返回值为float类型。
因此,函数的类型为float。
(2)函数名,可取为power。
(3)函数的参数,需要知道x的值和n的值函数才能执行运算得出结果,因此形参为(intx,intn)。
函数首部:
floatpower(intx,intn)
函数体:
inti,mul=1;
for(i=1;i<=n;i++)
mul=mul*x;
return(mul);(函数需要返回最后的运算结果,用return实现,注意返回值的类型应与函数的类型一致)
函数定义:
floatpower(intx,intn)
{
inti;
floatmul=1;
for(i=1;i<=n;i++)
mul=mul*x;
return(mul)
}
函数调用语句:
因为函数有返回值,应将这个返回值赋值给一个同种类型的变量,否则将得不到这个值。
因此,需要在主调函数中定义一个float类型的变量来接收return回来的mul值。
函数调用语句可写为mul=power(5,3);表示求5的3次幂。