C语言指针(含例子).ppt

上传人:xt****7 文档编号:16591424 上传时间:2020-10-17 格式:PPT 页数:70 大小:1.08MB
返回 下载 相关 举报
C语言指针(含例子).ppt_第1页
第1页 / 共70页
C语言指针(含例子).ppt_第2页
第2页 / 共70页
C语言指针(含例子).ppt_第3页
第3页 / 共70页
点击查看更多>>
资源描述
C语言程序设计大赛培训之 指针 教学实践部计算机中心 胡晓丽 指针的用途 指针在 C 语言里应用极为广泛,是 C语言的灵魂 使程序简洁、紧凑、高效 函数调用时批量参数的传递 内存的动态分配 内存地址的直接处理 复杂数据结构的简洁表达 等许多其它数据类型 难以实现的复杂操作 培训目的 掌握指针的概念、指针变量定义格式和引用 掌握指针的运算方法 指针应用举例 理解指针 指针 就是内存中的 变量的地址 理解指针 内存单元的编号:计算机内 存中,每一个字节的存储单 元都有一个编号(亦称为 内 存地址 ) 在 VC中,内存单元的编号是 一个 8位的十六进制数(表示 32位二进制数, VC是 32位编 译系统) 如: 0013FF7C 0013FF7C 0013FF7B 0013FF7A 0013FF79 0013FF00 . 理解指针 变量 : 实质是代表了 “ 内存中的某个存储单元 ” 。 若在内存中定义了一个变量,则这个变量的内存的地址也就确定了。 理解指针 变量的地址 :表示变量在内存中的位置,其 值是该变量在内存中所占存储单元的首字节的编 号 程序中 : int i; float k; 内存中每个字节有一个编号 -地址 . . 2000 2001 2002 2005 内存 0 2003 i k 编译或函数调用时为其分配内存单元 变量 是对程序中数据 存储空间的抽象 理解指针 a在内存中占 4个字节,但 a=8; printf(%d %pn,a, 0013FF7C 00000000 0013FF7B 00000000 0013FF7A 00000000 0013FF79 00001000 0013FF00 . 理解指针 理解指针 我们在程序中只需要指出变量名,无需知道每个变量 在内存中的具体地址,每个变量与具体地址的联系是 由 C编译系统来完成的。对变量的存取操作就是对某 个存储单元进行操作。这种 直接按变量的地址存取变 量值 的方式称为“ 直接存取 ”。 4502 实 验 室 二 我有几种方法 可以到实验室 上机? 2、按实验室所在的 教室编号 1、按实验室名字 按变量名 按变量地址 (即 指针 ) 实 验 室 一 实 验 室 三 4503 4707 理解指针 理解指针 指针 : 也是一种变量,这种变量是用来存放内 存地址的。 指针变量 指针是 字节的编号,即地址。 指针也是要存储的,因此每个指针也需要 一个变量来存储它。这个变量称为指针变 量。指针变量的值是某一定义好的变量的 地址。 理解指针变量 1011 a p 例: int *p; int a=3; 1012 2002 00000011 00000000 间接存取:这种通过变量 p到变量 a的地址, 然后再存取变量 a的值的方式称为“间接存取”。 指针变量 p指向了变量 a的含义是:指针 p中存放了变量 a的地址。 指针变量的定义 定义形式如下: 数据类型 *指针变量名 ; 如: int *p1, num; 表示的意思为: 定义了一个指针变量 p1,它指向的是一个整型数 据。或者说,这时候 p1中存储的是一个整型变量 的地址。 注意:指针变量定义了之后,需要给它赋一个确 定的变量的地址,否则,就会出现严重的系统错 误。 指针变量的引用 #include main() int a; /定义一个整型变量 a int *p1; /定义指向整型变量的指针 p1 p1= /p1中应存放变量 a的地址 *p1=5; /通过指针变量 p1给 a赋值 printf(a=%d, a); 例: int *p,*s,k=20; s= p= . . 2000 2004 2006 2005 整型变量 k 变量 s 2001 2002 2003 变量 p 2007 2008 20 2000 2004 s=*p k=*s 所以: k=*p 说明: ( 1)指针 p的基类型是 int 类型的指针。 ( 2)是求地址运算符。 ( 3)因为基本数据类型 int、 float、 char等所需存储 空间不同,所以需要定 义指针变量的基类型。 例 : 指针的概念 main() int a; int *pa= a=10; printf(a:%dn,a); printf(*pa:%dn,*pa); printf( printf(pa:%x(hex)n,pa); printf( 运行结果: a:10 *pa:10 DD00 q=p+2; DD04 q+; 6 q-; DD04 i=*p; 11 j=*q; 33 例: 指针的运算方法 指针的比较 在关系表达式中,可以对指针进行比较。即两 个变量地址的比较。 通常两个或多个指针指向同一目标时(一串连 续的存储单元),比较才有意义。 指针应用举例 -指针作为函数的参数 指针可以作为参数在主调函数和被调用函数之间 传递数据,通过指针可以在被调用函数中地调用 中的变量进行引用,这也就使得通过形参改变对 应实参的值有了可能,利用此形式就可以把两个 或两个以上的数据从被调用的函数返回到调用函数。 例 将数从大到小输出 指针应用举例 -指针作为函数的参数 swap(int x,int y) int temp; temp=x; x=y; y=temp; main() int a,b; scanf(%d,%d, if(ab) swap(a,b); printf(n%d,%dn,a,b); 指针应用举例 -指针作为函数的参数 . . 2000 2008 200A 2002 2004 2006 5 变量 a 变量 b (main) 9 变量 temp 变量 y 变量 x (swap) 5 5 9 5 9 COPY swap(int x,int y) int temp; temp=x; x=y; y=temp; main() int a,b; scanf(%d,%d, if(ab) swap(a,b); printf(n%d,%dn,a,b); 指针应用举例 -指针作为函数的参数 swap(int x,int y) int temp; temp=x; x=y; y=temp; main() int a,b; scanf(%d,%d, if(ab) swap(a,b); printf(n%d,%dn,a,b); 值传递 . . 2000 2008 200A 2002 2004 2006 5 变量 a 变量 b (main) 9 运行结果: 5, 9 变量 x 变量 y (swap) 变量 t 5 9 5 9 5 swap(int *p1, int *p2) int p; p=*p1; *p1=*p2; *p2=p; main() int a,b; int *pointer_1,*pointer_2; scanf(%d,%d, pointer_1= pointer_2= if(ab)swap(pointer_1,pointer_2); printf(n%d,%dn,a,b); . 2000 2008 200A 2002 2004 2006 200C 200E 2010 . 5 9 整型变量 a 整型变量 b (main) 指针 pointer_1 指针 pointer_2 2000 2002 (swap) 指针 p1 指针 p2 整型 p 5 9 2000 2002 COPY 5 运行结果: 9, 5 地址传递 通过传送地址值,可以在被调用函数中直接改变调用函数中的变量的值 指针应用举例 -指针作为函数的参数 指针应用举例 -指向数组的指针变量 例编写程序,定义一个含有 15个元素的数组,并编 写函数分别完成以下操作: ( 1)调用 C库函数中的随机函数给所有元素赋以 0 49之间的随机数; ( 2)输出数组元素中的值; ( 3)按顺序对每隔三个数求一个和数,并传回主函 数; ( 4)最后输出所有求出的和值。 指针应用举例 -指向数组的指针变量 调用随机函数的方法如下:包含头文件 stdlib.h n=rand()%x; n将得到一个在 0( x-1)之间的随机数。 指针应用举例 -指向数组的指针变量 分析: ( 1)由于要每隔 3个数求一个和, 15个数要求 出 5个和,所以主函数中要定义一个数组来存 放 5个和数。 ( 2)两次输出元素的值,虽然输出对象不同, 但是数组的类型相同,可调用一个函数来完成, 只要指定不同的数组名,不同的输出个数即可。 指针应用举例 -指向数组的指针变量 #include stdio.h #include stdlib.h #define SIZE 15 #define N 3 void getrand(int *,int); void getave(int *,int *,int); void printarr(int *,int); 指针应用举例 -指向数组的指针变量 void printarr(int *a,int n) int i; for(i=0;in;i+) printf(%4d, *(a+i); if(i+1)%5=0) printf(n); printf(n); 指针应用举例 -指向数组的指针变量 void getave(int *a,int *b,int n) int i,j=0,sum=0; for(i=0;in;i+) sum+=*(a+i); /*累加数组元素 */ if(i+1)%3=0) /*每累加 3个进行一次处理 */ bj=sum;sum=0;j+; 指针应用举例 -指向数组的指针变量 void getrand(int *a,int n) int i; for(i=0;in;i+) *(a+i)=rand()%50; 指针应用举例 -指向数组的指针变量 main() int xSIZE,wSIZE/N=0; /*数组中置初值为 0,准备存放 5个数的和 */ clrscr(); getrand(x,SIZE); /*调用函数产生 15个随机数放入数组 x中 */ printf(nOutput %d random numbers:n ,SIZE); printarr(x,SIZE); /*输出 15个随机数 */ getave(x,w,SIZE); /*每 3个数求一个和放入数组 w中 */ printf(nOutput 5 sum numbers:n); printarr(w,SIZE/N); /*输出 5个数的和 */ 指针应用举例 -指向数组的指针变量 指针应用举例 -指向数组的指针变量 例:编写程序,将数组中的数按颠倒的顺序重 新存放。在操作时,只能借助一个临时存储单 元而不得另外开辟数组。 分析:不是要求按颠倒的顺序打印数据,而是要 求按逆序重新放置数组中的内容。假定 a数组中 有 8个元素 指针应用举例 -指向数组的指针变量 10 20 30 40 50 60 70 80 1001 1003 1005 1007 1009 100B 100D 100F a0 a1 a2 a3 a4 a5 a6 a7 80 70 60 50 40 30 20 10 1001 1003 1005 1007 1009 100B 100D 100F a0 a1 a2 a3 a4 a5 a6 a7 指针应用举例 -指向数组的指针变量 ( 1)定义两个变量 i和 j, 首先将 a0,a7进行对调, 中间 用到一个临时存储单元,所以定义同类型变量 temp。 ( 2)将变量 i加 1,j减 1,满足条件 ij时,将 a1和 a6进行 对调 ( 3)最后将 a3和 a4进行对调,此时 i+1,j-1不再满足条 件 ij 指针应用举例 -指向数组的指针变量 #include stdio.h #define NUM 8 void invert(int *,int); void priout(int *,int); main() int aNUM=10,20,30,40,50,60,70,80; printf(nOutput primary data: ); priout(a,NUM); invert(a,NUM); printf(nOutput the inverse data: ); priout(a,NUM); 指针应用举例 -指向数组的指针变量 void priout(int s,int n) int i; for(i=0;in;i+) printf(%4d,si); printf(n); void invert(int *a,int n) int i,j,temp; for(i=0,j=n-1;ij;i+,j-) temp=*(a+i); *(a+i)=*(a+j); *(a+j)=temp; 指针应用举例 -指向数组的指针变量 例: w数组中存放了 n个数据,编写函数删除下标为 k 的元素的值。 指针应用举例 -指向数组的指针变量 21 22 23 24 25 26 27 28 29 30 1001 1003 1005 1007 1009 a0 a1 a2 a3 a4 a5 a6 a7 a8 a9 k 21 22 23 24 26 27 28 29 30 30* 1001 1003 1005 1007 1009 a0 a1 a2 a3 a4 a5 a6 a7 a8 a9 指针应用举例 -指向数组的指针变量 getindex:用于输入所删除元素的下标,函数中对 输入的下标进行检查,若越界,则要求重新输入, 直到正确为止。 arrout:用于输出数组中的元素 arrdel:进行所要求的删除操作 指针应用举例 -指向数组的指针变量 #include stdio.h #define NUM 10 int arrdel(int *,int,int); void arrout(int *,int); int getindex(int n); 指针应用举例 -指向数组的指针变量 main() int n,d,aNUM=21,22,23,24,25,26,27,28,29,30; n=NUM; printf(Output primary data: n); arrout(a,n); d=getindex(n); n=arrdel(a,n,d); printf(nOutput the data after delete:n); arrout(a,n); 指针应用举例 -指向数组的指针变量 getindex(int n) int p; do printf(nEnter the index 0=p%d:,n); scanf(%d, while(pn-1); return p; void arrout(int w,int m) int k; for(k=0;km;k+) printf(%5d,wk); printf(n); 指针应用举例 -指向数组的指针变量 int arrdel(int *a,int n,int k) int i; for(i=k;in-1;i+) ai=ai+1; n-; return n; 指针应用举例 -指针指向字符串 例:编写函数 strlength(*s),函数返回指针 s所 指字符串的长度。 相当于库函数 strlen的功能。 指针应用举例 -指针指向字符串 #include stdio.h #include string.h int strlength(char *s) int n=0; while(*(s+n)!=0) n+; return n; main() char str=ABCDEF; int len1,len2; len1=strlength(); len2=strlength(str); printf(len1=%d,len2=%d,len1,len2); 指针应用举例 -指针指向字符串 例:编写程序从若干字符串中找出最小的串进行输出。 #include stdio.h #include string.h #define N 20 #define M 81 指针应用举例 -指针指向字符串 int getstr(char pM) char tM; /*开辟一个临时的字符串存储空间 */ int n=0; printf(Enter string. a empty string to end.n); gets(t); while(strcmp(t,) strcpy(pn,t);n+; gets(t); return n; 指针应用举例 -指针指向字符串 char *findmin(char (*a)M,int n) char *q; int i; q=a0; /*用 q指向字符串数组中最小串的地址 */ for(i=0;i0) q=ai; return q; 指针应用举例 -指针指向字符串 main() char sNM,*sp; int n; n=getstr(s); sp=findmin(s,n); puts(sp); 指针应用举例 -函数指针 指向函数的指针变量的定义 #include “stdio.h” double fun(int a,int *p) main() double (*fp)(int ,int *),y; int n; fp=fun; y=(*fp)(56, double tran(double (*f1)(double),double (*f2)(double),double x) return (*f1)(x)/(*f2)(x); 指针应用举例 -函数指针 main() double y,v; v=60*3.1416/180.0; /*v=600*/ y=tran(sin,cos,v); printf(“tan(60)=%10.6fn”,y); y=tran(cos,sin,v); printf(“cos(60)=%10.6fn”,y); 指针应用举例 -动态存储分配 例: short int *pi; float *pf; pi=(short *)malloc(2); pf=(float *)malloc(4); 说明: ( 1)因为 malloc是 void型的,所以需要强制转换类型 ( 2)强制转换类型括号中的不可少,否则就变成了 普通类型。 if(pi!=NULL) *p=6; if(pf!=NULL) *pf=3.8 6 3.8 pi pf 指针应用举例 -动态存储分配 注意: 由动态存储分配得到的存储单元没有名字,只能 靠指针来引用它。一旦指针改变指向,则原存储 单元及所存数据都将无法引用。 通过调用 malloc函数所分配的单元动态存储单元 中没有确定的初值。 在动态申请存储空间时,若不能确定数据类型所 占字节数,可通过 sizeof运算符来求得。 指针应用举例 -动态存储分配 例: pi=(int *)malloc(sizeof(int); pf=(float *)malloc(sizeof(float); 由系统来计算指定类型所占的字节数,有利于程序 的移植。 指针应用举例 -链表 单链表 struct slist int data; struct slist *next; ; typedef struct slist SLIST; / 0 head 指针应用举例 -链表 ( 1)建立带有头结点的单向链表 步骤: 读取数据 生成新结点 将数据存入结点的成员变量中 将新结点插入到链表中。 (重复操作直到输入结束)。 指针应用举例 -链表 例:编写函数 creat_slist,建立如上图所求的单向链表。结点数据域的内 容从键盘输入,以 -1作为输入结束标志。链表头结点的地址由函数值 返回。 h:头指针,存放头结点的地址 r:指向链表当前的尾结点 s:指向新生成的结点 每当 s把新开辟的结点链接到链表尾后, r便移向这一新的表尾结点。 #include stdio.h #include stdlib.h struct node int data; struct node *next; ; typedef struct node SLIST; main() SLIST *head; . head=return creat_slist(); /*调用链表建立函数,得到头结点地址 */ SLIST *creat_slist() SLIST *h,*s,*r; int c; h=(SLIST*)malloc(sizeof(SLIST); /*生成头结点 */ r=h; scanf(%d, while(c!=-1) s=(SLIST *)malloc(sizeof(SLIST); /*生成新结点 */ r-data =c; r-next =s; r=s; /*使 r指向当前表尾 */ scanf(%d, r-next =0; /*置链表结束标志 */ return h; 0 head h-next=0 指针应用举例 -链表 ( 1)顺序访问链表中各结点的数据域 步骤: 指向指向一个结点 输出数据域的内容(重复上面两步) 直到链表结束为止。数据域内容为 0 例:编写函数 print_slist,顺序输出单向链表各结点 数据域中的内容。 指针应用举例 -链表 指针应用举例 -链表 void print_slist(SLIST *head) SLIST *p; p=head-next ; /*p指向头结点后的第一个结点 */ if(p=0) printf(Linklist is NULL!n); else printf(head); do printf(-%d,p-data ); /*输出当前结点数据域中的值 */ p=p-next ; while(p!=0); printf(-endn); ( 2)在单向链表中插入结点 s:用来指向新开辟的结点 p:指向插入的位置 q: p的前趋结点 x y q p s 链表非空,值为 x结点存在,插在 x 结点前 链表非空,值为 x结点不存在,插在表尾 链表为空,插在表尾,即头结点之后。 s-next =p; q-next =s; 指针应用举例 -链表 指针应用举例 -链表 insert_snode(SLIST *head,int x,int y) SLIST *s,*p,*q; s=(SLIST*)malloc(sizeof(SLIST); s-data=y; /*在新结点中存入 y的值 */ q=head; p=head-next ; /*指针初始化, p指向第一个结点 */ while(p!=0) p=p-next ; /*q指向 p的前趋结点 */ s-next =p; q-next =s; ( 3)删除单向链表中的结点 / 8 7 q p 9 头结点 头指针 q-next=p-next 指针应用举例 -链表 指针应用举例 -链表 struct link *delete_link(struct link *head,int x) struct link *q,*p; q=head; p=head-next; while(p!=0) /*q始终指向 m之前的结点 */ p=p-next; if(m=0) /*不存在符合条件的结点 */ printf(“can not exit!n”); else q-next=p-next; /*逻辑删除结点 */ free(m); /*物理删除结点 */ return(head);
展开阅读全文
相关资源
正为您匹配相似的精品文档
相关搜索

最新文档


当前位置:首页 > 图纸专区 > 课件教案


copyright@ 2023-2025  zhuangpeitu.com 装配图网版权所有   联系电话:18123376007

备案号:ICP2024067431-1 川公网安备51140202000466号


本站为文档C2C交易模式,即用户上传的文档直接被用户下载,本站只是中间服务平台,本站所有文档下载所得的收益归上传人(含作者)所有。装配图网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。若文档所含内容侵犯了您的版权或隐私,请立即通知装配图网,我们立即给予删除!