




版權說明:本文檔由用戶提供并上傳,收益歸屬內容提供方,若內容存在侵權,請進行舉報或認領
文檔簡介
第十一章結構和聯合
概述本章將主要介紹C語言中的構造數據類型:結構體、聯合以及用戶自定義類型等。知識點結構體的定義、變量的說明和引用聯合定義、變量的說明和引用本章章節11.1結構的說明與引用 11.2結構數組的聲明、引用和初始化 11.3聯合11.4應用程序舉例 11.5常見錯誤解析 11.6本章小結11.1結構的說明與引用“結構”是一種構造類型,它是由若干“成員”組成的。每一個成員可以是一個基本數據類型或者又是一個構造類型。定義一個結構的一般形式為:struct結構名
{成員表列};成員表列由若干個成員組成,每個成員都是該結構的一個組成部分。對每個成員也必須作類型說明,其形式為:類型說明符成員名;例如:
structstu{intnum;charname[20];charsex;floatscore;};在這個結構定義中,結構名為stu,該結構由4個成員組成。第一個成員為num,整型變量;第二個成員為name,字符數組;第三個成員為sex,字符變量;第四個成員為score,實型變量。說明結構變量有以下三種方法先定義結構,再說明結構變量。如:structstu{intnum;charname[20];charsex;floatscore;};structstustudent1,student2;在定義結構類型的同時說明結構變量。例如:structstu{intnum;charname[20];charsex;floatscore;}student1,student2;直接說明結構變量。例如:struct{intnum;charname[20];charsex;floatscore;}student1,student2;這種形式的說明的一般形式為:struct{成員表列}變量名表列;三種方法中說明的student1,student2變量都具有下圖所示的結構成員也可以又是一個結構,即構成了嵌套的結構。,下圖給出了另一個數據結構。按圖可給出以下結構定義:structdate{intmonth;intday;intyear;};Struct{intnum;charname[20];charsex;structdatebirthday;floatscore;}student1,student2;首先定義一個結構date,由month(月)、day(日)、year(年)三個成員組成。在定義并說明變量student1和student2時,其中的成員birthday被說明為data結構類型。成員名可與程序中其它變量同名,互不干擾。定義了結構體變量以后,便可以引用這個變量。
引用時應遵循以下規則:(1)不能將一個結構體變量作為一個整體進行輸入和輸出。只能對結構體變量中的各個成員分別進行輸入和輸出。例如,已定義student1和student2為結構體變量并且它們已有值。不能這樣引用:printf(”%ld,%s,%c,%d,%f”,student1);
也不能用以下語句整體讀入結構體變量,如:scanf(”%ld,%s,%c,%d,%d”,&student1);但可以通過賦值語句,把一個結構體變量的值賦給同類型的結構體變量中。例如:student2=student1;則student2和student1具有相同的內容。引用結構體變量中成員的方式為:結構體變量名.成員名例如:student1.num
即第一個人的學號student2.sex即第二個人的性別如果成員本身又是一個結構則必須逐級找到最低級的成員才能使用。只能對最低級的成員進行賦值、存取以及運算。例如:student1.birthday.month可以對變量的成員賦值,例如:student1.num=200201001(2)對結構體變量的成員可以像普通變量一樣進行各種運算。例如:student2.score=student1.score;sum=student1.score+student2.score;student1.age++;由于“.”運算符的優先級最高,因此student1.age++是對student1.age進行自加運算,而不是先對age進行自加運算。(3)可以引用結構體變量成員的地址,也可以引用結構體變量的地址。如:scanf(”%ld”,&sl.num); (輸入student1.num的值)printf(”%o”,&student1); (輸出student1的首地址)結構體變量的地址主要用于作函數參數,傳遞結構體的地址。(4)結構體變量的初始化和其他類型變量一樣,對結構體變量可以在定義時指定初始值。例如:structstu{longnum;charname[15];charsex;intage;intscore;}student1={200201001,”zhangsan”,’M’,18,86};經過初始化后,student1.num=200201001=”zhangsan”student1.sex=’M’student1.age=18student1.score=86[例1]用輸入語句或賦值語句來完成給結構變量賦值并輸出其值。#include"stdio.h"
intmain(){structstu{ intnum; char*name; charsex; floatscore;}student1,student2;student1.num=102;="Zhangping";printf("inputsexandscore\n");scanf("%c%f",&student1.sex,&student1.score);student2=student1;printf("Number=%d\nName=%s\n",student2.num,);printf("Sex=%c\nScore=%f\n",student2.sex,student2.score);
return0;}11.2結構數組的聲明、引用和初始化結構數組的每一個元素都是具有相同結構類型的下標結構變量。在實際應用中,經常用結構數組來表示具有相同數據結構的一個群體。如一個班的學生檔案,一個車間職工的工資表等。例如:structstu{intnum;char*name;charsex;floatscore;}student[5];定義了一個結構數組student,共有5個元素,student[0]~student[4]。每個數組元素都具有structstu的結構形式。對結構數組可以作初始化賦值。例如:structstu{intnum;char*name;charsex;floatscore;}student[5]={{101,"Limiao","M",45},{102,"Zhangping","M",62.5},{103,"Hefang","F",92.5},{104,"Chengling","F",87},{105,"Wangming","M",58}};當對全部元素作初始化賦值時,也可不給出數組長度。【例2】計算學生的平均成績和不及格的人數。#include"stdio.h"structstu{intnum;char*name;charsex;floatscore;}student[5]={{101,"Limiao",'M',45},{102,"Zhangping",'M',62.5},{103,"Hefang",'F',92.5},{104,"Chengling",'F',87},{105,"Wangming",'M',58},};intmain(){inti,c=0;floatave,s=0;for(i=0;i<5;i++){s+=student[i].score;if(student[i].score<60)c+=1;}printf("s=%.2f\n",s);ave=s/5;printf("average=%.2f\ncount=%d\n",ave,c);return0;}【例3】建立同學通訊錄#include"stdio.h"#defineNUM3structAddressBook{charname[20];charphone[10];};intmain(){structAddressBookClassMate[NUM];inti;for(i=0;i<NUM;i++){ printf("inputname:\n"); gets(ClassMate[i].name); printf("inputphone:\n"); gets(ClassMate[i].phone);}printf("name\t\t\tphone\n\n");for(i=0;i<NUM;i++)printf("%s\t\t\t%s\n",ClassMate[i].name,ClassMate[i].phone);return0;}11.3聯合“聯合”與“結構”有一些相似之處。但兩者有本質上的不同。在結構中各成員有各自的內存空間,一個結構變量的總長度是各成員長度之和。而在“聯合”中,各成員共享一段內存空間,一個聯合變量的長度等于各成員中最長的長度。應該說明的是,這里所謂的共享不是指把多個成員同時裝入一個聯合變量內,而是指該聯合變量可被賦予任一成員值,但每次只能賦一種值,賦入新值則沖去舊值。一個聯合類型必須經過定義之后,才能把變量說明為該聯合類型。當一個聯合被說明時,編譯程序自動地產生一個變量,其長度為聯合中最大的變量長度。聯合訪問其成員的方法與結構相同。同樣聯合變量也可以定義成數組或指針,但定義為指針時,也要用"->"符號,此時聯合訪問成員可表示成:聯合名->成員名。聯合的定義
聯合也是一種新的數據類型,它是一種特殊形式的變量。
聯合變量定義與結構十分相似。其形式為:union聯合名
{成員表
};成員表中含有若干成員,成員的一般形式為:類型說明符成員名
成員名的命名應符合標識符的規定。
例如:定義一個聯合變量“data”。
uniondata{chara;intb;floatc;};該共用體的名稱為data,該共用體中有三個成員,分別為a、b、c。它們占用同一個起始地址的存儲空間,內存長度等于最長的成員的長度。需要注意的是:聯合定義之后,即可進行聯合變量說明,被說明為data類型的變量,可以存放字符型量a或整型量b或存放浮點型量c。要么賦予字符型量,要么賦予整型量,要么賦予浮點型量,不能把3者同時賦予它。
聯合既可以出現在結構內,它的成員也可以是結構
例如:Struct{intage;char*addr;union{inti;char*ch;}x;}y[10];若要訪問結構變量y[1]中聯合x的成員i,可以寫成:y[1].x.i;若要訪問結構變量y[2]中聯合x的字符串指針ch的第一個字符可寫成:*y[2].x.ch;若寫成"y[2].x.*ch;"是錯誤的。2、聯合變量的說明
聯合變量的說明和結構變量的說明方式相同,也有三種形式。即先定義,再說明、定義同時說明和直接說明。以聯合變量department為例,說明如下:uniondepartment{intgrade;charoffice;};uniondepartmenta,b;/*說明a,b為department類型*/或者:uniondepartment{intgrade;charoffice;}a,b;/*同時說明a,b為department類型*/或者:union{intgrade;charoffice;}a,b/*直接說明a,b為department類型*/
經說明后的a,b變量均為department類型。a,b變量的長度應等于department的成員中最長的長度,即等于office數組的長度,共10個字節。a,b變量如賦予整型值時,只使用了2個字節,而賦予字符數組時,可用10個字節。
3、聯合變量的賦值和使用
對聯合變量的賦值、使用都只能是對變量的成員進行。聯合變量的成員表示為:聯合變量名.成員名例如,a被說明為department類型的變量之后,可使用
a.grade或a.office。不允許只用聯合變量名作賦值或其它操作。也不允許對聯合變量作初始化賦值,賦值只能在程序中進行一個聯合變量,每次只能賦予一個成員值。一個聯合變量的值就是聯合變員的某一個成員值。【例11-4】設有一個教師與學生通用的表格,教師數據有姓名,年齡,身份,教研室四項。學生有姓名,年齡,身份,班級四項。編程輸入人員數據,再以表格輸出。
#include<stdio.h>#defineN3intmain(){struct{charname[15];intage;charstatus;union{intgrade;charoffice[20];}depa;}body[3];inti;for(i=0;i<N;i++){ printf("inputname:\n");/*提示語*/ gets(body[i].name);/*gets函數接收帶空格的姓名*/ printf("inputage:\n");scanf("%d",&body[i].age);getchar();/*吸收上一句輸入的回車符*/printf("inputstatus(sort):\n"); body[i].status=getchar();if(body[i].status=='s') {getchar();/*吸收上一句輸入的回車符*/ printf("inputgrade:\n"); scanf("%d",&body[i].depa.grade);getchar();/*吸收上一句輸入的回車符*/ } else {getchar();/*吸收上一句輸入的回車符*/ printf("inputoffice:\n"); gets(body[i].depa.office); } }printf("name\t\tagestatusgrade/office\n");for(i=0;i<N;i++)
{if(body[i].status=='s')printf("%15s\t%3d%3c%20d\n",body[i].name,body[i].age,body[i].status,body[i].depa.grade);/*對齊輸出數據*/else printf("%15s\t%3d%3c%20s\n",body[i].name,body[i].age,body[i].status,body[i].depa.office);/*對齊輸出數據*/
} return0;}說明:在處理結構體問題時經常涉及字符或字符串的輸入,這時要注意:①scanf()函數用%s輸入字符串遇空格即結束,因此輸入帶空格的字符串可改用gets函數。②在輸入字符類型數據時往往得到的是空白符(空格、回車等),甚至運行終止,因此常作相應處理,即在適當的地方增加getchar();空輸入語句,以消除緩沖區中的空白符。類型定義符typedefC語言不僅提供了豐富的數據類型,而且還允許由用戶自己定義類型說明符,也就是說允許由用戶為數據類型取“別名”。類型定義符typedef即可用來完成此功能。typedef定義的一般形式為:typedef原類型名
新類型名
其中原類型名中含有定義部分,新類型名一般用大寫表示,以便于區別。有時也可用宏定義來代替typedef的功能,但是宏定義是由預處理完成的,而typedef則是在編譯時完成的,后者更為靈活方便。例如,有整型量a,b,其說明如下:inta,b;int的完整寫法為integer,為了增加程序的可讀性,可把整型說明符用typedef定義為:typedefintINTEGER這以后就可用INTEGER來代替int作整型變量的類型說明了。
例如:INTEGERa,b;它等效于:inta,b;用typedef定義數組、指針、結構等類型將帶來很大的方便,不僅使程序書寫簡單而且使意義更為明確,因而增強了可讀性。
例如:typedefcharNAME[20];表示NAME是字符數組類型,數組長度為20。然后可用NAME說明變量,如:NAMEa1,a2,s1,s2;完全等效于:chara1[20],a2[20],s1[20],s2[20]又如:typedefstructstu{charname[20];intage;charsex;}STU;定義STU表示stu的結構類型,然后可用STU來說明結構變量:STUbody1,body2;11.4應用程序舉例【例5】一個公司有10名員工,每個員工的數據包括職工號、姓名、生日和工資。請使用結構體表示員工的信息,并用結構體數組來存所有員工的數據。要求輸入10名員工的信息,計算平均工資,并輸出工資最高的員工的數據。然后對上述的員工數據數組按工資從大到小排序,并輸出排序后各員工的信息。#include<stdio.h>#defineN3/*員工個數N在下列各個函數內的數值都是10,是不變的。*/floatavesalary;structst{ intnum; charname[20]; charbirth[20]; floatsalary;};voidinput(structsta[])/*輸入所有員工信息*/{ inti; for(i=0;i<N;i++){ printf("職工號,姓名,出生日期,工資:\n"); scanf("%d%s%s%f",&a[i].num,a[i].name,&a[i].birth,&a[i].salary); }}voidaves(structstb[])/*求出所有員工的平均工資*/{ inti; floattotal=0; for(i=0;i<N;i++) total=total+b[i].salary; avesalary=total/N;}voidsort(structstc[])/*按員工工資從高到低進行排序*/{ inti,j; structstt; for(i=0;i<N-1;i++) for(j=0;j<N-1-i;j++) if(c[j].salary<c[j+1].salary) { t=c[j]; c[j]=c[j+1]; c[j+1]=t; }}voidoutputmax(structstd[])/*輸出最高工資的員工信息*/{ printf("最高工資的員工信息:職工號%d,姓名%s,生日%s,工資%.2f\n",d[0].num,d[0].name,d[0].birth,d[0].salary);}voidoutputall(structst
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯系上傳者。文件的所有權益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網頁內容里面會有圖紙預覽,若沒有圖紙預覽就沒有圖紙。
- 4. 未經權益所有人同意不得將文件中的內容挪作商業或盈利用途。
- 5. 人人文庫網僅提供信息存儲空間,僅對用戶上傳內容的表現方式做保護處理,對用戶上傳分享的文檔內容本身不做任何修改或編輯,并不能對任何下載內容負責。
- 6. 下載文件中如有侵權或不適當內容,請與我們聯系,我們立即糾正。
- 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 海淀區2024-2025學年高一化學下學期單元測試(化學反應原理基礎檢測)真題解析
- 2025年美國學術十項全能(USAD)社會科學模擬試卷:歷史與經濟學能力提升
- 2025年計算機二級MySQL知識提升試題及答案
- 2025年考研政治中國近現代史綱要圖表題歷史事件發展目標試題卷
- 2025年西班牙語DELEC1模擬試卷:旅游體驗分享與高級語言組織
- 患者昏迷的應急預案與流程
- 濱江區高三年級英語下學期模擬考試概要寫作技巧評估試卷
- 2025年劍橋英語CAE(C1)模擬試卷深度剖析:商務英語與高級寫作技巧揭秘
- IGCSE中文第一語言2024-2025模擬試卷:文言文閱讀與寫作技巧提升
- 2025年托福聽力天文講座專項訓練:天文科普教育與公眾參與解析卷
- 糖尿病酮癥完整版本
- 五年級下冊數學約分練習100題附答案
- 跨文化交流中的語言適應性研究
- 第5.2課 《飛向太空的航程》同步練習 (原卷版)
- 新概念英語第二冊Lesson8課件
- 地攤市集活動策劃方案
- 勞務外包與勞務派遣課件
- 白酒行業財務知識培訓課件
- 智慧倉儲配送機器人案例
- 中醫護理-生活起居的護理內容
- 《商標權授權與侵權》課件
評論
0/150
提交評論