CHINAUNIVERSITYOFPETROLEUM(华东)第8章数组主讲教师:孙运雷计算机与通信工程学院计算机科学系sunyunlei@upc.edu.cn18853283536输入理想的程序,输出快乐的人生回顾•基本数据类型:int,float/double,char•数据的处理:根据问题需求,先作几个简单变量的定义,然后对这些变量赋值并作相应的运算即得结果•例如:输入10个实数,求其平均值。#includestdio.hintmain(){inti;floatnum,sum=0;printf(input10numbers:\n);for(i=1;i=10;i++){scanf(%f,&num);sum+=num;}printf(average=%.2f\n,sum/10.);return0;}各变量独立存储,之间没有任何关系不需要也不可能保留变量的历史值输入理想的程序,输出快乐的人生问题的提出•一个人n门课的成绩怎样存储和处理?•一个班n门课的成绩怎样存储和处理?•如何从键盘输入100个数然后按相反顺序输出?•输入10个数,将高于平均值的数输出?•......这些数据的特点:1.具有相同的数据类型2.使用过程中需要保留原始数据为了方便的使用这些数据,C语言提供了一种构造数据类型:数组。一定要理解并用好数组!输入理想的程序,输出快乐的人生本章主要内容C语言中数组的概念一维数组二维数组数组作为函数参数传递的方法用数组实现常用的算法输入理想的程序,输出快乐的人生C语言中的数组•数组是具有相同类型的数据的顺序集合•数组可以在内存中连续存储多个元素Rate1.53.20.0945.39870123下标标明了元素在数组中的位置,从0开始数组元素下标Rate[0]Rate[1]Rate[2]Rate[3]输入理想的程序,输出快乐的人生数组类型输入理想的程序,输出快乐的人生本章主要内容C语言中数组的概念一维数组二维数组数组作为函数参数传递的方法用数组实现常用的算法输入理想的程序,输出快乐的人生定义一维数组datatypearrayName[size];类型说明符int、char、float…数组名常量表达式:数组大小intnum[50];charlist_of_initials[20];doublepressure_level[6];#defineLIMIT20...intemp_codes[LIMIT];数组和变量一样,必须先定义后使用;数组大小定义好后,将不能改变;数组大小最好用宏来定义,以适应未来可能的变化输入理想的程序,输出快乐的人生定义一维数组•C89:定义数组时不能使用变量定义数组的大小,即使在此之前变量已经赋值,只能使用整形常量定义数组的大小•C99:允许用变量定义数组的大小intarray(10);intn=5;floatscore[n];intn;scanf(%d,&n);intdata[n];charstr[];floatchar[10];输入理想的程序,输出快乐的人生一维数组在内存的存放数组下标从0开始数组元素在内存中按顺序连续存放数组名代表数组的首地址,即score的值与score[0]的地址值相同内存score数组高地址低地址12345score[0]score[1]score[2]score[3]score[4]数组元素序号intscore[5];score输入理想的程序,输出快乐的人生数组元素的引用——数组元素就是变量C语言中,不允许引用数组进行运算,只能引用数组元素基本形式:数组名[下标表达式];说明:下标表达式的值必须为整型下标从0开始,最大下标为数组长度减1[]是下标运算符,引用数组元素时根据数组首地址和下标计算出该元素的实际地址,然后取出该地址的内容如引用score[2]:1.计算2000+2*4=20082.取出地址2008的内容87907786score[0]score[1]score[2]score[3]2000H2004H2008H200CH例如:inta[5];a[0]=20;a[4]=2*a[0];输入理想的程序,输出快乐的人生下标越界是大忌!•inta[10];scanf(%d,&a[10]);/*下标越界*/–编译程序不检查是否越界–下标越界,将访问数组以外的空间,可能带来严重后果#includestdio.hintmain(){inta=1,c=2,b[5]={0},i;printf(%p,%p,%p\n,b,&c,&a);for(i=0;i=8;i++){b[i]=i;printf(%d,b[i]);}printf(\nc=%d,a=%d,i=%d\n,c,a,i);return0;}b[0]b[1]b[2]b[3]b[4]caib[8]1234560784044484c5054585c6064686c9运行程序或单步执行观察变量变化情况可以看到,变量c和a的值因数组越界而被悄悄破坏了输入理想的程序,输出快乐的人生一维数组的初始化•初始化:在定义数组时给数组元素赋初值–形式:数据类型数组名称[数组长度]={数值列表}•在定义数组时,对全部数组元素赋初值:–例如:inta[5]={0,1,2,3,4};•此时也可省略数组长度–例如:inta[]={0,1,2,3,4};//只写inta[];是错误的•在定义数组时,对部分数组元素赋初值:–例如:inta[5]={0,1,2};//数组其余元素自动赋0•当初值的个数多于数组元素个数时,编译出错–例如:inta[5]={0,1,2,3,4,5};输入理想的程序,输出快乐的人生只能逐个对数组元素进行操作(字符数组例外)一般一维数组的处理用一重循环来实现,用循环变量的值对应数组元素的下标动态赋值方法:inta[10],i;输入第3个数组元素:scanf(%d,&a[2]);输入整个数组元素:for(i=0;i10;i++)scanf(%d,&a[i]);输出方法:输出第1个数组元素:printf(%d,a[0]);输出整个数组元素:for(i=0;i10;i++)printf(%d,a[i]);一维数组的动态赋值和输出输入理想的程序,输出快乐的人生一维数组示例【例1】输入10个整数,输出它们的和,并逆序打印这些数#includestdio.h#defineN10//数组程序推荐该用法intmain(){inti,sum=0,data[N];for(i=0;iN;i++){scanf(%d,&data[i]);sum=sum+data[i];}printf(Sum=%d\n,sum);for(i=N-1;i=0;i--)printf(%d,data[i]);printf(\n);return0;}输入理想的程序,输出快乐的人生一维数组示例【例2】用数组来求Fibonacci数列前20项#includestdio.h#defineN20intmain(){inti,f[N]={1,1};for(i=2;iN;i++)f[i]=f[i-2]+f[i-1];for(i=0;iN;i++){if(i%4==0)printf(\n);printf(%6d,f[i]);}printf(\n);return0;}1(n=1)Fn=1(n=2)Fn-2+Fn-1(n≥3)Fibonacci数列:1,1,2,3,5,8,13,21,34…输入理想的程序,输出快乐的人生总结理解:C语言中的数组•数组是一组相同类型的数据组成的有限集合•数组是可以在内存中连续存储多个元素的结构•数组中的数据称为数组元素,数组元素个数称为数组长度•数组元素用数组名和元素下标表示,如score[0],score[1]score859377880123score[4]数组名(首地址)下标标明了元素在数组中的位置,从0开始数组元素下标数组大小输入理想的程序,输出快乐的人生本章主要内容C语言中数组的概念一维数组二维数组数组作为函数参数传递的方法用数组实现常用的算法输入理想的程序,输出快乐的人生二维数组的定义—思考为何需要二维数组?intnum[4][2];4X2=8数据类型数组名[常量表达式1][常量表达式2];为了便于理解,二维数组一般理解为几行几列的矩阵数据类型数组名[行大小][列大小];num[0][0]num[0][1]num[1][0]num[1][1]num[2][0]num[2][1]num[3][0]num[3][1]错误的定义:inta[3,4],b(3,4);intc[][],d(3)(4);输入理想的程序,输出快乐的人生二维数组的存储结构—思考该如何存?inta[2][3];a[0]a[1]a[1][0]a[1][1]a[1][2]a[0][0]a[0][1]a[0][2]二维数组元素在内存中的存放顺序:先按行存放,再按列存放,即先顺序存放第0行的元素再存放第1行的元素,…a[0][0]a[0][1]a[0][2]a[1][0]a[1][1]a[1][2]输入理想的程序,输出快乐的人生二维数组元素的引用•二维数组元素的引用形式:•例如:inta[3][4];a[0][0]=3;a[0][1]=a[0][0]+10;a[3][4]=5;/*下标越界*/数组名[行下标][列下标];输入理想的程序,输出快乐的人生二维数组的初始化按行赋初值:例如:inta[2][3]={{1,2,3},{4,5,6}};inta[2][3]={{1},{4,5}};按数组元素存放顺序赋初值:例如:inta[2][3]={1,2,3,4,5,6};inta[2][3]={1,2,3};省略行数(根据初值个数和列声明自动确定行数)例如:intb[][3]={1,2,3,4,5,6,7,8,9,10};intc[][3]={{1,2},{3}};1234561230001004504行120300输入理想的程序,输出快乐的人生二维数组的初始化•下列二维数组的定义都是错误的:inta[][],b[3][],c[][2];intarr[2][]={{1,2,3},{4,5,6}};intb[2][3]={1,2,3,4,5,6,7,8};输入理想的程序,输出快乐的人生二维数组值的输入和输出一般二维数组的处理用二重循环来实现,用循环变量的值控制数组元素的下标inta[3][4],i,j;输入方法:输入第i行第j列元素的值:scanf(“%d”,&a[i][j]);输入整个数组元素:for(i=0;i3;i++)for(j=0;j4;j++)scanf(“%d”,&a[i][j]);输出方法:输出第i行第j列元素的值:printf(“%d“,a[i][j]);输出整个数组元素:for(i=0;i3;i++)for(j=0;j4;j++)printf(“%d”,a[i][j]);输入理想的程序,输出快乐的人生二维数组的输入和输出为一个3行4列的二维数组输入/输出数据intmain(){inta[3][4],i,j;for(i=0;i3;i++)for(j=0;j4;j++)scanf(“%d”,&a[i][j]);for(i=0;i3;i++){for(j=0;j4;j++)printf(“%5d”,a[i][j]);printf(“\n”);}return0;}输入理想的程序,输出快乐的人生二维数组示例•【例3】将二维数组a转置存到二维数组b中654321a635241ba[0][1]b[1][0]a[1][2]b[2][1]设行下标为i,列下标为j,则:b[j][i]=a[i][j]输入理想的程序,输出快乐的人生【例3】将二维数组a转置存到二维数组b中#includestdio.hintmain(){inta[2][3]={{1,2,3},{4,5,6}},b[3][2],i,j;printf(数组a:\n);for(i=0;i2;i++){for(j=0;j3;j++)prin