《第十章-用户自定义数据类型课件.ppt》由会员分享,可在线阅读,更多相关《第十章-用户自定义数据类型课件.ppt(52页珍藏版)》请在taowenge.com淘文阁网|工程机械CAD图纸|机械工程制图|CAD装配图下载|SolidWorks_CaTia_CAD_UG_PROE_设计图分享下载上搜索。
1、第十章第十章 用户自定义数据类型用户自定义数据类型结构体数据类型概述结构体数据类型概述1结构体数据类型的定义及其变结构体数据类型的定义及其变量的声明和引用量的声明和引用2共用体数据类型定义与共用体共用体数据类型定义与共用体变量的声明于引用变量的声明于引用4结构体变量的应用结构体变量的应用3为数据类型能够定义新的数据为数据类型能够定义新的数据类型名类型名52/12/2023前面学习的数据类型都属于简单数据类型,前面学习的数据类型都属于简单数据类型,实际问题的结构是复杂、多样的,仅用内建实际问题的结构是复杂、多样的,仅用内建的简单数据类型进行问题描述是不够的。的简单数据类型进行问题描述是不够的。C
2、语言没有提供表达复杂问题结构的公共数语言没有提供表达复杂问题结构的公共数据类型,但它提供了由用户根据不同问题结据类型,但它提供了由用户根据不同问题结构定制相应数据类型描述的技术机制。构定制相应数据类型描述的技术机制。由用户定制的数据类型称为用户自定义数据由用户定制的数据类型称为用户自定义数据类型类型(User Definition Data Type)。2/12/202310.1 结构体数据类型概述结构体数据类型概述数组数组是一种构造数据类型,其所有元素的数是一种构造数据类型,其所有元素的数据类型相同。据类型相同。结构体结构体是另一种构造数据类型,是另一种构造数据类型,它它将具有多个属性的对象
3、作为一个整体来描将具有多个属性的对象作为一个整体来描述述。如商品的描述包括商品的编号、名称、。如商品的描述包括商品的编号、名称、价格、生产日期和生产厂商等属性。用基本价格、生产日期和生产厂商等属性。用基本数据类型来定义和描述商品对象需要设置若数据类型来定义和描述商品对象需要设置若干个简单变量或数组变量,它不利于对实际干个简单变量或数组变量,它不利于对实际问题求解过程的描述与实现。问题求解过程的描述与实现。结构体结构体提供了一个变量名下引用多种数据类提供了一个变量名下引用多种数据类型的机制型的机制以便把与对象描述相关的各类数据以便把与对象描述相关的各类数据信息组合到一起进行管理。它克服了只用简信
4、息组合到一起进行管理。它克服了只用简单数据类型和数组进行表述的缺陷。单数据类型和数组进行表述的缺陷。2/12/202310.2 结构体类型定义及其变量的声明和引用结构体类型定义及其变量的声明和引用u10.2.1 结构体数据类型的定义结构体数据类型的定义 struct 结构体数据类型名结构体数据类型名 类型标识符类型标识符 成员变量名;成员变量名;类型标识符类型标识符 成员变量名;成员变量名;结构体数据类型名和关键字结构体数据类型名和关键字struct一起构一起构成成结构体数据类型标识符结构体数据类型标识符。结构体数据类型标识符结构体数据类型标识符用于声明用于声明结构体数结构体数据类型变量据类型
5、变量(简称简称结构体变量结构体变量)struct不能不能省略省略基本数据类型或已定基本数据类型或已定义的构造数据类型义的构造数据类型结构体数据结构体数据类型标识符类型标识符2/12/2023例如:例如:struct student int nStNo;char cName20;char cSex;int nAge;float fScore;char cAddr30;保留关键字保留关键字结构体结构体类型名类型名成成员员列列表表分号分号结构体数据类型的信息存储结构体数据类型的信息存储结构体数据类型的信息存储结构体数据类型的信息存储结构映射实例结构映射实例结构映射实例结构映射实例cNamecName
6、nStNonStNocSexnAgenAgefScorefScore cAddr cAddr2 2字节字节字节字节2 2字节字节字节字节2020字节字节字节字节1 1字节字节字节字节4 4字节字节字节字节3030字节字节字节字节2/12/2023用用结构体数据类型标识符结构体数据类型标识符声明的变量称为声明的变量称为结结构体变量构体变量。注意:注意:遵守先声明、后定义,再遵守先声明、后定义,再使用的基本原则。使用的基本原则。1.先定义结构体类型,再声明结构体变量先定义结构体类型,再声明结构体变量struct 结构体数据类型名结构体数据类型名 类型标识符类型标识符 成员变量名成员变量名;类型标识
7、符类型标识符 成员变量名成员变量名;struct 结构体数据类型名结构体数据类型名 变量名列表变量名列表;u10.2.2 结构体变量的声明结构体变量的声明例如:例如:struct student int nStNo;char cName20;char cSex;int nAge;float fScore;char cAddr30;struct student struStu1,struStu2;2/12/20232.在定义结构体数据类型在定义结构体数据类型的同时声明结构变量的同时声明结构变量struct 结构体数据类型名结构体数据类型名 类型标识符类型标识符 成员变量名成员变量名;类型标识符类
8、型标识符 成员变量名成员变量名;变量名表列变量名表列;例如:例如:struct student int nStNo;char cName20;char cSex;int nAge;float fScore;char fAddr30;struStu1,struStu2;2/12/20233.不定义结构体数据类型不定义结构体数据类型名,直接声明结构体变量名,直接声明结构体变量struct 类型标识符类型标识符 成员变量名成员变量名;类型标识符类型标识符 成员变量名成员变量名;变量名表列变量名表列;例如:例如:struct int nStNo;char cName20;char cSex;int n
9、Age;float fScore;char cAddr30;struStu1,struStu2;由于无数据类型名,本方法只能在此声明结由于无数据类型名,本方法只能在此声明结构体变量,不能在其它地方。构体变量,不能在其它地方。在不同地方出现的完全相同的结构体数据类在不同地方出现的完全相同的结构体数据类型定义,本质上属于不同的用户自定义数据类型定义,本质上属于不同的用户自定义数据类型,其声明的变量也属于不同数据类型。型,其声明的变量也属于不同数据类型。2/12/2023说明说明结构体数据类型与结构体变量的区别:结构体数据类型与结构体变量的区别:结构体数据类型不涉及内存分配问题结构体数据类型不涉及内
10、存分配问题,结构体变量涉及内存分配问题。结构体变量涉及内存分配问题。结构体数据类型只是定义数据类型,不结构体数据类型只是定义数据类型,不涉及赋值、存取、运算等操作行为涉及赋值、存取、运算等操作行为;结结构体变量涉及操作行为。构体变量涉及操作行为。结构体数据类型的定义可嵌套结构体数据类型的定义可嵌套结构体内部的成员变量名与外部的其它变结构体内部的成员变量名与外部的其它变量名可相同,量名可相同,不会混淆不会混淆(同名屏蔽同名屏蔽)结构体数据类型及变量的作用域与生存期结构体数据类型及变量的作用域与生存期例如:例如:struct date int month;int day;int year;stru
11、ct student int num;char name20;struct date birthday;stu;num namebirthdaymonth day year又如:又如:struct student int num;char name20;struct date int month;int day;int year;birthday;stu;num namebirthdaymonth dayyear2/12/2023struct student int nStNo;char cName20;char cSex;int nAge;float fScore;char cAddr30;
12、struStud;例例10-1 测试结构体数据类型存储空间长度。测试结构体数据类型存储空间长度。int main(void)/*两种方法计算两种方法计算*/int nSizeStud;printf(Size of struStud are%d and%d.n,sizeof(struct student),sizeof(struStud);nSizeStud=sizeof(struStud.nStNo)+sizeof (struStud.cName)+sizeof(struStud.cSex);nSizeStud+=sizeof(struStud.nAge)+sizeof (struStud.f
13、Score)+sizeof(struStud.cAddr);printf(Total size is%dn,nSizeStud);return 0;/*End of main()*/不能省略不能省略struct运行结果为:运行结果为:Size of struStud are 59 and 59.Total size is 592/12/2023u10.2.3 结构体变量的初始化结构体变量的初始化对结构体变量初始化的方法:对结构体变量初始化的方法:按照所定义结构体变量中的成员数据类型依按照所定义结构体变量中的成员数据类型依顺序对各成员变量赋以初值。编译时系统会将顺序对各成员变量赋以初值。编译时系
14、统会将声明初始化值赋值给各个成员变量。声明初始化值赋值给各个成员变量。struct date int month,day,year;birthday=12,15,1974;实例:实例:2/12/2023形式形式一一struct 结构体名结构体名 类型标识符类型标识符 成员名;成员名;类型标识符类型标识符 成员名;成员名;struct 结构体名结构体名 结构体变量结构体变量=初始数据初始数据;例如:例如:struct date int month;int day;int year;struct date birthday=12,15,1974;2/12/2023形式二形式二struct 结构体名
15、结构体名 类型标识符类型标识符 成员名成员名;类型标识符类型标识符 成员名成员名;结构体变量结构体变量=初始数据初始数据;例如:例如:struct person long lPersonNo;char cName20;char cSex;struct date birthday;struPerson=10001,ZhangLi,W,12,13,1988;struPerson=10001,ZhangLi,W,12,13,1988;struPerson=10001,ZhangLi,W,struPerson=10001,ZhangLi,W,12,13,198812,13,1988;展开成单层展开成单
16、层层次化列表层次化列表2/12/2023形式三形式三struct 类型标识符类型标识符 成员名;成员名;类型标识符类型标识符 成员名;成员名;结构体变量结构体变量=初始数据初始数据;例如:例如:struct int num;char name20;char sex;int age;char addr30;stu1=112,Wang Lin,M,19,200 Beijing Road;stu1=112,Wang Lin,M,19,200 Beijing Road;2/12/2023注意:注意:初始化列表中值的个数少于结构体成初始化列表中值的个数少于结构体成员变量个数时,余下的成员变量自动初始化员
17、变量个数时,余下的成员变量自动初始化为为0 或或NULL。反之,将出现编译型错误:。反之,将出现编译型错误:Too many initializers。例如:例如:struct score_type long lStNo;float fScore;stuScore1=1;stuScore1=1;struct score_type struct score_type struScore2=1,100,2,200;struScore2=1,100,2,200;例例10-2 无初始化列表的自动、外部和静态结无初始化列表的自动、外部和静态结构体变量的初值对比。构体变量的初值对比。(P277-278)2
18、/12/2023引用规则:引用规则:既可以访问结构体中的成员变量,既可以访问结构体中的成员变量,也可以将结构体变量作整体引用。也可以将结构体变量作整体引用。1.结构体变量成员的引用结构体变量成员的引用格式:格式:结构体变量名结构体变量名.成员变量名成员变量名对成员变量进行访问的逻辑示意图对成员变量进行访问的逻辑示意图 struStud先定位到结构体变量先定位到结构体变量先定位到结构体变量先定位到结构体变量再定位到成员变量再定位到成员变量再定位到成员变量再定位到成员变量100010001002100210041004int nStNo;int nStNo;int nAge;int nAge;fl
19、oat fScore;float fScore;图图图图1 10 0-5 5 结结结结构构构构体体体体变变变变量量量量及及及及其其其其成成成成员员员员访访访访问问问问过过过过程程程程示示示示意意意意图图图图u10.2.4 结构体变量及其成员引用结构体变量及其成员引用2/12/2023例例10-3 输入并输出学生的成绩记录数据。输入并输出学生的成绩记录数据。#include struct score_type int nStNo,int nAge;float fScore;int main(void)struct score_type struStud;printf(Enter nStNo,nA
20、ge,fScore:);scanf(%d,%d,%f,&(struStud.nStNo),&struStud.nAge,&struStud.fScore);printf(nStNo=%d,nAge=%d,fScore=%.1f n,struStud.nStNo,struStud.nAage,struStud.fScore);return 0;/*End of main()*/运行结果为:运行结果为:EnternStNo,nAge,fscore:1,20,95.5nStNo=1,nAge=20,fScore=95.5 2/12/2023(1)结构体变量之间的整体赋值结构体变量之间的整体赋值变量类
21、型相同才可以变量类型相同才可以变量类型相同才可以变量类型相同才可以进行整体赋值进行整体赋值进行整体赋值进行整体赋值(2)结构体变量的整体输入输出问题结构体变量的整体输入输出问题不能不能不能不能进行进行进行进行整体输入输出整体输入输出整体输入输出整体输入输出,只能只能只能只能进行进行进行进行成员级成员级成员级成员级引用,引用,引用,引用,且要求成员是基本数据类型且要求成员是基本数据类型且要求成员是基本数据类型且要求成员是基本数据类型利用利用利用利用scanfscanf()()和和和和printfprintf()()函数完成函数完成函数完成函数完成含字符型数据的输入格式要严格对齐,否则易含字符型数
22、据的输入格式要严格对齐,否则易含字符型数据的输入格式要严格对齐,否则易含字符型数据的输入格式要严格对齐,否则易错位。错位。错位。错位。例如:例如:例如:例如:scanf(%dscanf(%d%c,&i,&chc,&i,&ch););执行时,执行时,执行时,执行时,如果键盘输入:如果键盘输入:如果键盘输入:如果键盘输入:30 A30 A。chch接收的是接收的是接收的是接收的是空格空格空格空格字符,字符,字符,字符,不是不是不是不是AA。利用利用利用利用gets()gets()和和和和puts()puts()函数完成函数完成函数完成函数完成gets()gets()可以获取有空格的字符串数据项。可
23、以利可以获取有空格的字符串数据项。可以利可以获取有空格的字符串数据项。可以利可以获取有空格的字符串数据项。可以利用字符串函数截取相应数据项串,利用用字符串函数截取相应数据项串,利用用字符串函数截取相应数据项串,利用用字符串函数截取相应数据项串,利用atoiatoi()()、atolatol()()和和和和atofatof()()等函数将数据项串分别转化为整型、等函数将数据项串分别转化为整型、等函数将数据项串分别转化为整型、等函数将数据项串分别转化为整型、长整型和浮点数等数据类型值。长整型和浮点数等数据类型值。长整型和浮点数等数据类型值。长整型和浮点数等数据类型值。例例10-4例例10-52.结
24、构体变量的整体引用结构体变量的整体引用2/12/2023(3)结构体变量的其他整体引用情形:结构体变量的其他整体引用情形:将结构体变量将结构体变量作为函数参数作为函数参数使用使用将结构体数据类型将结构体数据类型作为函数名类型作为函数名类型使用使用并由函数名返回结构体数据类型值并由函数名返回结构体数据类型值获取获取结构体变量结构体变量地址地址和结构体变量和结构体变量存储存储空间大小空间大小用结构体指针变量用结构体指针变量引用引用整个结构体整个结构体及其及其成员变量成员变量。2/12/2023u10.3.1 结构体数组结构体数组(struct array)一个简单结构体变量只能表示一个对象,表一个
25、简单结构体变量只能表示一个对象,表示多个同类型对象要用多个变量名。示多个同类型对象要用多个变量名。0.结构体数组:结构体数组:数组的数组的元素数据类型元素数据类型为为结构结构体数据类型体数据类型的数组。的数组。1.结构体数组的声明:结构体数组的声明:(1)先定义类型,再声明结构体数组先定义类型,再声明结构体数组(2)定义类型的同时声明结构体数组定义类型的同时声明结构体数组(3)不定义类型名的情况下直接声明结构不定义类型名的情况下直接声明结构体数组体数组10.3 结构体变量的应用结构体变量的应用struct student int nStNo,nAge;float fScore;char cNa
26、me20,cSex,cAddr30;;struct student struStud10;struct student int nStNo,nAge;float fScore;char cName20,cSex,cAddr30;struct student struStud10;struct int nStNo,nAge;float fScore;char cName20,cSex,cAddr30;struStud10;2/12/2023a0a0 a1a1 a2a2 a3a3 a4a4 a5a5 1 12 23 34 45 56 67 78 81000110001LimingLimingMM2
27、0208989Sichuan Sichuan 1000210002ZhangliZhangliWW19197676HebeiHebeistruStud0struStud0struStud1struStud1(a)(a)int a10;int a10;空间分配空间分配空间分配空间分配(b)(b)struct student struct student struStud2;struStud2;空间分配空间分配空间分配空间分配100010001059105910001000100210021004100410061006100810081010101010121012101410141016101
28、610181018数组的数组的数组的数组的首地址首地址首地址首地址数组元数组元数组元数组元素地址素地址素地址素地址简单数组和结构体数组存储比较简单数组和结构体数组存储比较2/12/20232.结构体数组初始化结构体数组初始化(1)采用完整初始化值列表采用完整初始化值列表(2)采用部分初始值列表采用部分初始值列表(3)数组长度由初始化值列表确定数组长度由初始化值列表确定struct student struStud=,;struct student struct student int nStNo;int nStNo;char cName20;char cName20;char cSex;cha
29、r cSex;int nAge;int nAge;float fScore;float fScore;char cAddr30;char cAddr30;struStud2=10001,Liming,M,20,89,Sichuan struStud2=10001,Liming,M,20,89,Sichuan CD,1002,zhangli,W,19,76,Heber HG;CD,1002,zhangli,W,19,76,Heber HG;struct student struct student int nStNo;int nStNo;char cName20;char cName20;cha
30、r cSex;char cSex;int nAge;int nAge;float fScore;float fScore;char cAddr30;char cAddr30;stu_1stu_12=10001,Liming,M,20,89,Sichuan 2=10001,Liming,M,20,89,Sichuan CD,CD,stu_2stu_25=1001,10002;5=1001,10002;2/12/2023stu_10stu_10 stu_11stu_11 1000110001LimingLimingMM20208989SichuanSichuan0 0000 00 00.000.0
31、000(a)(a)stu_25stu_25的的的的 初初初初 始始始始化化化化(b)(b)stu_12 stu_12的初始化的初始化的初始化的初始化10001000105910591000100010591059111811181177117712361236stu_20stu_20stu_21stu_21stu_22stu_22 stu_23stu_23 stu_24stu_24 0 010002100020 00 00 00 01000110001部分初始化值列表的初始化结果部分初始化值列表的初始化结果部分初始化值列表的初始化结果部分初始化值列表的初始化结果2/12/2023对一维结构体数
32、组的引用对一维结构体数组的引用结构体数组元素的引用结构体数组元素的引用J赋值赋值给同一结构体数据类型变量或元素给同一结构体数据类型变量或元素struct student_type strustudArr3,struStud;struStud=struStudArr0;struStudArr0=struStudArr1;J不能不能直接作整体输入输出和进行常量赋值直接作整体输入输出和进行常量赋值struStudArr1=10001,Liming,M,20,89,“Sichuan CD”是是非法非法的。的。J作为函数参数或返回值进行作为函数参数或返回值进行整体引用整体引用J引用结构体数组元素的引用结
33、构体数组元素的成员变量成员变量 struStudArri.nStNo=10001;3.结构体数组的引用结构体数组的引用2/12/2023结构体数组名的引用结构体数组名的引用J表示引用从数组首地址开始并表示引用从数组首地址开始并以结构体数以结构体数组元素为存储单位组元素为存储单位的一段连续存储空间。有的一段连续存储空间。有函数参数和函数返回值两种引用形式函数参数和函数返回值两种引用形式结构体数组的指针引用结构体数组的指针引用(例例10-7)J一维结构体数组名或指针引用一维结构体数组名或指针引用J一维结构体数组元素的地址引用一维结构体数组元素的地址引用J一维结构体数组元素的成员变量地址引用一维结构
34、体数组元素的成员变量地址引用2/12/2023二维结构体数组的引用二维结构体数组的引用结构体数组元素的引用结构体数组元素的引用结构体数组名的引用结构体数组名的引用J注意注意二次引用特点二次引用特点及二维数组二级指针及二维数组二级指针的声明与引用方法的声明与引用方法结构体数组的指针引用结构体数组的指针引用(例例10-8)J二维二维数组名数组名、指向一维结构体数组的指指向一维结构体数组的指针针和和二级指针二级指针引用引用J二维结构体数组二维结构体数组行地址行地址和和行指针行指针,列地列地址址和和列指针列指针引用引用J指向结构体数组指向结构体数组元素成员变量的地址和元素成员变量的地址和指针指针引用引
35、用2/12/2023u10.3.2 结构体变量作函数参数及函数返回值结构体变量作函数参数及函数返回值结构体变量作为函数参数结构体变量作为函数参数结构体变量结构体变量及其及其指针指针、结构体、结构体成员变量成员变量及及其其指针指针均可作为函数参数均可作为函数参数结构体变量作为函数返回值结构体变量作为函数返回值(P294295)89891980198013131212WWchenweichenwei242410011001stud_pstud_p89891980198013131212WWchenweichenwei242410011001studstud例如:例如:例如:例如:(P293294)
36、(P293294)void out_stud_info(void out_stud_info(structstruct studentstudent studstud););/*/*函数声明函数声明函数声明函数声明*/*/struct studentstruct student stud_p=10001,24,zhangli,W,stud_p=10001,24,zhangli,W,12,13,1980,89;12,13,1980,89;/*/*变量声明变量声明变量声明变量声明*/*/out_stud_info(out_stud_info(stud_pstud_p););/*/*函数调用语句函数
37、调用语句函数调用语句函数调用语句*/*/stud_pstud_p为实参,为实参,为实参,为实参,studstud为形参,为形参,为形参,为形参,studstud的存储空间是调用的存储空间是调用的存储空间是调用的存储空间是调用时临时分配的。时临时分配的。时临时分配的。时临时分配的。2/12/2023u10.3.3 结构体变量指针结构体变量指针1.指向结构体变量的指针指向结构体变量的指针(结构体指针和结结构体指针和结构体成员指针构体成员指针)例如:例如:对以下结构体变量对以下结构体变量stru_pen,其有关的指针,其有关的指针逻辑关系如逻辑关系如图图所示。所示。struct product_in
38、fo int no;char cName20;float fPrice;sturct product_info stru_pen;2/12/2023100010001002100210221022结构体变量地址结构体变量地址:&stru_pen结结 构构 体体 变变 量量 名名:stru_pen成员变量地址成员变量地址:&stru_pen.no&stru_pen.cName&stru_pen.fPrice图图10-10 结构体变量、成员变量及其地址关系结构体变量、成员变量及其地址关系nonocNamecNamefPricefPrice2/12/2023结构体指针变量的声明及初始化结构体指针变量
39、的声明及初始化 int*iPtr;struct product_info*penPtr;简单指针变量简单指针变量:结结构构体体指指针针变变量量:类型标识符类型标识符指针变量名指针变量名例如:例如:struct product_info stru_pen,*penPtr;penPtr=&stru_pen;声明声明初始化初始化2/12/2023通过结构体指针变量的成员引用通过结构体指针变量的成员引用由由或或操作符完成操作符完成J(*结构体指针变量名结构体指针变量名).成员变量名成员变量名J结构体指针变量名结构体指针变量名成员变量名成员变量名 几种等价的访问形式几种等价的访问形式 stru_pen.
40、no*(&stru_pen.no)*(&(*(&stru_pen.no)(&stru_pen.no)nopenPtrno*(&(penPtrno)(*penPtr).no *(&(*penPtr).no)例例10-11 用指向结构体的指针变量改写例用指向结构体的指针变量改写例10-7。(P296297)例例10-12 用结构体变量指针作为函数返回值用结构体变量指针作为函数返回值改写例改写例10-11的输入模块。的输入模块。(P298299)2/12/20232.指向结构体数组的指针指向结构体数组的指针结构体数组主要通过数组名和下标索引进结构体数组主要通过数组名和下标索引进行数组元素访问,也可用
41、指针指向结构体行数组元素访问,也可用指针指向结构体数组及其元素。数组及其元素。例例10-13 用指向一维结构体数组的指针对成绩用指向一维结构体数组的指针对成绩单进行输入和输出,并求其平均值。单进行输入和输出,并求其平均值。(P296297)例例10-14*用指向结构体数组的指针或二级指用指向结构体数组的指针或二级指针改写例针改写例10-8。(P298299)u10.3.4 动态存储分配技术及其应用动态存储分配技术及其应用*(略略)2/12/2023u10.4.1 共用体数据类型定义及其变量声明共用体数据类型定义及其变量声明属于构造数据类型,也叫属于构造数据类型,也叫联合体联合体用途:用途:使几
42、个不同类型的变量共占一段内使几个不同类型的变量共占一段内存存(相互覆盖相互覆盖)基本定义格式:基本定义格式:union 共用体数据类型名共用体数据类型名 成员表列;成员表列;;类型定义类型定义不分配内存不分配内存10.4 共用体数据类型共用体数据类型2/12/2023union person_nolong unsigned luStNo;unsgned uGradeNo;unsigned uWorkNo;共用体数共用体数据类型名据类型名保保留留关关键键字字共用体数据共用体数据类型标识符类型标识符成成员员列列表表分号分号共用体数据类型的定义实例共用体数据类型的定义实例2/12/2023形式一形式
43、一 union 共用体数据类型名共用体数据类型名 成员列表成员列表;union 共用体数据类型名共用体数据类型名 变量名列表变量名列表;形式二形式二 union 共用体数据类型名共用体数据类型名 成员列表成员列表;变量名列表变量名列表;形式三形式三 union 成员列表成员列表;变量名列表变量名列表;共用体变量的声明共用体变量的声明2/12/2023例如:例如:union data int i;char ch;float f;a,b;ab共用体共用体变量的变量的内存分配长内存分配长度度=最长成员最长成员所占字节数所占字节数共用体共用体变量任何时刻变量任何时刻只有只有一个成员一个成员存在存在ff
44、iichch2/12/2023共用体和结构体数据类型的相似性共用体和结构体数据类型的相似性类型定义及变量声明方法相似类型定义及变量声明方法相似成员变量的访问方法相似成员变量的访问方法相似本质差异本质差异union的有成员变量共享同一段存储空间的有成员变量共享同一段存储空间 FFD9FFD8FFD7FFD6地址地址成员成员nNum成员成员lNum和和fVal成员成员chArr4图图10-23 共用体变量共用体变量unTmp存储空间逻辑结构存储空间逻辑结构u10.4.2 共用体变量的基本性质共用体变量的基本性质union union_test int nNum;long lNum;float fV
45、al;char chArr4;unTmp;2/12/2023union以成员以成员存储空间最大者为准存储空间最大者为准;struct以所有成员变量所需存储空间大小为准以所有成员变量所需存储空间大小为准union变量及其变量及其成员共同享有该段存储空间成员共同享有该段存储空间;而而struct变量中各成员变量间享有独立的、变量中各成员变量间享有独立的、相对固定的存储空间相对固定的存储空间所有所有union成员变量的首地址相同,即共用成员变量的首地址相同,即共用体变量首地址;体变量首地址;struct中各成员变量的地址中各成员变量的地址各不相同。只有第一个成员变量的地址与各不相同。只有第一个成员变
46、量的地址与结构体变量地址相同,但其意义不同结构体变量地址相同,但其意义不同。union在存储空间占用上的特性在存储空间占用上的特性FFD9FFD8FFD7FFD6地址地址成员成员nNum成员成员lNum和和fVal成员成员chArr4图图10-23 共用体变量共用体变量unTmp存储空间逻辑结构存储空间逻辑结构union union_test int nNum;long lNum;float fVal;char chArr4;unTmp;2/12/2023union采用覆盖技术,任何时刻共用体变量采用覆盖技术,任何时刻共用体变量只能代表一个成员变量。只能代表一个成员变量。struct变量各成员
47、变量各成员变量独立拥有自己的存储空间,任何时刻变量独立拥有自己的存储空间,任何时刻所有成员变量的值都是有效的。所有成员变量的值都是有效的。注意:注意:J任何时刻任何时刻union变量中变量中起作用的起作用的都是都是最后最后修改或赋值的成员变量修改或赋值的成员变量J如果最后一次对如果最后一次对union变量的修改性处理变量的修改性处理没有覆盖整个共用体存储空间,没有覆没有覆盖整个共用体存储空间,没有覆盖的部分将保持盖的部分将保持原有状态原有状态,在,在引用时要引用时要小心小心。2.从成员变量值的有效性上从成员变量值的有效性上2/12/2023直接通过圆点操作符直接通过圆点操作符引用引用 例例10
48、-21 共用体变量及其成员值的引用、赋共用体变量及其成员值的引用、赋值和初始化实例。值和初始化实例。结论结论共用体及其成员变量有相同首地址值共用体及其成员变量有相同首地址值共用体成员变量赋值前的值是随机的共用体成员变量赋值前的值是随机的成员变量赋值时,如果不是最大存储空间成员变量赋值时,如果不是最大存储空间成员,赋值操作不影响高位存储空间的状成员,赋值操作不影响高位存储空间的状态态(图图10-24)任何时刻都只有一个成员变量有效任何时刻都只有一个成员变量有效图图10-24中有下划线的部分是对应成员的中有下划线的部分是对应成员的有效值部分,阴影部分是无效值部分有效值部分,阴影部分是无效值部分u1
49、0.4.3 共用体变量的引用及其声明初始化共用体变量的引用及其声明初始化例如:例如:t.nNum=100时时FFD8和和FFD9字节的内字节的内容不受影响,容不受影响,t.chArr0=A对对FFD7、FFD8和和FFD9字节内容也不影响字节内容也不影响(图图10-24中的阴中的阴影部分影部分)。例如:例如:例例10-21中的中的4次赋值运算都只有刚被次赋值运算都只有刚被赋值的成员变量之值是有效和确定的。赋值的成员变量之值是有效和确定的。2/12/2023图图10-24 共用体及其成员的初值、共用体及其成员的初值、赋值和引用对比图示赋值和引用对比图示0111000001110000 01100
50、001011000010010000100100001 1000000010000000FFD9FFD9FFD8FFD8FFD7FFD7FFD6FFD6地址地址地址地址初始值初始值初始值初始值0111000001110000 01100001011000010000000000000000 0110010001100100t.nNum=t.nNum=1001000000000000000000 00000000000000000000000000000000 0110010001100100t.lNum=t.lNum=1001000100001001000010 110010001100100