




版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
第8章指针编辑ppt学习目标理解内存单元的双重属性指针的使用指针与数组的关系指针与函数的关系2编辑ppt…3000300130023006内存030033004300530073008…8.1指针概述变量与地址程序中:intx;
int*p;x=5;内存中每个字节有一个编号——地址
xp
编译或函数调用时为其分配内存单元名称类型地址值xint3000随机pint*3004随机553编辑ppt直接访问与间接访问直接访问:按变量地址存取变量值间接访问:通过存放变量地址的变量去访问变量…3000300130023006内存030033004300530073008…程序中:intx;
int*p;x=5;p=&x;*p=30;
5p
编译或函数调用时为其分配内存单元名称类型地址……iint3000pint*30043000——直接访问——间接访问304编辑pptAB5编辑pptAB6编辑ppt直接访问是用简单变量来访问内存单元的地址间接访问是通过存放简单变量地址(指针)的变量去访问内存单元的地址结论7编辑ppt…3000300130023006内存030033004300530073008…程序中:intx;
int*p;x=5;p=&x;*p=30;
3000308编辑ppt-9-main(){inta,*p;a=10;p=&a;printf("a:%d\n",a);printf("p:%x\n",p);}运行结果:a:10p:ffcc…...…...ffccffd4ffd8ffd6a10
pffceffd0ffd2ffcc例
9编辑ppt为什么引入指针的概念指针的主要应用:指针作形参可以在子函数中修改实参变量的值利用指针作形参可以使子函数有多于一个的返回值利用指针可以实现动态分配内存利用指针可以实现动态数据结构(链表、队列、堆栈、树等)的操作指针可以改善某些函数的效率10编辑ppt【例8-1】编写一个的子程序,子程序的功能为交换两个变量的值#include"stdio.h"voidswap(intx,inty);voidmain(void){ inta,b; printf("请输入交换的数值:"); scanf("%d%d",&a,&b); printf("交换前a=%d,b=%d\n",a,b); swap(a,b); printf("交换后a=%d,b=%d\n",a,b);}voidswap(intx,inty){inttemp;temp=x;x=y;y=temp;}ab××××35xy3553调用前调用时调用结束单向值传递11编辑ppt参数传递方式单向值传递形参是变量,实参可以是常量、变量或表达式。形参与实参占用不同的内存单元。单向值传递(形参的改变并不影响实参)。地址传递形式参数为指针变量,实际参数为变量的地址。形参指向实参。12编辑ppt【例8-1】编写一个的子程序,子程序的功能为交换两个变量的值(改进)#include<stdio.h>voidswap(int*x,int*y);voidmain(){inta,b;scanf("%d%d",&a,&b);printf("&a=%x,&b=%x\n",&a,&b);printf("调用前:a=%d,b=%d\n",a,b);swap(&a,&b);printf("调用后:a=%d,b=%d\n",a,b);}地址传递13编辑pptvoidswap(int*x,int*y){ intt;printf("\n-----swap-----\n");
printf("x=%x,y=%x\n",x,y);
t=*x;*x=*y;*y=t;printf("-----swap-----\n\n");}14编辑ppt…13ff76内存13ff7813ff7a13ff7c…35&a=13ff7c,&b=13ff78调用前:a=3,b=5
-----swap-----x=13ff7c,y=13ff78-----swap-----
调用后:a=5,b=313ff8213ff8413ff8613fe88abxy&a13ff7c&b13ff7835t:#include<stdio.h>voidswap(int*x,int*y);voidmain(){inta,b;scanf("%d%d",&a,&b);printf(("…",&a,&b);printf("调用前:…",a,b);swap(&a,&b);printf("调用后:…",a,b);}voidswap(int*x,int*y){ intt;printf("\n-swap-\n“);printf("…",x,y);t=*x;*x=*y;*y=t;printf("-swap-"y);}15编辑ppt说明在该例题中,我们利用指针作形参实现了修改实参变量的值。16编辑ppt8.2指针基础指针变量的说明数据类型*指针变量名;17编辑ppt注意int*p1,*p2;
与int*p1,p2;指针变量只能指向定义时所规定类型的变量不能将一个常数值赋给指针变量;
但可以将NULL或者0赋值给指针变量指针变量定义后,变量值不确定,使用前必须先赋值int*p1,*p2,*p;float*q;q=p;p=3000;p=0;18编辑ppt指针运算符
&——取变量或存储单元的地址*——
取指针所指向的单元(变量)结论:*pt相当于a(*pt)++相当于a++&*pt=&a=pt*&a=*pt=a
&aapt*pta=1;例:inta,*pt;pt=&a;*pt=1;19编辑ppt指针变量的初始化一般形式数据类型*指针名=初始地址值;例
inti; int*p=&i;20编辑ppt例
main(){inti=10;int*p;
*p=20;printf(“%d”,*p);}例
main(){inti=10;int*p;p=&i;*p=20;printf(“%d”,*p);}指针变量必须先赋值,再使用…...…...20002008整型变量i10指针变量p2004随机危险!*p21编辑ppt-22-main(){intx,*px;
px=&x;
x=8;*px*=2;
printf(“%d\t%d\n”,x,*px);
}xpx&x8运行结果为:161616例读程序,写结果。22编辑ppt8.3指针编程实例【例8-3】求一元二次方程ax2+bx+c=0(a≠0)的根,根据数学知识,我们知道一元二次方程ax2+bx+c=0(a≠0)的求解,取决于判别式b2-4ac是否大于,等于或小于零23编辑ppt#include<stdio.h>#include<math.h>intsolvroot(floata,floatb,floatc,float*r1,float*r2);voidmain(){floata,b,c,t1,t2;intflag;printf("Inputparametersa,b,c:\n");scanf("%f,%f,%f",&a,&b,&c);24编辑ppt
flag=solvroot(a,b,c,&t1,&t2);
if(flag>0)printf("Tworealsolutions:x1=%f,x2=%f\n",t1+t2,t1-t2);elseif(flag==0)printf("Onesolution:x1=x2=%f\n",t1);elseprintf("Twocomplexsolutions:x1=%f+%fi,x2=%f-%fi\n",t1,t2,t1,t2);}25编辑pptintsolvroot(floata,floatb,floatc,float*r1,float*r2){floatdelta;
*r1=-b/(2*a);delta=b*b-4*a*c;if(delta>=0)
*r2=sqrt(delta)/(2*a);else
*r2=sqrt(-delta)/(2*a); return(int)delta;}26编辑ppt说明在该例题中,我们利用指针作形参实现了子函数有三个的返回值。子函数通过返回值返回(int)delta的值,通过形参*r1、*r2与实参&t1、&t2结合返回另外两个值27编辑ppt8.4指针型函数函数定义形式:类型标识符*函数名([形参列表]){[函数体]}例int*f(int*x,int*y)28编辑ppt【例8-4】利用指针型函数实现求两个数中的最大数#include<stdio.h>int*larger(int*,int*);voidmain(){inta,b,*p;scanf("%d%d",&a,&b);p=larger(&a,&b);printf("较大的数是%d\n",*p);}29编辑pptint*larger(int*x,int*y){ if(*x>*y) returnx; else returny;}30编辑ppt8.5指针与一维数组一、指向数组元素的指针数组元素是内存的一个单元,故指向数组元素的指针变量的性质和指向变量的指针变量是一样的数组名是指针(地址)常量例如:inta[10],
*p;
p=&a[0];p=a;
也可以在定义时对指针赋初值:
inta[10],*
p=&a[0];a[0]a[1]a[2]a[3]a[9]...p&a[0]a31编辑ppt二、通过指针引用数组元素指针的运算指针变量的赋值运算p=&a;p=array;p=&array[i];p1=p;inti,a,*p,*p1;intarray[10];(将变量a地址p)(将数组array首地址p)(将数组元素地址p)(指针变量p值p1)32编辑ppt指针的算术运算pi表示的p向前或向后移动i个元素(i为整型数)p++,p--,p+=i,p-=i等若p1与p2指向同一数组,p1-p2=两指针间元素个数p1+p2无意义例
p指向int型数组,且p=&a[0];
则p+1指向?a[0]a[1]a[2]a[3]a[4]a[5]a[6]a[7]a[8]a[9]a数组例
inta[10];int*p=&a[2];p++;*p=1;例
inta[10];int*p1=&a[2];int*p2=&a[5];则:p2-p1=3;当p指向数组中的元素时,
算术运算才有意义pp+1p+5p+9pp1p21p33编辑ppt指针的关系运算若p1和p2指向同一数组,则
p1<p2表示p1指的元素在前
p1>p2表示p1指的元素在后
p1==p2表示p1与p2指向同一元素若p1与p2不指向同一数组,比较无意义当p1、p2指向数组中的元素时,关系运算才有意义a[0]a[1]a[2]a[3]a[4]a[5]a[6]a[7]a[8]a[9]a数组p1p2p2p1p1p234编辑ppt数组元素表示方法inta[10],*p=a;
则我们要使用数组中第i个元素,可以用如下的方法表示:下标法:a[i],p[i]指针法:如*(a+i),*(p+i)35编辑ppt-36-a[i]*(a+i)p[i]*(p+i)数组元素表示法数组元素地址表示法&a[i]a+i&p[i]p+i36编辑ppt下标法main(){inta[10];i;for(i=0;i<10;i++)scanf("%d",&a[i]);for(i=0;i<10;i++)printf("%d",a[i]);}数组名计算地址法main(){inta[10];i;for(i=0;i<10;i++)scanf("%d",a+i);for(i=0;i<10;i++)
printf("%d",*(a+i));}例:输入输出整型数组a的全部元素。(假有10个元素)指针法main(){inta[10],i,*p;p=&a[0];for(i=0;i<10;i++)scanf("%d",p+i);for(i=0;i<10;i++)
printf("%d",*(p+i));}37编辑ppt-38-inta[]={1,2,3,4,5,6,7,8,9,10},*p=a,i;
数组元素地址的正确表示:
(A)&(a+1)(B)a++(C)&p(D)&p[i]例注意指针变量的运算38编辑ppt-39-main(){inti,*p,a[10];p=a;for(i=0;i<10;i++){
scanf("%d",p);p++;}
for(i=0;i<10;i++)printf("%d",*(p+i));}p=a;ppppppp例:注意指针的当前值pppa987654321010987654321p12345678910-362851–3822–340149141249p39编辑ppt
1.数组名是数组的首地址,p=&a[0]与p=a等价。
2.指针变量可以使本身的值改变,数组名不可以。
p++正确a++不正确
3.指针变量可以指到数组后的内存单元。
4.要注意指针变量的当前值。使用指针变量时应注意的问题:40编辑ppt例
voidmain(){inta[]={5,8,7,6,2,7,3};inty,*p=&a[1];y=(*--p)++;printf(“%d”,y);printf(“%d”,a[0]);}输出:56pp58762730123456a6--p;y=*p;(*p)++;y=*p;--p;(*p)++;--p;*p++;y=*p;指针变量的复杂运算41编辑ppt【例】写一个函数,将包含n个元素的数组进行排序voidmain()/*冒泡*/{intn=10,a[10]={3,2,4,5,6,8,9,25,21,10};inti,j,temp;for(i=0;i<n-1;i++)for(j=0;i<n-i-1;j++)if(a[j]>a[j+1]){temp=a[j];a[j]=a[j+1];a[j+1]=temp;}}voidsort(inta[],intn)a[j]*(a+j)voidsort(int*a,intn)if(*(a+j)>*(a+j+1))
temp=*(a+j);*(a+j)=*(a+j+1);*(a+j+1)=temp;
42编辑pptint*p与inta[10]p——是指针变量
数组名a
——是指针(地址)常量若p=a,则p+i是a[i]的地址(即p+i==&a[i])数组元素的表示方法:下标法和指针法,
即:若p=a,则p[i]a[i]*(p+i)*(a+i)
系统只给p分配能保存一个指针值的内存区(一般4字节);而给a分配4*10字节的内存区形参数组实质上是指针变量,
即:q作为形参时:intq[]
int*q总结一级指针变量与一维数组的关系43编辑ppt二维数组与指针例
inta[3][4];a[0][0]a[0][1]a[0][2]a[0][3]a[1][0]a[1][1]a[1][2]a[1][3]a[2][0]a[2][1]a[2][2]a[2][3]a[2]a[1]a[0]提出问题:a和a[0]一样吗?a+1和a[0]+1一样吗?a每个元素a[i]是由包含4个元素的一维数组组成把二维数组a理解成
由3个元素组成的一维数组44编辑ppt【例8-6】读以下程序,分析运行结果,理解二维数组指针的概念#include<stdio.h>voidmain(){inta[2][2]={1,2,3,4};inti;4545编辑pptfor(i=0;i<2;i++){printf("a+%d=%x",i,a+i);printf("\t*(a+%d)=%x",i,*(a+i));printf("\ta[%d]=%x",i,a[i]);printf("\t*(*(a+%d))=%d\n",i,*(*(a+i)));}for(i=0;i<2;i++){printf("a[0]+%d=%x",i,a[0]+i);printf("\t*(a[0]+%d)=%d\n",i,*(a[0]+i));}}a+0=13ff70*(a+0)=13ff70a[0]=13ff70*(*(a+0))=1a+1=13ff78*(a+1)=13ff78a[1]=13ff78*(*(a+1))=3a[0]+0=13ff70*(a[0]+0)=1a[0]+1=13ff74*(a[0]+1)=246编辑ppt对于二维数组a[2][2],指针常量a和a[0]是不同类型的指针。通过运行结果我们可以看到:数组名a是指针常量,a的比例因子为1行
指向二维数组的第0行;a[0]也是指针常量,比例因子为1个元素
指向二维数组第0行第0个元素47*(a+0)和*(a+1)*(*(a+0))和*(*(a+1))*(a[0]+0)和*(a[0]+1)a[0]+2指向谁呢?a[1][1]有多少表示法呢?*(a[0]+3)、*(a[1]+1)*(*(a+1)+1)例
inta[2][2];a[0][0]a[0][1]a[1][0]a[1][1]a[0]a47编辑ppt例:求二维数组a[3][4]所有元素的和以及平均值。main(){inta[3][4]={1,2,3,4,5,6,7,8,9,10,11,12};inti,sum=0,*p;
p=&a[0][0];
for(i=0;i<12;i++,p++)sum=sum+*p;printf(“sum=%d,aver=%f”,
sum,sum/12.0)}0a[0][0]1a[0][1]2a[0][2]3a[0][3]4a[1][0]5a[1][1]6a[1][2]7a[1][3]8a[2][0]9a[2][1]10a[2][2]11a[2][3]pppppppppppp48编辑ppt8.6指针与数组编程实例【例8-7】数列的中位数是数列中按照数值大小排在中间位置的数。例如:数列1,2,3,4,5的中位数为3。算法:先对数列排序,然后寻找排序序列的中位数。4949编辑ppt#include<stdio.h>voidsort(inta[],intn);voidmain(){intser[100]; inti,num;
printf("Inputlengthofserial:\n");
scanf("%d",&num);
printf("inputserialelements:\n");for(i=0;i<num;i++)scanf("%d",ser+i);
sort(ser,num);printf("Themedianofserialis%d\n",*(ser+num/2));}50编辑pptvoidsort(inta[],intn){inti,temp;int*p;for(i=0;i<n-1;i++)
for(p=a;p<a+n-i-1;p++)if(*p>*(p+1))
{temp=*p; *p=*(p+1); *(p+1)=temp;}}51Inputlengthofserial:5inputserialelements:1-3236715Themedianofserialis2351编辑ppt例编写函数求出二维整型数组中元素的最大值及其下标号#include<stdio.h>#defineM3#defineN2intmaxarray(inta[M][N],intm,intn,int*pmaxi,int*pmaxj);voidmain(){inta[M][N]={1,2,3,4,5,6};intmax,maxi,maxj;max=maxarray(a,M,N,&maxi,&maxj);printf(“a[%d][%d]=%d”,max,maxi,maxj);}52编辑pptintmaxarray(inta[M][N],intm,intn,int*pmaxi,int*pmaxj){inti,j,max=a[0][0];for(i=0;i<m;i++)for(j=0;j<n;j++){if(max<a[i][j]){max=a[i][j];*pmaxi=i;*pmaxj=j;}}returnmax;}53编辑ppt8.7指针与字符串字符串表示形式用字符数组实现main(){charstring[]=“IloveChina!”;printf(“%s\n”,string);printf(“%s\n”,string+7);}stringIstring[0]string[1]lstring[2]ostring[3]vstring[4]estring[5]string[6]Cstring[7]hstring[8]istring[9]nstring[10]astring[11]!string[12]\0string[13]string+7IloveChina!China!54编辑pptmain(){char*cp=“IloveChina!”;printf(“%s\n”,*cp);
printf(“%s\n”,cp);cp+=7;
printf(“%s\n”,cp);}cp用字符指针实现IloveChina!\0cpIIloveChina!China!字符指针初始化:把字符串首地址赋给cpchar*cp;cp=“IloveChina!”;55编辑pptffc0Iffc1loveChina!\0......stringcharstring[20]=“IloveChina!”;char*cp=“IloveChina!”;cp!anihCevolI存放常量的空间aa00aa0056编辑ppt字符型指针变量与字符数组charstr[20];与
char*cp;str由若干元素组成,每个元素放一个字符
cp只是一个指针变量,存放字符串首地址
charstr[20];str=“IloveChina!”;char*cp;cp=“IloveChina!”;str是地址常量;cp是地址变量cp接受键入字符串时,必须先开辟存储空间例charstr[10];scanf(“%s”,str);()而char*cp;scanf(“%s”,cp);()改为:char*cp,str[10];cp=str;scanf(“%s”,cp);()57编辑pptcharstr[]={“Hello!”};charstr[]=“Hello!”;
charstr[]={‘H’,‘e’,‘l’,‘l’,‘o’,‘!’};char*cp=“Hello”;inta[]={1,2,3,4,5};int*p={1,2,3,4,5};charstr[10],*cp;inta[10],*p;str=“Hello”;cp=“Hello!”;a={1,2,3,4,5};p={1,2,3,4,5};分析下列用法正确与否58编辑ppt【例8-8】编写出程序读入矩阵元素,并且利用指针遍历矩阵所有元素,要求输出矩阵和矩阵元素的最大值#include<stdio.h>#include<stdlib.h>voidmain(){inta[10][10];int*p;intnum,max,i;printf("Inputelementofcolumn:\n");scanf("%d",&num);5959编辑pptif(num<1||num>10){printf("Wrongnumber!\n");exit(0);}printf("Inputelementofmatrix:\n");for(i=0;i<num;i++){for(p=a[i];p<=&a[i][num-1];p++)scanf("%d",p);}60编辑pptmax=a[0][0];for(i=0;i<num;i++){for(p=a[i];p<=&a[i][num-1];p++)if(max<*p)max=*p;}for(i=0;i<num;i++){for(p=a[i];p<=&a[i][num-1];p++)printf("%6d",*p);printf("\n");}printf("Themaxelementis%d\n",max);}6161编辑ppt【例8-9】写程序,判断一个单词是否为回文。回文指的是单词按从前到后与从后到前的顺序读都相同,例如“level”就是是一个回文单词。#include<stdio.h>#include<stdlib.h>#defineMAXLEN80voidmain(){char*str; intflag;
intpal(char*); if((str=(char*)
malloc(MAXLEN))==NULL){ printf("Memoryallocationerror!\n");exit(0);} 62编辑pptprintf("Inputaword:\n");scanf("%s",str);while(*str!='#'){flag=pal(str);if(flag)printf("%sisa
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 工作与生活场景下的智能穿戴需求分析
- 工作中的心理调适与健康管理
- 工作中的时间管理与优化
- 工作场所心理健康关注与干预措施
- 工业设备涂装的耐腐蚀性研究
- 工作分析与职位设置
- 工作环境创新与员工工作动力提升
- 工作报告的炫酷动态效果制作
- 工程师必 备的数据分析技能
- 工程质量管理与工程验收标准研究
- 医院电梯安全培训(同名873)课件
- 无人机飞行计划申请表
- 主动脉夹层腔内隔绝术操作规范
- 初三自主招生简历范文自荐信
- 电梯维修报价表格
- 矿区专项边坡治理方案设计
- 国产上海7120手表机芯
- 4配电柜安全风险点告知牌
- 《卖炭翁》中考阅读经典赏析试题(共27题)
- 养老服务礼仪与实务全书ppt完整版课件最全电子教案正本书教学教程
- Q∕GDW 11445-2015 国家电网公司管理信息系统安全基线要求
评论
0/150
提交评论