第8章 结构和联合.ppt_第1页
第8章 结构和联合.ppt_第2页
第8章 结构和联合.ppt_第3页
第8章 结构和联合.ppt_第4页
第8章 结构和联合.ppt_第5页
已阅读5页,还剩46页未读 继续免费阅读

下载本文档

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

文档简介

1、第8章 结构和联合,本章要点 C语言的结构类型。 结构数组。 指向结构的指针。 C语言的动态数据结构。 联合类型。 本章难点 结构指针和C语言的动态数据结构。,8.1 结构的说明和引用 8.2 结构的指针 8.3 结构和函数 8.4 结构数组 8.5 结构和指针的应用 8.6 联合(共用体) 8.7 用typedef定义类型名,8.1 结构的说明和引用,在实际中常常描述同一对象的不同属性,如一个学生有学号、姓名、性别、年龄、各科分数,表示这些属性的数据具有不同的类型,因而不能用数组表示。C语言提供了一种数据结构,可以把这些不同类型的数据组成一个整体,这就是结构类型。 结构类型是各种结构的总称,

2、是一种构造类型。一个结构变量可以由不同类型的成员变量组成,这些成员变量又称为结构的域、分量。结构的所有成员除自身的名字外,还拥有共同的名字,即结构变量名。,8.1.1 结构说明 8.1.2 结构的引用,8.1.1 结构说明,struct 结构体名 数据类型1 成员名1; 数据类型2 成员名2; 数据类型n 成员名n; ;,结构体类型定义的一般形式:,struct为关键字; 结构体名是用户定义的类型标识。 中是组成该结构体的成员。成员的数据类型可以是C语言所允许的任何数据类型。,在定义结构体类型的同时定义变量,例如: struct student char num8,name20,sex; in

3、t age; float score; st30;,struct 结构体名 成员定义表; 变量名表;,直接定义结构体类型变量,例如: struct char num8,name20,sex; int age; float score; st30, a, b, c;,struct 成员定义表; 变量名表;,在结构的说明中,结构成员可以为任何类型且结构成员还可以和结构外部的其它变量同名,不同结构的成员也可以同名,但同一结构的成员不能同名。,例如学生类型的定义: struct student char num8; /* 学号是字符数组类型 */ char name30; /* 姓名是字符数组类型 *

4、/ char sex; /* 性别是字符型 */ int age; /* 年龄是整型 */ char addr60; /* 住址是字符数组类型 */ int score6; /* 成绩是整型数组类型 */ ;,利用已定义的结构体类型名定义变量 struct 结构体名 变量名表; 例如: struct student s30, t1, t2;,按照结构体类型的组成,系统为定义的结构体变量分配内存单元。结构体变量的各个成员在内存中占用连续存储区域,结构体变量所占内存大小为结构体中每个成员所占用内存的长度之和。,8.1.2 结构的引用,1结构的初始化 结构变量在说明时可以初始化,初值是由常量表达式组

5、成的初值表。例如, struct student char name10; short sex; int age; float score; student1“zhangsan”,1,20,88.8;,2结构变量的引用 对结构变量的引用只允许下列5种情况: (1)同类型的结构变量相互赋值。例如 student2=student1; (2)函数返回的结构成员给同类型的结构变量。 (3)对结构变量取地址。例如 student.sex=0; scanf(“%s”,); 但=”zhang san”; 则为非法。,4嵌套的结构 结构的一个成员可以是一个

6、结构,含有结构成员的结构称为嵌套的结构。,struct date int year,month,day; struct student char num8; char name30; char sex; struct date birthday; /* 成员为结构体类型 */ char addr60; int score6; ;,8.2 结构的指针,指向结构的指针(或称结构指针)可以用来引用结构的成员,可以作为参数传给函数,也可以作为函数的返回值。 1结构指针的说明 指向结构的指针使用之前也要进行说明,例如 struct date int year, month, day;d, *p=,用结构

7、体变量名的引用形式: d.year d.month d.day,用结构体指针变量的引用形式: (*p).year (*p).month (*p).day p-year p-month p-day 注意:成员引用表达式中的( )不能省,如(*pd).day不能写成*pd.day,因为“.”运算符的优先级高于*,所以*pd.day等同于*(pd.day),在该例中为非法操作。 结构成员运算符“-”和“.”的优先级相同,它们与()、 属于同一优先级,按从左到右结合。,8.3 结构和函数,1结构作函数的参数 结构作函数的参数有三种可能的方法。 (1)传一个结构成员(用结构成员作实参); (2)传整个结

8、构(用结构变量名作实参); (3)传结构的指针(用结构的地址或指向结构的指针作实参)。 我们推荐使用第三种方法。 函数的返回值为结构变量或指向结构变量的指针。,【例8.3】写一个函数计算两个复数的和。 #include comp.h struct complex *addcomp(struct complex c1, struct complex c2) static struct complex temp; temp.re=c1.re+c2.re; temp.im=c1.im+c2.im; return( ,8.4 结构数组,8.4.1 结构数组的说明,引用和初始化 8.4.2 结构数组作函

9、数参数 8.4.3 sizeof运算符 8.4.4 用结构的指针引用结构数组的成员,8.4.1 结构数组的说明、引用和初始化,结构数组是其元素都是具有相同结构体类型的结构体变量。定义的一般格式为: struct 结构体名 结构体数组名元素个数,结构体数组名元素个数,; 其中,“struct 结构体名”是已定义过的结构体类型。因此定义结构体数组和定义结构体变量的方法相仿,只需说明其为数组即可。,例如: struct student int num; char name10; char sex; int age; float score; char addr30; ; struct student

10、 stu3; 以上定义了一个数组stu,其元素为struct student类型数据,数组有3个元素。,2、结构体数组的初始化 一个外部的或静态的结构体数组在定义的同时可以初始化。其一般格式是在定义之后紧跟一个用花括号括起来的一组初始化数据: struct 结构体名 结构体数组名=初始数据表列; 其中,“struct 结构体名”是已定义过的结构体类型。,【例8.6】对候选人得票的统计程序。设有三个侯选人,每次输入一个得票的候选人的名字,要求最后输出各人得票结果。 #include struct person char name18; int count; leader3=Li,0,Zhang,

11、0,Wang,0;,void main () int i,j; char leader_name18; for(i=1;i=10;i+) scanf (%s,leader_name); for (j=0;j3;j+) if(strcmp(leader_name,)=0) leaderj.count+; printf (n); for (i=0;i3;i+) printf(%5s,%dn,,leaderi.count); ,8.4.2 结构数组作函数参数,8.4.3 sizeof运算符,sizeof是一个单目运算符,用于计算一个对象的大小,它是在编

12、译时执行的运算,所以sizeof表达式是一个常量表达式,sizeof表达式有两种形式: sizeof表达式或 sizeof(表达式) sizeof(类型名),【例】利用结构体指针输出一组化学元素名称及其原子量。 struct list int i; char name4; float w; tab4=1,H,1.008,2,He,4.0026, 3,Li,6.941,4,Be,9.01218;,8.4.4 用结构的指针引用结构数组的成员,main( ) struct list *p; printf(NotNametAtomic Weightn); for (p=tab; pi, p-name,

13、 p-w); ,No Name Atomic Weight,1 H 1.008,2 He 4.0026,3 Li 6.941,4 Be 9.01218,链表是一种动态数据结构,可根据需要动态地分配存储单元。在数组中,插入或删除一个元素都比较繁琐,而用链表则相对容易。但是数组元素的引用比较简单,对于链表中结点数据的存取操作则相对复杂。, 链表中每个元素称为一个结点。 构成链表的结点必须是结构体类型数据。, 相邻结点的地址不一定是连续的,依靠指针将 它们连接起来。,struct node char c; struct node *next; ;,8.5 结构指针的应用,C语言提供了相关的存储管理库

14、函数。这里仅介绍其中三个,它们的原型说明在“stdlib.h”头文件和“alloc.h”头文件中,使用这三个函数时,应选择其中一个头文件包含到源程序中。, 动态分配存储区函数malloc( ) 函数原型:void *malloc(unsigned size); 调用格式:malloc(size) 功能:在内存分配一个size字节的存储区。调用 结果为新分配的存储区的首地址,是一个void 类型指针。若分配失败,则返回NULL(即0)。,在ANSI C标准中,关键字void有两种用法。 第一种用法,可将无返回值的函数定义为void类型 第二种用法,用void * 定义指针,这是一个指向 非具体数

15、据类型的指针,称为无类型指针。,动态分配和释放存储单元,【例】调用malloc函数分配所需存储单元。 #include main( ) struct st int n; struct st *next; *p; p=(struct st *)malloc(sizeof(struct st); p-n=5; p-next=NULL; printf(p-n=%dtp-next=%xn,p-n,p-next); ,将函数返回值转换成结构体指针, 动态分配存储区函数calloc( ) 函数原型: void *calloc(unsigned int n,unsigned int size); 调用格式:

16、calloc(n,size) 功能:在内存分配一个n倍size字节的存储区。调用结果为新分配的存储区的首地址,是一个void类型指针。若分配失败,则返回NULL(即0)。,【例】调用calloc函数分配所需存储单元。 #include main( ) int i,*ip; ip=(int *)calloc(10,2); for (i=0; i10; i+) scanf(%d,ip+i); for (i=0; i10; i+) printf(%d ,*(ip+i); printf(n); ,动态分配了10个存放整型数据的存储单元, 释放动态分配存储区函数free( ) 函数原型:void fre

17、e(void *p);,此函数无返回值,实参必须是一个指向动态分配存储区的指针,它可以是任何类型的指针变量。,调用格式:free(p) 功能:释放p所指向的动态分配的存储区。,建立链表就是根据需要一个一个地开辟新结点,在结点中存放数据并建立结点之间的链接关系。,【例9.13】建立一个学生电话簿的单向链表函数。,建立单向链表,【例9.14】输出学生电话簿链表函数。,输出单向链表中各结点信息,在链表中,如果要删除第i个结点,一般是将第(i-1)个结点直接与第(i+1)个结点相连接,然后再释放第i个结点的存储单元 。,删除单向链表中指定的结点,【例】删除学生电话簿链表中指定学生的信息。,删除第一个结

18、点,删除中间结点或尾结点,学生姓名,当姓名不同并且不是尾结点循环,【例】删除学生电话簿链表中指定学生的信息。,(a) 删除第一个结点 (head=p-next),【例】删除学生电话簿链表中指定学生的信息。,(b) 删除中间结点或尾结点 (q-next=p-next),【例】删除学生电话簿链表中指定学生的信息。,(c) 未找到指定的结点 (strcmp(x,p-name)!=0),将一个新结点插入到链表中,首先要寻找插入的位置。如果要求在第i个结点前插入,可设置三个工作指针p0、p和q,p0是指向待插入结点的指针。利用p和q指针查找第i个结点,找到后再将新结点链接到链表上。,q,q,新的第i个结点,在单向链表中插入结点

温馨提示

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

评论

0/150

提交评论