《第十章 指针.ppt》由会员分享,可在线阅读,更多相关《第十章 指针.ppt(46页珍藏版)》请在淘文阁 - 分享文档赚钱的网站上搜索。
1、第十章 指针第十章第十章 指针指针10.1 指针与地址指针与地址10.2 指针与变量指针与变量10.3 指针与数组指针与数组10.4 指针与字符串指针与字符串10.5 指针与函数指针与函数10.6 指针数组和指向指针的指针指针数组和指向指针的指针第十章 指针10.1 指针与地址指针与地址1.地址:内存区的每一个字节的编号。若有:int a,b;char c;a=3;b=7;c=A;.37A地址200020022004变量名 a b c第十章 指针2.两种访问方式直接访问:通过变量名如:scanf(“%d”,&a);printf(“%d”,a);间接访问:通过一个中间变量 把变量a的地址存放在另
2、一个变量p中,通过变量p来间接访问变量a。3.指针:地址的形象化称谓,用来表示指向关系。4.指针变量:存放地址值的变量,如p。p2000a3第十章 指针10.2 指针与变量指针与变量10.2.1 指针变量的定义指针变量的定义形式:基类型 *指针变量名基类型:表示指针变量可存放哪一类型变量的地址。*:表示该变量为一指针变量。如:int *p;表示定义了一个指针变量p,p只能指向int型的变量,即p只能存放一个int型变量的地址值。第十章 指针10.2.2 指针变量的引用指针变量的引用先定义后使用,使指针变量有一确定的指向(赋初值)。1.两个相关的运算符(1)&:取地址运算符(2)*:指针运算符,
3、取指向。例:int a,*p;/此时的*并非指针运算符 p=&a;/指针变量p指向a *p=3;/*p表示p所指向的量,即apa&a3第十章 指针2.注意:(1)指针变量只能存放地址只能存放地址,不能存放其他非地址类型的数据。如:int a,*p;p=&a;/*对*/p=a;/*错*/(2)指针变量只能存放同一类型变量的地址。如:int a,*p;char c;p=&a;/*对*/p=&c;/*错*/第十章 指针3.直接访问和间接访问若有定义:int a,*p;p=&a;(1)直接访问 scanf(“%d”,&a);printf(“%d”,a);(2)间接访问 scanf(“%d”,p);pr
4、intf(“%d”,*p);形式:scanf(“%d”,指针变量名指针变量名);printf(“%d”,*指针变量名指针变量名);第十章 指针例10.1 通过指针变量访问整型变量 main()int a=10,b=20;int *p,*q;p=&a;q=&b;printf(“%d,%dn”,a,b);printf(“%d,%dn”,*p,*q);结果:10,20 10,20第十章 指针例10.2 利用指针变量交换a和b的值。交换整型变量的值 main()int a=5,b=8;int *p,*q,t;p=&a;q=&b;t=*p;*p=*q;*q=t;printf(“%d,%dn”,a,b);
5、printf(“%d,%dn”,*p,*q);结果:8,5 8,5 pa&a5qb&b8pa&a8qb&b5*p*q第十章 指针交换指针变量的值(地址)main()int a=5,b=8;int *p,*q,*t;p=&a;q=&b;t=p;p=q;q=t;printf(“%d,%dn”,a,b);printf(“%d,%dn”,*p,*q);结果:5,8 8,5 pa&a5qb&b8pa&b5qb&a8第十章 指针4.进一步说明两个运算符优先级:相同结合性:右结合性 若有 int a,*p;p=&a;则:&*p&a p *&a *p a+与*:优先级相同,右结合性 若有 int a,*p;p
6、=&a;则:*p+*(p+):地址值加一 (*p)+a+:变量值加一第十章 指针10.2.3 指针变量作为函数参数指针变量作为函数参数例10.3 交换a和b的值交换整型变量的值 void swap(int *p,int *q)int t;t=*p;*p=*q;*q=t;main()int a=5,b=8;int *p1=&a,*q1=&b;swap(p1,q1);printf(“%d,%dn”,a,b);p1a&a5q1b&b8p1a&a8q1b&b5p&aq&bp&aq&bmain函数swap函数第十章 指针交换指针变量的值 void swap(int *p,int *q)int *t;t=
7、p;p=q;q=t;main()int a=5,b=8;int *p1,*q1;p1=&a;q1=&b;swap(p1,q1);printf(“%d,%dn”,a,b);结果:5,8p1a&a5q1b&b8p1a&a5q1b&b8p&aq&bp&bq&amain函数swap函数第十章 指针结论:用指针变量作为函数参数,在被调函数的执行过程中使指针变量所指向的变量值发生变化,函数调用结束后,这些变量值的变化依然保留下来。这样,就可以在主调函数中使用这些改变了的值。因此,用指针变量作参数,可以得到多个变化了的值。第十章 指针10.3 指针与数组指针与数组10.3.1 指向数组元素的指针指向数组元素
8、的指针用法与指向变量的指针变量相同int a5,*p;p=&a0;等价于 p=a;也可以在定义的同时赋初值 int a5,*p=a;/*先定义数组,再给指针变量赋值*/第十章 指针10.3.2 通过指针引用数组元素通过指针引用数组元素例10.5 输出数组中的全部元素1.下标法main()int a5,j;for(j=0;j5;j+)scanf(“%d”,&aj);for(j=0;j5;j+)printf(“%5d”,aj);第十章 指针2.指针法如*(a+j)或*(p+j),等价于aj。main()int a5,j;for(j=0;j5;j+)scanf(“%d”,&aj);for(j=0;j
9、5;j+)printf(“%5d”,*(a+j);main()int a5,j,*p;for(j=0;j5;j+)scanf(“%d”,&aj);for(p=a;pa+5;p+)printf(“%5d”,*p);第十章 指针3.说明(1)指针变量的值可以改变,但数组首地址不能改变。若有定义:int a5,*p=a;则:p+;/*对*/a+;/*错,因为数组的首地址是一个常量*/(2)注意指针变量的当前值第十章 指针main()int a5,j,*p;p=a;for(j=0;j5;j+,p+)scanf(“%d”,p);p=a;for(j=0;j5;j+,p+)printf(“%5d”,*p);
10、a0a1a2a3a4ppp第十章 指针(3)注意指针变量的运算 p+:指向下一个元素*p+:先取出p所指向的元素的值,然后p指向下一个元素。(*p)+:将p所指向的元素的值加一第十章 指针10.3.3 数组名作函数参数数组名作函数参数四种形式:四种形式:(1)形参和实参都用数组名)形参和实参都用数组名 f(int x,int n)main()int a10;f(a,10);例例10.7第十章 指针实际上,能够接受并存放地址值的只能是指针变量。实际上,能够接受并存放地址值的只能是指针变量。(2)实参用数组名,形参用指针变量。)实参用数组名,形参用指针变量。f(int *x,int n)main(
11、)int a10;f(a,10);将例将例10.7中的形参改为指针变量中的形参改为指针变量第十章 指针(3)实参和形参都用指针变量)实参和形参都用指针变量 f(int *x,int n)main()int a10,*p;p=a;f(p,10);将例将例10.7中的参数改为指针变量中的参数改为指针变量第十章 指针(4)实参用指针变量,形参用数组名)实参用指针变量,形参用数组名 f(int x,int n)main()int a10,*p;p=a;f(p,10);注意:如果用指针变量作实参,必须先使指针变量有注意:如果用指针变量作实参,必须先使指针变量有确定值,指向一个已定义的数组。确定值,指向一
12、个已定义的数组。第十章 指针用第一种形式求解例用第一种形式求解例10.8用第二种形式求解例用第二种形式求解例10.810.3.4 指向多维数组的指针和指针变量指向多维数组的指针和指针变量通过前面的介绍,我们可以得到以下两个结论:(1)一维数组名代表数组的起始地址,是一个指针常量,指向数组的第一个元素。(2)一维数组中任一元素的地址都可以用数组名加上一个偏移量偏移量来表示。有等价关系:a&a0,a+1&a1,a+i&ai *a a0,*(a+1)a1,*(a+i)ai 在C语言中,可以把二维数组解释为以一维数组为元素的一维数组。第十章 指针1.二维数组的地址int a34;a00a01a02a0
13、3a10a11a12a13a20a21a22a23a0a1a2aa0+1*(a+0)+1a1+1a2+1*(a+1)+1*(a+2)+1a+1a+2行指针行指针列指针列指针二维数组元素二维数组元素第十章 指针二维数组元素aij还可以表示为:*(ai+j)和*(*(a+i)+j)。行指针:指向一维数组的指针变量,加一表示加一行,如:a、a+1、a+2 等。列指针:指向二维数组元素的指针变量,加一表示加一列(元素),如:a0和*a、a1+1和*(a+1)+1、a2+2和*(a+2)+2 等。行、列指针的互换:行列前加*列行前加&第十章 指针2.指向二维数组的指针变量(1)列指针:指向数组元素的指针
14、变量定义:与指向变量的指针变量的定义相同。初始化:给出一维数组名(二维数组所包含的)。例10.12 用列指针输出数组元素的值。main()int a34=1,3,5,7,9,11,13,15,17,19,21,23;int *p;for(p=a0;p=a0+11;p+)printf(“%4d”,*p);第十章 指针(2)行指针:指向由m个元素组成的一维数组的指针变量。定义:基类型 (*指针变量名)m;初始化:给出二维数组名。例10.13 输出二维数组任一行任一列元素的值。main()int a34=1,3,5,7,9,11,13,15,17,19,21,23;int (*p)4,i,j;p=a
15、;scanf(“%d,%d”,&i,&j);printf(“%dn”,*(*(p+i)+j);第十章 指针10.4 指针与字符串指针与字符串10.4.1 字符串的表示形式字符串的表示形式1.下标法例例 10.18注意:通过数组名,以%s的格式可以对一个字符串进行整体的输入输出。而对一个数值型数组,则不能企图用数组名输出它的全部元素。如:int a10;printf(“%dn”,a);是不对的,数值型数组只能逐个逐个地输出元素。第十章 指针2.指针法(1)用字符指针指向一个字符串如:char s=“I am happy”;char *p=s;或 char *p=“I am happy”;此时,系
16、统自动为字符串常量开辟存储空间,并将字符串首地址赋给指针变量p。例例10.19第十章 指针10.4.2 字符指针作函数参数字符指针作函数参数用字符指针作函数参数,将一个字符串的首地址从一个函数传递到另一个函数,在被调函数中可以改变字符串的内容,在主函数中可以得到改变了的字符串。1.例例10.202.用字符指针处理例用字符指针处理例10.203.简化简化copy函数函数(1)void copy(char *from,char *to)while(*to=*from)!=0)/*先赋值后判断*/from+;to+;第十章 指针(2)void copy(char *from,char *to)whi
17、le(*to+=*from+)!=0);10.4.3 字符指针变量和字符数组的区别字符指针变量和字符数组的区别1.存放内容 字符数组由多个元素组成,存放若干个字符;而字符指针变量存放的是地址。2.赋值方式(1)在定义的同时 char str=“I am happy”;/*整体赋初值*/char *s=“I am happy”;第十章 指针(2)在赋值语句中 char str20;str0=I;str1=;str2=a;/*只能逐个赋值*/char *s;s=“I am happy”;/*s存放字符串常量的首地址*/3.编译时的处理方式 在编译时,为数组分配一段段内存单元,要为数组元素赋值;为指
18、针变量分配一个个内存单元,要为指针变量赋一地址值,使其有确定的指向。第十章 指针例 main()char a25=“abc”,“defg”;char *p,*s;p=a0;s=a1;while(*p)p+;while(*s)*p+=*s+;printf(“%sn%sn”,a0,a1);结果:abcdefgfg fgfga0cb00defga0a1a0cbdefgfg第十章 指针10.5 函数和指针函数和指针10.5.1 函数的指针和指向函数的指针变量函数的指针和指向函数的指针变量1.定义:数据类型 (*指针变量名)();2.说明:(1)数据类型要与函数返回值的类型一致(2)括号不可省3.使用:
19、(1)只需将函数名赋给指针变量,不必写参数。(2)通过指针变量调用函数,只需用(*指针变量)代替函数名即可。例例 求两个数中的最大值求两个数中的最大值第十章 指针10.5.2 返回指针值的函数返回指针值的函数定义:数据类型 *函数名(参数类型1 参数名1,)与函数的定义相比多了一个*例例10.25区别:int *p();int (*p)();第十章 指针10.6 指针数组和指向指针的指针指针数组和指向指针的指针10.6.1 指针数组指针数组1.概念P248:存放指针的数组。2.定义:数据类型 *数组名常量表达式 只比整型数组的定义多了一个*3.区别:int *p4;int (*p)4;第十章
20、指针4.使用:常用来指向若干个字符串,使字符串的处理更方便灵活。(1)定义的同时整体初始化,赋值语句中逐个赋值。如:char *p=“China”;char *name4=“China”,“Japan”,“USA”,“India”;将各字符串常量的首地址赋值各个指针数组元素。China0Japan0USA0name0name1name2name3India0例例10.27第十章 指针10.6.2 指向指针的指针指向指针的指针1.概念:指向指针数据的指针变量,即存放另一指针型数据的地址。2.定义:基类型 *指针变量名 比指向变量的指针变量多了一个*。3.使用:要将一指针数组名或二维数组名赋值给它
21、,使用方法类似于行指针。第十章 指针例10.28 使用指向指针的指针。main()char *name4=“China”,“Japan”,“USA”,“India”;char *p;int j;for(j=0;j4;j+)p=name+j;printf(“%sn”,*p);China0Japan0USA0nameIndia0第十章 指针例10.29 使用指向指针的指针main()static int a5=1,3,5,7,9;int *num5=&a0,&a1,&a2,&a3,&a4;int *p,j;p=num;for(j=0;j1)argv+;printf(“%sn”,*argv);argc-;若以下输入命令:file1 China Beijing则结果为:China Beijingfile10China0Beijing0argv第十章 指针作业作业(一)作业均要求用指针方法处理1.习题10.12.习题10.33.习题10.44.有一个班4个学生,5门课。要求使用列指针求出第一个学生的平均成绩,用行指针求出第一门课的平均成绩。第十章 指针(二)作业均要求用指针方法处理1.习题10.62.习题10.73.写一函数,用于判断一个串是否为“回文”(顺读和逆读结果相同)。例如:“abcdcba”为回文,“abcdba”不是回文。4.用指向指针的指针的方法将一个字符串逆序输出。
限制150内