C语言程序设计2ppt.ppt_第1页
C语言程序设计2ppt.ppt_第2页
C语言程序设计2ppt.ppt_第3页
C语言程序设计2ppt.ppt_第4页
C语言程序设计2ppt.ppt_第5页
已阅读5页,还剩235页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

C语言程序设计2,第5章 数 组,从前面几章所介绍的内容可以看到,我们在进行程序设计时仅涉及C语言的基本数据类型。在实际应用过程中仅仅有基本数据类型是远远不够的,为了解决这一矛盾,C语言还提供了多种构造数据类型;数组是C语言提供的一种常用的构造数据类型。数组是把具有相同类型的若干变量按有序(指位置上有序)的形式组织起来的同类数据元素的集合,它的每一个元素是由数组名和下标来唯一标识的。,C语言的数组类型具有两个特点:一是数组元素的个数必须是确定的,不允许随机变动,但元素值是可变的;二是数组元素的类型必须相同,不允许是混合类型,即一个数组的元素只能取一种数据类型,可以是整型、浮点型、字符型、指针类型、结构体类型等。 数组又可分为一维数组和多维数组,本章介绍数值数组和字符数组定义和使用方法,其余的在以后各章陆续介绍。,5.1 一 维 数 组, 根据标识符的定义规则自行确定数组的名称; 确定数组的大小,即数组中元素的个数; 表明数组的基类型,即其元素的类型。,在使用一个数组之前,同前面讲到的变量一样必须对它先行定义。一般来说,数组的定义语句出现在函数体的开头,它的任务是:,5.1.1 维数组的定义,当数组中每个元素只带有一个下标时,这样的数组称为一维数组。在C语言中,定义一维数组的一般形式如下: 类型说明符 数组名常量表达式,; 其中,类型说明符是指数组的基类型,也就是每个数组元素的类型。常量表达式是一个其值为正整数的表达式,用来表示该数组含有的元素个数,即定义了数组的大小。例如: long array20; 它表示数组名为array,该数组有20个long型元素,它们是array0、array1、array2 array19。 在定义一维数组时要注意以下几点:, 数组名的命名规则遵守标识符的命名规则。 常量表达式指出数组的长度,长度为n时,数组元素下标只能从0到n-1,即数组中第一个元素的下标是0,数组中的最后一个元素的下标应该是n-1(称为数组下标的上界)。 常量表达式可以包含常量和符号常量,但不能包含变量。也就是说,不允许对数组的大小作动态的改变。例如:,int n=20; int an; 此种定义形式是错误的,因为n是变量而不是常量。 在一个定义数组的语句中,可以有多个数组说明符,它们之间用逗号隔开。例如: float s10,t20,w30; 以上语句定义了三个分别名为s、t、w的单精度(即float)类型数组,其中数组s包含10个元素,数组下标的上界为9;数组t包含20个元素,数组下标的上界为19;数组w包含30个元素,数组下标的上界为29。,5.1.2 一维数组元素的引用,数组定义好之后,便可使用它了。但是,数组是一种构造类型,它的使用与简单类型的使用是不一样的。语言中数组名实质上是数组的首地址,是一个常量地址,不能对它进行赋值,因而不能利用数组名来整体引用一个数组,只能单个地使用数组元素。数组元素的描述与引用是由数组名加方括号中的下标组成。, 其中下标可以是整型常量、整型变量或整型表达式,要求变量和表达式要有确定的值,并且其起始值最小为0,最大为元素总个数减1。例如: array3=array2+array1+array2-2 一个数组元素实质上等同于一个变量,代表内存中的一个存储单元。它具有和相同类型单个变量一样的属性,可以对它进行赋值和参与各种运算。一个数组占有一串连续的存储单元,而变量即使连续定义,其存储位置不一定连续。 在C语言中,数组作为一个整体,不能参与运算,只能对单个的元素进行处理。,一维数组元素的引用方式为: 数组名下标 说明:,注意:在引用时,下标不要超过数组的范围。例如,array数组的长度为5,则下标值只能在04之间。特别需要强调的是,由于C语言对程序设计的语法限制不太严格,所以C编译不作下标越界检查,即使引用array5,编译时系统也不会提示错误,是把array4后面的一个单元中的内容作为array5来引用,如图5.1所示。而array 4后面的单元并不是我们想要引用的数组元素,如果我们对其进行修改,有可能会造成数组以外的其他变量的值无法使用。所以,必须保证使用的下标值在数组定义的范围内。,图5.1 一维数组元素的引用,5.1.3 一维数组的初始化,变量在定义的同时可以进行初始化,数组也可在定义的同时对其各元素指定初始值,即初始化。 一维数组的初始化有以下几种方式:, 对数组的全部元素赋初值。例如: static int num51,2,3,4,5; 用花括号把要赋给各元素的初始值括起来,数据之间用逗号分隔。关键字static是“静态存储”的含义,可以省略,但意义不同,对于静态存储将在第6章介绍。 该语句执行之后有: num0=1,num12,num23,num34,num45。 对数组的部分元素赋初值。例如: int num5=1,2,3; 该语句执行之后有: num01,num12,num23,num30,num40。, 对数组的全部元素赋初值时,可以省略数组长度说明,c编译系统会根据元素实际个数自行确定。例如: int num1,2,3,4,5;该语句执行之后num数组的长度自动确定为5,并有: num01,num12,num23,num34,num45。 若定义数组长度大于元素个数,则不能省略数组长度的定义。,5.1.4 一维数组应用举例,例5.1 建立一个存放10个数据的数组,假设数组元素值为此数组元素下标的10倍,然后将全部元素按正序和逆序分别输出。 本例的程序如下: #include void main() ,int i,a10; /*定义一个整型变量i和一个具有十个元素的数组a*/ for(i=0;i=0;i-) printf(“%5d“,ai); /*通过for循环倒序输出数组元素的值*/,printf(“n“); /*为了输出时格式清晰,程序控制换一行*/ 运行结果如下: 0 10 20 30 40 50 60 70 80 90 90 80 70 60 50 40 30 20 10 0 例5.2 从键盘任意输入10个整数,求它们中的最大值、总和和平均值。 本例的程序如下:,#include void main() int i,a10,sum=0,max; float ave; printf(“input 10 number:n“); for(i=0;i10;i+) scanf(“%d“,i+) ,if(aimax) max=ai; /* 求最大值 */ sum+=ai; /* 求总和 */ ave=sum/10.0; /* 求平均值 */ printf(“max=%d,sum=%d,ave=%fn“,max,sum,ave); 运行结果如下: input 10 number: 77 87 94 68 72 56 90 64 82 85 max=94,sum=698,ave=69.800003,例5.3 用一维数组计算Fibonacci数列的前20项。 Fibonaccti数列有如下特点:第1,第2两个数为1,1。从第3个数开始,该数是其前面两个数之和。数列定义如下: f(1)1 (n=1) f(2)1 (n=2) f(n)=f(n-1)+f(n-2) (n3),思考一下:在求平均值时,若写成ave=sum/10 ,结果会有怎样变化?,由于数组的下标从0开始,为了符合人们的习惯,只用120,这里定义一个有21个元素的数组f21,而f0没有使用。本例的程序如下: #include void main() int f21,i; f1=1; f2=1; for(i=3;i=20;i+) fi=fi-1+fi-2; for(i=1;i=20;i+), if(i-1)%5=0) printf(“n“); /* 5个数据换行 */ printf(“%10d“,fi); 本程序的执行结果如下: 1 1 2 3 5 8 13 21 34 55 89 144 233 377 610 987 1597 2584 4181 6765 思考一下,如果想求Fibonaccti数列的前40项,程序该如何修改?,例5.4 判定用户输入的正整数是否为“回文数”。 所谓回文数是指正读反读都相同的数。把用户输入的数的各位数字分离出来进行比较。 本例的程序如下: #include void main() int a10,i,k=0,b; long number,n; printf(“输入一正整数:“); scanf(“%ld“,do /* 利用循环分离正整数的各位数字*/ ak+=n%10; /*把分离出来的数字放在定义好的数组中*/ n=n/10; while(n!=0); b=1; /* 设定标志用以判定该数是否为回文数 */ for(i=0 ;i=(k-1)/2;i+) if(ai!=ak-1-i) b=0; /*标志变量被赋值为0*? if(b) /*若b不等于0*? printf(“%ld n 是回文数“,number); else /*若b等于0*/ printf(“%ld n不是回文数“,number);, 本程序的两次执行结果如下: 输入一正整数:1234321 1234321是回文数 输入一正整数:123321 123321是回文数 输入一正整效:12345621 12345621不是回文数 例5.5 输入任意10个数,对其进行从小到大排序。 方法1:用起泡排序法。 起泡排序是将相邻的两个数进行比较,若为逆序,则将两个数据交换。小的数据就好像水中气泡逐渐向上漂浮,大的数据好像石块往下沉。如图5.2所示。,图5.2 起泡排序,若有10个数,第1次将49和38交换,第2次将49和64交换共进行9次,得到38、49、64、75、13、27、52、34、22、96的顺序。经过这样的交换,则最大的数96已经像石块一样沉到底,为最下面的一个数,而小数像水中气泡一样向上浮起到一个位置。经过第一趟(共9次)比较后,得到最大的数96。然后进行第二趟(共8次)比较,得到一个次大的数75,依次进行下去,对余下的数按上面的方法进行比较,共需要9趟。如果有n个数,则要进行n-1趟比较。在第一趟中要进行n-1次比较,在第j趟进行n-j次比较。,程序如下: #include void main() int data10; /* 定义一个一维整型数组data */ int i,j,temp; /* 定义循环变量和临时变量 */ printf(“Please input 10 numbers:n“); for(i=0; i10; i+) scanf(“%d“, ,/* 冒泡法排序 */ for(i=0; idataj+1) /* 如果dataj大于dataj+1,交换两者的位置 */ temp=dataj; dataj=dataj+1; dataj+1=temp; printf(“nthe result of sort:n“); /* 输出排序后的数据 */,for(i=0; i10; i+) printf(“%d “,datai); 本程序的执行结果如下: Please input 10 numbers: 49 38 64 96 75 11 27 52 34 22 the result of sort: 11 22 27 34 38 49 52 64 75 96 方法2:用选择排序法。 选择排序法是从10个数据中找出最小数与第1个元素值交换,在后9个数据中找出最小数与第2个元素值交换在后2个数据中找出最小数与第9个元素值交换,即每比较一次,找出一个未排序数中的最小值。共比较9轮,如图5.3所示。,图5.3 选择排序,程序如下: #include void main() int values10, i; /* 定义一个一维整型数组values */ int temp, current, j; /* 定义循环变量和临时变量 */ printf(“Please input 10 numbers:n“); for (i = 0; i 10; i+) scanf(“%d“, current+) /* 选择法排序 */,for (j = current + 1; j valuesj) temp = valuescurrent; valuescurrent = valuesj; valuesj = temp; printf(“nthe result of sort:n“); /* 输出排序后的数据 */ for (i = 0; i 10; i+) printf(“%d “, valuesi); ,本程序的执行结果如下: Please input 10 numbers 49 38 64 96 75 11 27 52 34 22 the result of sort: 11 22 27 34 38 49 52 64 75 96 需要特别说明的是:以上两个排序程序并不是最优化的,在掌握上述程序之后,有兴趣的读者可以对上述两个程序分别进行优化。,5.2 二维数组和多维数组,前面介绍的数组只有一个下标,称为一维数组, 其数组元素也称为单下标变量。在实际问题中有很多量是二维的或多维的, 因此语言允许构造多维数组。多维数组元素有多个下标, 以标识它在数组中的位置,所以也称为多下标变量。 本小节只介绍二维数组,多维数组可由二维数组类推而得到。二维数组类型说明二维数组类型说明的一般形式是:,5.2.1 二维数组和多维数组的定义,类型说明符 数组名常量表达式1常量表达式2; 其中常量表达式1表示第一维下标的长度,常量表达式2 表示第二维下标的长度。 例如:int array35; 说明了一个三行四列的数组,数组名为array,其下标变量的类型为整型。该数组的下标变量共有35个,即下面15个元素(注意括号中的数值的范围):array00,array01,array02,array03,array04 array10,array11,array12,array13 ,array14 array20,array21,array22,array23 ,array24,二维数组在概念上是二维的,即是说其下标在两个方向上变化,下标变量在数组中的位置也处于一个平面之中,而不是象一维数组只是一个向量。但是,实际的硬件存储器却是连续编址的,也就是说存储器单元是按一维线性排列的。如何在一维存储器中存放二维数组,可有两种方式:一种是按行排列, 即放完一行之后顺次放入第二行。另一种是按列排列,即放完一列之后再顺次放入第二列。在语言中,二维数组是按行排列的。按行顺次存放,先存放array0行,再存放array1行,最后存放array2行。每行中有四个元素也是依次存放。由于数组array说明为int类型,该类型占两个字节的内存空间,所以每个元素均占有两个字节。,值得说明的是:可以把array看作是一个有3个元素的一维数组,而每个一维数组中的元素又是一个大小为5的一维数组。如图5.4所示,即定义了一个35(3行5列)的二维数组array。,图5.4 二维数组的含义,定义二维数组时要注意以下几点:, 二维数组中元素的顺序是按行存放,即在内存中先顺序存放第一行的元素,再存放第二行的元素,依此类推。如图5.5所示。 从二维数组的排列顺序可以计算数组元素在数组中的顺序号。假设为nm的二维数组,其中第i行第j列元素在数组中的位置公式为im+j+1。 二维数组可看成是一个特殊的一维数组,它的元素又是一维数组。 多维数组的定义与二维数组的定义相似。例如:,int array232; 定义了一个三维数组array,array是含有2个元素的二维数组,array的每个元素是含有3个元素的一维数组,而array的每个元素中的元素是含有2个整数,则array中共包括23212个整型元素,结构如图5.6所示。其在内存中的排列如图5.7所示。,图5.5 二维数组元素存放顺序,图5.6 三维数组的含义,图5.7 三维数组元素存放顺序,可以看到,第三维的下标变换得最快,其次为第二维的下标,最慢的是第一维的下标。 注意:对于初学者而言,掌握到二维数组就可以了。 5.2.2 二维数组和多维数组的引用 数组必须先定义,然后才能使用。二维数组元素的引用方式为: 数组名下标下标 其中:下标可以是整型常量、变量或整型表达式,但每一维的下标值都不能超过定义时的范围。例如:,array2-12 但要区别定义数组array23和引用array23的含义,前者表示定义数组的维数和各维的大小,后者array23中的2和3是下标值,array23形式上代表某一个元素,但对于给定定义int array23而言,引用array23时是不合法的。 多维数组的引用方式和二维数组元素的引用方式相似。例如: array120 注意每一维的下标都用方括号括起来,每一维的下标值都不能超过定义时的范围。,5.2.3 二维数组和多维数组的初始化,二维数组的初始化有如下几种方式: (1) 对数组的全部元素赋初值,分以下几种情况 分行给二维数组赋初值,例如: 把第一个花括弧内的数据赋给第一行元素,把第二个花括弧内的数据赋给第二行元素依次按行赋值。 该语句执行之后有: array001,array012,array02=3, array104,array115,array12=6, 按数组在实际存储时的排列顺序赋初值,例如: int array231,2,3,4,5,6; 该语句执行之后有: array001,array012,array02=3, array104,array115,array12=6, 允许省略第一维长度的说明,但第二维的长度不能省。例如: int array31,2,3,4,5,6; array001,array012,array02=3, array104,array115,array12=6,分行给二维数组部分元素赋初值时,也可以省略第一维长度的说明,但第二维的长度不能省。例如: int array31,2 ,4,5 ; 该语句执行之后,系统会根据内部花括号的个数确定为2行。并且未被赋值的元素自动赋0值,因此有: array001,array012,array02=0, array104,array115,array12=0, 多维数组的初始化和二维数组的初始化相似。,三维数组的初始化有如下几种方式: 分行给三维数组赋初值,例如: int array232=1,2,3,4,5,6,7,8,9,10,11,12; 把array看作是两个二维数组,每个二维数组是3行2列,按每个二维数组按行赋初值的方法,分别用花括号把各行元素值括起来,再将第三行的初值再用花括号括起来。 按数组在存储时的排列顺序赋初值,例如: int array232=1,2,3,4,5,6,7,8,9,10,11,12;, 允许省略第一维长度,例如: int array32=1,2,3,4,5,6,7,8,9,10,11,12; 系统自动算出第一维的大小为2,但第二维和第三维不能省。,5.2.4 二维数组和多维数组的举例,例5.6 输入一个33的矩阵,分别计算并输出矩阵主对角线和周边元素的和。 本例的程序如下: #include void main() int a33,sum1=0,sum2=0,i,j; printf(“Please input A: n“); /* 输入矩阵A */ for(i=0;i3;i+) for(j=0;j3;j+),scanf(“%d“,运行结果如下: Please input A: 1 2 3 4 5 6 7 8 9 caculate sum of catercorner and around: sum1= 15,sum2= 40 例5.7 向三维数组中输入值并输出此数组中的元素值。 本例的程序如下: #include void main() int a232,i,j,k;,printf(“Please input A n“); /* 输入三维数组A */ for(i=0;i2;i+) for(j=0;j3;j+) for(k=0;k2;k+) scanf(“%d“,运行结果如下: Please input A 1 2 3 4 5 6 7 8 9 10 11 12 Please output A a000=1 a001=2 a010=3 a011=4 a020=5,a021=6 a100=7 a101=8 a110=9 a111=10 a120=11 a121=12 例5.8 求一个44矩阵的次对角线元素之积。 本例的程序如下:,#include void main() int a44=1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,i,j; int s=0; /*设定累加和变量并设初值为0*/ for(i=0;i4;i+) for(j=0;j4;j+) if(i+j=3) s*=aij; printf(“s=%dn“,s); 运行结果如下: s=34,例5.9 编写一个程序统计某班3门课程的成绩,它们是语文、数学和英语。先输入学生人数,然后按从小到大的编号顺序依次输入学生成绩,最后统计每门课程全班的总成绩、平均成绩以及每个学生课程的总成绩和平均成绩。 依题意,本程序定义一个二维数组score505。scorei0、scorei1、scorei2分别存储3门课程的分数,scorei3和scorei4分别存储计算出来的个人总分和平均分。total3和avg3分别存储全班各科总分和平均分,本例程序如下:,#include void main() int score505,total3,avg3; int i,j,n; printf(“学生人数:“); scanf(“%d“,scanf(“%d%d%d“, j+), totalj=0; for(i=0;in;i+) totalj+= scoreij; avgj=totalj/n; printf(“n编号 语文 数学 英语 总分 平均分n“); for(i=0;in;i+), printf(“%5d“,i+1); for(j=0;j5;j+) printf(“%7d“, scoreij); printf(“n“); printf(“总分: “); for(i=0;i3;i+) printf(“%7d“,totali); printf(“n平均分:“);,printf(“总分: “); for(i=0;i3;i+) printf(“%7d“,totali); printf(“n平均分:“); for(i=0;i3;i+) printf(“%7d“,avgi); 本程序的一次执行结果如下: 学生人数:3,输入成绩 1 65 76 70 2 82 79 85 3 92 82 95 编号 语文 数学 英语 总分 平均分 1 65 76 70 211 70 2 82 79 85 246 82 3 92 82 95 269 89 总分: 239 237 250 平均分: 79 79 83,5.3 字符数组和字符串,5.3.1 字符数组 字符数组是用来存放字符的数组,其定义和引用方式与前面介绍的数组形式相同,只是定义的数据类型为字符型,并且利用字符数组处理字符串时具有一定得特殊性和便利性,字符数组既可以是一维的,也可以是多维的。 1. 字符数组的定义形式 一维字符数组的定义形式: char 数组名常量表达式; 例如:char str5;,二维字符数组的定义形式: char 数组名常量表达式常量表达式; 例如:char str520; 2. 字符数组的引用 数组必须先定义,然后才能使用。 一维字符数组的引用形式: 数组名下标 例如:str2=str2*2; 二维字符数组的引用形式: 数组名下标下标,其中下标可以是整型常量、变量或整型表达式,但每一维的下标值都不能超过定义时的范围。 例如:str21=str1*20; 3. 字符数组的初始化 一维字符数组的初始化可以逐个地将字符赋给数组中每个元素,例如: char str10=C,L,a,n,g,u,a,g,e ; 该语句执行之后有: str0=C,str1= , str2=L,str3=a,str 4=n, str5=g,str6=u, str7=a,str8=g ,str9=e,如果花括号中提供的初值个数大于数组长度,则按语法错误处理。如果初值个数小于数组长度,则只将这些字符赋给数组中前面的那些元素,其余的元素自动定为空字符(即0),例如: char str11=C, ,L,a,n,g,u,a,g,e ;,数组的状态如图5.8所示,图5.8 全部元素初始化,该语句执行之后有: str0=C,str1= , str2=L,str3=a,str 4=n, str5=g,str6=u, str7=a,str8=g ,str9=e 数组的状态如图5.8所示。 str0str1str2str3str 4str5str6str7str8str9CLanguage图5.8 全部元素初始化 如果花括号中提供的初值个数大于数组长度,则按语法错误处理。如果初值个数小于数组长度,则只将这些字符赋给数组中前面的那些元素,其余的元素自动定为空字符(即0),,例如: char str11=C, ,L,a,n,g,u,a,g,e ; 该语句执行之后有: str0=C,str1= , str2=L,str3=a,str 4=n, str5=g,str6= u, str7=a,str8=g ,str9=e,str 10=0, 数组的状态如图5.9所示。 str0str1str2str3str4str5str6str7str8str9str10CLanguage0图5.9 部分元素初始化,二维字符数组的初始化有以下两种方式: 逐个字符赋给数组中每个元素,这一点和数值型数组相同,例如: char str25=b,o,o,k,s,c,o,m,e,s ; 该语句执行之后有: str00=b,str01=o, str02=o,str03=k,str04=s, str10=c,str11=o, str12=m,str13=e,str14=s, 数组的状态如图5.10(a)所示。 部分字符赋给数组中每个元素,例如:,char str25=b,o,o,k,c,o,m,e; 该语句执行之后有: str00=b,str01=o, str02=o,str03=k,str04=0, str10=c,str11=o, str12=m,str13=e,str14=0, str0booksstr1comes(a) 数组的状态如图5.10(b)所示。 str0book0str1come0 (b) 图5.10 二维字符数组初始化,5.3.2 字符串,1. 字符串的意义 从逻辑意义上说,字符串就是一串字符文字,从物理意义上说,字符串就是用一个字符数组来存储的一组字符。但不能说字符数组就是字符串,因为数组中的每一个数据元素在逻辑上是独立的,而字符串在逻辑上是一段相关的文字内容,不是一个个独立的字符。C语言没有字符串变量,字符串不是存放在一个变量中而是存放在一个字符数组中。C语言规定以“0”作为字符串的结束标志。“0”是ASCII代码值为0的字符。ASCII代码值为0的字符,不是一个普通的可显示字符,而是一个“空操作”字符,它不进行任何操作,只是作为一个标记。它占内存空间,但不计入字符串的长度。 2. 用字符串给字符数组赋初值 char str8“Goodbye“; char str25=“book“,“come“; 说明: 用字符串赋初值可以省略花括号。 如果字符串的字符个数大于数组的长度,系统报错。, 如果字符串的字符个数小于数组的长度,则最后一个字符后添加“0”作为字符串的结束标志。 在用字符串给一维数组赋初值时也可以省略数组长度,对二维数组赋初值时可以省略第一维的长度,但和数值型数组有所不同;例如: char str=”Goodbye”,虽然引号内是7个字符,但中括号内隐含的数是8,因为字符串有一个结束标志0也要占据存储空间;而数值型数组有几个数中括号内就是熟的总数。 3. 通过赋初值确定数组长度 char str1G,o,o,d,b,y,e; char str2“Goodbye“;,str1是长度为7的字符数组,如图5.11(a)所示,str2是长度为8的字符数组(包括结尾的“0”),如图5.11(b)所示。,图5.11 字符数组的长度,注意:字符串存放在字符数组中,但字符数组与字符串可以不等长。字符串以“0”作为结束标志,字符数组不要求其末尾必须为“0”。C语言对下标运算中的下标值不做越界检查,下标运算中所提供的下标值如果超过定义的空间范围,在语法上也不算错,即字符数组中所存储的字符串的长度如果超出了字符数组的定义空间,编译时不会有错,但在运行时,却可能由于溢出而导致不可预测的后果,5.3.3 字符串处理函数,为了便于字符串的处理,C语言的库函数中提供了一些字符串处理函数: 1. 字符串的输入输出函数 (1) 逐个字符输入输出(利用已讲过的函数) 在输入、输出字符串时使用格式符“c”。例如: char str10; scanf(“%c“, 向数组元素str4中输入和输出一个字符,其方法与数值型数组的输入和输出一样。,(2) 将整个字符串一次输入输出 使用格式符“s”整体输入输出(利用已讲过的函数) 在输入字符串时使用格式符“s”,输入的字符串是以“0”结尾,即输入的字符串中不能包含“0”字符,否则输入结束。输入字符串时,字符数组名前不要加“&”前缀。由于数组名代表数组的起始地址,所以不用加“&”前缀(其实&是C语言中计算变量地址的运算符)。在输入、输出字符串时从该起始地址开始逐个输入、输出字符,直到遇到字符结束标志0为止。,在输入、输出字符串时从该起始地址开始逐个输入、输出字符,直到遇到字符结束标志0为止。在输出字符串时使用格式符“s”,输出的字符串是以0结尾,即输出的字符串中不能包含0字符 串中不能包含0字符,否则输出结束。例如: char str10; scanf(“%s“,str); printf(“%s“,str); 说明: 如果数组长度大于字符串实际长度,也只输出到“0”为止。, 如果一个字符数组中包含一个以上“0”,则遇到第一个“0”时输出就结束。例如: char string15; scanf(“%s“,string); 输入数据: C Language 在内存中的状态如图5.12(a)所示。则输出的结果只有“C”,没有“Language”,因为空格是输入函数的默认分隔符。 如果输入多个字符串,则字符串之间以空格分隔。例如:,char string15, string210; scanf(“%s%s“,string1,string2); 输入数据: C Language 在内存中的状态如图5.12(b)所示。但是,如果字符串中含有空格,则可以用字符串的输入、输出函数来完成。 使用gets和puts函数 gets(字符数组)字符串输入函数:功能:从终端输入一个字符串到字符数组,该函数返回值是字符数组的起始地址。例如: 功能:从终端输入一个字符串到字符数组,该函数,返回值是字符数组的起始地址。例如: char string11; gets(string); 输入:C Language 将字符串“C Language”送给字符数组string,函数返回值是字符数组string的起始地址。在内存中的状态如图5.12(c)所示。 (a) (b),图5.12 字符串输入后的内存状态 说明: gets( )读取的字符串,其长度没有限制,编程者要保证字符数组有足够大的空间,用于存放输入的字符串。,说明: gets( )读取的字符串,其长度没有限制,编程者要保证字符数组有足够大的空间,用于存放输入的字符串。 用gets函数可以读入含有空格字符的字符串,而scanf则不能。 在输入时,将“n”转换成字符串结束标志“0”。 puts(字符串) 字符串输出函数: 功能:将一个字符串输出到终端。输出的字符串可以包括转义字符。例如: char string = “This is an examplenoutput string“; puts(string); 输出: This is an example output string,说明: 在输出时将字符串结束标志“0”转换成“n”,即输出完字符串后会换行,而printf函数换行时必须用转义字符“n”。 字符串可以是字符数组(要求数组内部包含“0”)或字符串常量。 一次只能输入/输出一个字符串。,2. strcat (字符数组1,字符数组2) 字符串拼接函数 功能:连接两个字符串,把第二个字符串连接到第一个字符串的后面,结果放在字符数组1中。该函数返回值是字符数组1的起始地址。例如: char destination25= “C+“; char Borland8 = “Borland“; strcat(destination, Borland); printf(“%sn“, destination); 输出: C+ Borland,说明: 字符数组1必须足够大,否则出错。 连接前,两个字符串均以“0”结束;连接后,字符串1的“0”被去掉,新字符串最后加“0”如图所示。 连接前 destination C+000000 00Borland Borland0连接后destination的内容 C+Borland03. strcpy(字符数组1,字符串2) 字符串拷贝函数,功能: 将字符串2拷贝到字符数组1中。该函数返回值是字符数组1的起始地址。 例5.10 void main() char string10,str1= “abcdefghi“; strcpy(string, str1); printf(“%sn“, string,输出: abcdefghi 说明: 字符数组1的长度必须足够长,能够容纳复制过来的字符串。否则出错。 字符数组1必须写成数组名形式(如string),字符串2可以是字符数组名,也可以是一个字符串常量。例如: strcpy(string, “abcdefghi“); 复制时,连同结束标志“0”一起复制。 不能用赋值运算符“=”将一个字符串直接赋值给一个字符数组,只能用strcpy( )函数来处理。例如: char str120,str220; str1=“Hello!“; str2=str1;,上面两种赋值方法均不正确,应改为: strcpy (str1, “Hello!“); strcpy (str2, str1); 在C语言中,数组的名字代表数组的首地址,是一个地址常量,即代表该数组的第一个元素的地址。然后依次存放该数组的后序元素,所以本程序中的赋值语句str=“ Hello!“是错误的,它表示把一个字符串赋给了一个常量。, 用strcpy( )函数将字符串2中的前面若干字符复制到字符数组中。 例5.11 #include “conio.h” #include “stdio.h” void main() char string10,str1= “abcdefghi“; strncpy(string, str1, 3); string3 = 0; printf(“%sn“, string); getch (); ,4. strcmp(字符串1,字符串2) 字符串比较函数 功能:比较两个字符串。对两字符串从左向右逐个字符比较(按ASCII码值大小比较),直到遇到不同字符或“0”为止。如全部字符相同,则字符串1和字符串2相等;若出现不相同的字符,则以第一个不相同的字符比较结果作为整个字符串比较的结果。例如:“computer“compare“,“A“C“等。 比较的结果用函数的返回值表示。若字符串1字符串2,则函数返回0;若字符串1字符串2,则返回-1;若字符串1字符串2,则返回1。,例5.12 #include “string.h” void main() char buf1 = “aaa“, buf2 = “bbb“, buf3 = “ccc“; int ptr; ptr = strcmp(buf2, buf1); if (ptr 0) printf(“buffer 2 is greater than buffer 1n“); else printf(“buffer 2 is less than buffer 1n“);,ptr = strcmp(buf2, buf3); if (ptr 0) printf(“buffer 2 is greater than buffer 3n“); else printf(“buffer 2 is less than buffer 3n“); 输出: buffer 2 is greater than buffer 1 buffer 2 is less than buffer 3,说明: 两个字符数组不能直接比较大小,应使用strcmp()函数。例如: if(str1str2) printf(“1”);是不正确的,应改为: if(strcmp(str1,str2)0) printf(“1“); 5. strlen(字符数组) 测试字符串长度函数 功能:统计字符串中字符的个数。返回字符数组中包含的字符串的实际长度,不包括“0”在内。,例5.13 #include “string.h” void main() char s =“tv0willn“; printf(“%dn“, strlen(s); 输出:3,6. strlwr(字符串) 字符串小写函数 功能:将字符串中的大写字母转换成小写字母。 7. strupr(字符串) 字符串大写函数 功能:将字符串中的小写字母转换成大写字母。 以上介绍的几种常用的字符串处理函数都是C语言所提供的库函数,不需要用户再来编写这些函数,但这些库函数的说明都包含在头文件string.h中,如果要在程序中使用这些库函数,则需在程序的开头加入:#include 初学者需要注意:应牢固掌握以上这些函数的功能和用法,并学会自己动手编写这些函数。,5.3.4 字符数组的举例,本例的程序如下: #include #include void main() char s120,s220,ch1,ch2; int m; printf(“String:“); gets(s1);,printf(“Old,New char is:“); scanf(“%c,%c“, ,本程序的执行结果如下: String:even Old,New char is:n,r End String:ever,例5.15 判定一个字符串是否是另一个字符串的子串的程序。 本例的程序如下: #include #include void main() int m,n,k,index=0; char s120,s220; printf(“String:“); gets(s1); printf(“Sub String:“); gets(s2);,for(m=0;s1m!=0;m+) for(

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论