版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)
文檔簡介
第八章結(jié)構(gòu)體8.1概述8.2定義結(jié)構(gòu)體變量的方法8.3結(jié)構(gòu)體變量的初始化8.4結(jié)構(gòu)體變量的引用8.5結(jié)構(gòu)體數(shù)組8.6指向結(jié)構(gòu)體數(shù)據(jù)的指針8.7用指針處理鏈表8.1概述
在實(shí)際問題中我們常需要把不同類型的幾個(gè)數(shù)據(jù)組合起來,構(gòu)成一個(gè)整體。如一個(gè)公司職員的個(gè)人信息,或?qū)W校中教師和學(xué)生的信息。以學(xué)生信息為例,它可能包括學(xué)生的學(xué)號(hào)、班級(jí)、姓名、性別、年齡、成績等。這時(shí)原有的那些數(shù)據(jù)類型就顯的有點(diǎn)無能為力了,所以引入一種新的數(shù)據(jù)類型----結(jié)構(gòu)體。結(jié)構(gòu)體是由一些邏輯相關(guān),但數(shù)據(jù)類型不同的分量組成的一組數(shù)據(jù)。注意:用戶需要先定義結(jié)構(gòu)體類型,之后才能定義結(jié)構(gòu)體變量注意不要忘了分號(hào)成員列表結(jié)構(gòu)體類型定義形式:struct
結(jié)構(gòu)體類型名{數(shù)據(jù)類型成員名1;
數(shù)據(jù)類型成員名2;::
數(shù)據(jù)類型成員名n;};關(guān)鍵字用戶定義的標(biāo)識(shí)符8.2定義結(jié)構(gòu)體變量的方法一、定義結(jié)構(gòu)體變量1.先定義結(jié)構(gòu)體類型,
再定義變量
structstudent{charname[10];
intage;floats1,s2;};
structstudentst1,st2;st1st2nameages1s2nameages1s2結(jié)構(gòu)體變量st1和st2各自都需要20個(gè)字節(jié)的存儲(chǔ)空間2.定義結(jié)構(gòu)體類型同時(shí)定義變量
structstudent{charname[10];
intage;floats1,s2;}
st1,st2;3.直接定義結(jié)構(gòu)體變量
struct
{charname[10];
intage;floats1,s2;}
st1,st2;4.說明:(1)結(jié)構(gòu)體變量具有結(jié)構(gòu)體類型的一切特征在內(nèi)存中結(jié)構(gòu)體變量占有一片連續(xù)的存儲(chǔ)單元存儲(chǔ)單元的字節(jié)數(shù)可用sizeof
運(yùn)算符算出
printf(“%d\n”,sizeof(structstudent));
printf(“%d\n”,sizeof(st1));(2)結(jié)構(gòu)體類型可以嵌套定義
例:structdate{intyear;
intmonth;
intday;};
structstud{charname[10];
structdatebirthday;floats1,s2;};
或:structstud{charname[10];
structdate{intyear;
intmonth;
intday;}
birthday;floats1,s2;};8.3結(jié)構(gòu)體變量的初始化structstudent{charname[10];
intage;floatscore1,score2;}st1={“Mary”,21,78,86};structstud{charname[10];
structdatebirthday;floatscore1,score2;};structstudst2={“John”,1980,11,23,89,95};structstudent{charname[10];
intage;floatscore1,score2;};structstudentst3;st3={“Mary”,21,78,86};正確初始化錯(cuò)誤,C不允許這樣賦值正確初始化8.4結(jié)構(gòu)體變量的引用1.引用結(jié)構(gòu)體變量中的成員
格式:
結(jié)構(gòu)體變量名.成員名structstudent{charname[10];
intage;floats1,s2;};注意:一般是對(duì)結(jié)構(gòu)體變量的各個(gè)成員分別進(jìn)行賦值st1={“Mary”,21,78,86};這樣的賦值是不允許的structstudentst1;strcpy(,“Mary”);st1.age=21;st1.s1=78;st1.s2=86;structdate{int
year;
intmonth;
intday;};structstud{charname[10];
int
age;
structdatebirthday;floats1,s2;};structstudst2;intage,year;strcpy(,“John”);st2.age=20;
st2.birthday.year=1980;st2.birthday.month=11;st2.birthday.day=23;st2.s1=89;st2.s2=95;age=24;year=2000;可以定義與結(jié)構(gòu)體變量成員名相同名字的變量它們之間不會(huì)發(fā)生混亂2.相同類型的結(jié)構(gòu)體變量可以進(jìn)行整體賦值
structdate{intyear;
intmonth;
intday;};structstud{charname[10];
intage;
structdatebirthday;floats1,s2;};structstudst1,st2,st3;strcpy(,“John”);st1.age=20;st1.birthday.year=1980;st1.birthday.month=11;st1.birthday.day=23;st1.s1=89;st1.s2=95;st2=st1;strcpy(,“Mary”);st3.age=20;st3.birthday=st1.birthday;st3.s1=76;st3.s2=85;注意要正確賦值的條件是變量st1已經(jīng)有了初值3.結(jié)構(gòu)體變量的輸入輸出
C語言不允許結(jié)構(gòu)體變量整體進(jìn)行輸入和輸出,
只能對(duì)結(jié)構(gòu)體變量的成員進(jìn)行輸入和輸出gets(
);scanf(“%d%d%d”,&st1.birthday.year,
&st1.birthday.month,&st1.birthday.day
);scanf(“%d%f%f”,&st1.age,&st1.s1,&st1.s2
);
puts();printf(“%4d”,st1.age);printf(“%d.%d.%d”,st1.birthday.year,st1.birthday.month,st1.birthday.day);printf(“%5.2f%5.2f\n”,st1.s1,st1.s2);8.5結(jié)構(gòu)體數(shù)組
一、結(jié)構(gòu)體數(shù)組的定義
1.先定義結(jié)構(gòu)體類型再定義結(jié)構(gòu)體數(shù)組
structstudent
{charname[10];
intage;floats1,s2;};
structstudentst[6];2.定義結(jié)構(gòu)體類型的同時(shí)定義數(shù)組
structstudent{charname[10];
intage;floats1,s2;}st[6];
3.直接定義結(jié)構(gòu)體數(shù)組
struct
{charname[10];
intage;floats1,s2;}st[6];
二、結(jié)構(gòu)體數(shù)組的初始化
將每個(gè)數(shù)組元素的數(shù)據(jù)用花括號(hào){}括起來structstudent{charname[10];
intage;floats1,s2;};structstudentst[3]={{“Mary”,21,78,86},
{“Alex”,20,90,80},{“Mike”,19,75,68}};Mary217886Alex209080Mike197568st[0]st[1]st[2]2.數(shù)組元素之間可以整體賦值也可以將一個(gè)元素賦給一個(gè)相同類型的結(jié)構(gòu)體變量
structstudentx,st[3]={{“Mary”,21,78,86},{“Alex”,…}};
st[2]=st[0];x=st[1];3.只能對(duì)數(shù)組元素的成員進(jìn)行輸入和輸出gets(st[2].name);scanf(“%d”,&st[2].age
);scanf(“%f%f”,&st[2].s1,&st[2].s2);puts(st[0].name);printf(“%4d%5.2f%5.2f\n”,st[0].age,st[0].s1,st[0].s2);都是結(jié)構(gòu)體變量的整體賦值三、結(jié)構(gòu)體數(shù)組的引用1.引用某個(gè)數(shù)組元素的成員例:
puts(st[0].name);
printf(“%d,%d”,st[1].age,st[1].s1);例:有30名學(xué)生,輸入每個(gè)學(xué)生信息包括學(xué)號(hào)、姓名、成績,要求找出成績最高者,并輸出他的信息#include<stdio.h>#defineN30voidmain(){structstudent{intn;charname[10];
intscore;};
structstudent
st[N];
inti,m;
intmax;for(i=0;i<N;i++)
scanf(“%d%s%d”,&st[i].n,st[i].name,&st[i].score);
max=st[0].score;for(i=1;i<N;i++)if(st[i].score>max){max=st[i].score;m=i;}printf(“%4d”,st[m].n);printf(“%10s”,st[m].name);printf(“%5d”,st[m].score);}例:按成績對(duì)學(xué)生信息進(jìn)行從高到底的排序#include<stdio.h>#defineN30voidmain(){
structstud{intn;charname[10];
ints;};
structstud
a[N],temp;
inti,j,k;for(i=0;i<N;i++)
scanf(“%d%s%d”,&a[i].n,a[i].name,&a[i].s);for(i=0;i<N-1;i++){for(j=i+1;j<N;j++)if(a[i].s<a[j].s)k=j;temp=a[k];
a[k]=a[i];
a[i]=temp;}for(i=0;i<N;i++)printf(“%4d%10s%4d”,
a[i].n,a[i].name,a[i].s);}8.6指向結(jié)構(gòu)體數(shù)據(jù)的指針
一、指向結(jié)構(gòu)體變量的指針
1.定義
structstudent{charname[20];
intage;floats1,s2;};
structstudentstu,*p;
p=&stu;2.成員的引用格式(1)
結(jié)構(gòu)體變量名.成員名
gets();(*p).age=21;p->s1=87;p->s2=90;(2)(*指針變量名).成員名
(*p).age(3)指針變量名->成員名
p->s1p只能指向一個(gè)結(jié)構(gòu)體變量,如:p=&stu;而不能指向結(jié)構(gòu)體變量的一個(gè)成員。如:p=&stu.age;是非法的。
->運(yùn)算符的優(yōu)先級(jí)最高。例如:struct
{charname[20];
intage;}*p;則表達(dá)式:
++p->age:表示age的值增加1。等價(jià)于++(p->age)
使用結(jié)構(gòu)體指針變量應(yīng)注意以下幾點(diǎn):
p不是結(jié)構(gòu)體變量(是指向結(jié)構(gòu)體變量的指針),因此不能寫成成員引用方式p.age的形式。二、指向結(jié)構(gòu)體數(shù)組的指針1.定義structstudentst[3],*p;2.使用for(p=st;p<st+3;p++){gets(p->name);
scanf(“%d%d
%d”,&p->age,&p->s1,&p->s2);}對(duì)于指向結(jié)構(gòu)體數(shù)組的指針:p只能指向一個(gè)結(jié)構(gòu)體數(shù)組的一個(gè)元素(相當(dāng)于變量),然后用->指向運(yùn)算符取其成員的值,而不能直接指向一個(gè)數(shù)組元素的成員。(++p)->age:表示p指針指向下一個(gè)數(shù)組元素后,再訪問其成員age。(p++)->age:先訪問age操作,再對(duì)指針p加1,使其指向下一個(gè)數(shù)組元素。結(jié)構(gòu)體變量作為函數(shù)參數(shù)1.函數(shù)的實(shí)參和形參都用結(jié)構(gòu)體變量,參數(shù)之間為值傳遞即:實(shí)參結(jié)構(gòu)體變量各成員的值依次傳給形參結(jié)構(gòu)體變量2.返回結(jié)構(gòu)體類型值的函數(shù)函數(shù)定義格式:結(jié)構(gòu)體類型名函數(shù)名(形參表列){函數(shù)體;}
例:structstudentfunct(intx,floaty){函數(shù)體;}注意結(jié)構(gòu)體類型是已經(jīng)定義好的三、結(jié)構(gòu)體與函數(shù)注意結(jié)構(gòu)變量作為參數(shù)傳遞時(shí),其實(shí)參與形參的結(jié)構(gòu)類型必須一致,傳遞時(shí)其實(shí)參只需指定其結(jié)構(gòu)變量名即可。當(dāng)實(shí)參為數(shù)組時(shí),其形參可以定義為同類型結(jié)構(gòu)的結(jié)構(gòu)數(shù)組或結(jié)構(gòu)指針。與普通變量一樣,結(jié)構(gòu)變量在函數(shù)內(nèi)部定義時(shí)為局部的,其值只在本函數(shù)范圍內(nèi)有效,不會(huì)影響其它函數(shù)將結(jié)構(gòu)傳遞給函數(shù)的方式有三種傳遞單個(gè)成員傳遞整個(gè)結(jié)構(gòu)傳遞指向結(jié)構(gòu)的指針傳遞結(jié)構(gòu)變量的地址可以實(shí)現(xiàn)結(jié)構(gòu)的傳址調(diào)用。結(jié)構(gòu)數(shù)組也可作為函數(shù)參數(shù)傳遞。在調(diào)用print時(shí),&stud做實(shí)參,將stud的地址傳遞給函數(shù)的形參p,這時(shí)p指向了結(jié)構(gòu)變量
stud的成員值。#include<string.h>#defineFORMAT“%d\n%s\n%6.2f\n”
structstudent{intnum;charname[20];floatscore;};main(){voidprint();
structstudentstud;stud.num=1001;
strcpy(,”michell”);stud.score=90.9;
print(&stud);}voidprint(structstudent*p){
printf(FORMAT,p->num,p->name,p->score);
printf(“\n”);}例:求學(xué)生成績的總分和平均分
#include<stdio.h>#defineN5structstud{charname[10];
ints[3];floatsum,ave;};structstudcomp(structstudx){intj;x.sum=0;for(j=0;j<3;j++)
x.sum=x.sum+x.s[j];
x.ave=x.sum/3;
return(x);}voidmain(){structstuda[N];
intj;for(j=0;j<N;j++){scanf(“%s%d%d%d”,a[j].name,&a[j].s[0],&a[j].s[1],&a[j].s[2]);}for(j=0;j<N;j++)a[j]=comp(a[j]);
for(j=0;j<N;j++){printf(“%10s%4d”,a[j].name,a[j].s[0]);printf(“%4d%4d”,a[j].s[1],a[j].s[2]);printf(“%8.2f%6.2f\n”,a[j].sum,a[j].ave);}}例:按成績對(duì)學(xué)生信息進(jìn)行從高到底的排序#include<stdio.h>#defineN30structstud{intn;charname[10];
ints;};voidinput(structstuda[]){inti;for(i=0;i<N;i++)
scanf(“%d%s%d”,&a[i].n,
a[i].name,&a[i].s);}
voidoutput(structstuda[]){inti;for(i=0;i<N;i++)printf(“%4d%10s%4d”,a[i].n,a[i].name,a[i].s);}
voidsort(structstuda[]){inti,j,k;
structstudtemp;for(i=0;i<N-1;i++){k=i;for(j=i+1;j<N;j++)if(a[i].s<a[j].s)k=j;
if(k!=i){temp=a[k];
a[k]=a[i];
a[i]=temp;}}}voidmain(){structstud
st[N];
input(st);
sort(st);
output(st);}8.7利用結(jié)構(gòu)體組織鏈表一、基本概念1.動(dòng)態(tài)存儲(chǔ)分配:根據(jù)需要臨時(shí)分配內(nèi)存單元用以存放數(shù)據(jù),
當(dāng)數(shù)據(jù)不用時(shí)可以隨時(shí)釋放內(nèi)存單元2.鏈表:是可以動(dòng)態(tài)地進(jìn)行存儲(chǔ)分配的一種數(shù)據(jù)結(jié)構(gòu)它是由一組動(dòng)態(tài)數(shù)據(jù)鏈接而成的序列3.結(jié)點(diǎn):鏈表中的每一個(gè)動(dòng)態(tài)數(shù)據(jù)稱為一個(gè)結(jié)點(diǎn)4.結(jié)點(diǎn)類型:是一個(gè)包含指針項(xiàng)的結(jié)構(gòu)體類型
一般由兩部分組成:(1)數(shù)據(jù)成員:存放數(shù)據(jù)(2)指針成員:存放下一個(gè)結(jié)點(diǎn)的地址struct
sd{intnum;
intscore;
struct
sd*next;};數(shù)據(jù)成員指針成員頭指針表頭結(jié)點(diǎn)表尾結(jié)點(diǎn)2010head2010142815709514281861570282NULL3NULL為空地址,表示鏈表到此結(jié)束二、簡單鏈表#include<stdio.h>struct
sd{intnum;
intscore;
struct
sd*next;};voidmain(){struct
sda,b,c,*head,*p;
head=&a;a.num=1;a.score=95;a.next=&b;b.num=2;b.score=86;b.next=&c;c.num=3;c.score=82;c.next=NULL;
p=head;while(p!=NULL){printf(“%3d%4d\n”,p->num,p->score);
p=p->next;}}head2010142815702010abc19514282861570382NULLp201014281570NULL說明:該程序雖然建立了一個(gè)鏈表,但這個(gè)鏈表是靜態(tài)的,因?yàn)樗慕Y(jié)點(diǎn)個(gè)數(shù)是固定的,不能按需要增加新的結(jié)點(diǎn),也不能按需要?jiǎng)h除結(jié)點(diǎn).這樣的鏈表并不實(shí)用,我們需要的是“動(dòng)態(tài)鏈表”三、處理動(dòng)態(tài)鏈表所需的函數(shù)(需用頭文件<stdlib.h>)1.malloc
函數(shù)原型:void*malloc(unsignedintsize)
作用:在內(nèi)存中開辟一個(gè)長度為size的連續(xù)存儲(chǔ)空間,
并將此存儲(chǔ)空間的起始地址帶回注意:(1)函數(shù)返回值是指針,但該指針是指向void類型的,因此在使用時(shí)希望這個(gè)指針指向其他類型需要用強(qiáng)制類型轉(zhuǎn)換(2)如果內(nèi)存缺少足夠大的空間進(jìn)行分配,則malloc
函數(shù)返回值為“空指針”(即NULL)例:struct
sd*p;p=(struct
sd*)
malloc(sizeof(struct
sd));強(qiáng)制類型轉(zhuǎn)換結(jié)構(gòu)體類型占用的字節(jié)長度2.free函數(shù)原型:voidfree(void*ptr)
作用:將指針變量ptr指向的存儲(chǔ)空間釋放注意:(1)ptr的值不是任意的地址,必須是程序中執(zhí)行malloc或
calloc函數(shù)所返回的地址(2)模型中ptr是void型,但調(diào)用free函數(shù)時(shí),參數(shù)可能是其他類型,計(jì)算機(jī)系統(tǒng)會(huì)自動(dòng)進(jìn)行轉(zhuǎn)換例:struct
sd*p;p=(struct
sd*)malloc(sizeof(struct
sd));
free(p);p42004200
四、鏈表應(yīng)用舉例
1.建立鏈表(表尾添加法)
#include<stdio.h>#include<stdlib.h>#defineSTstructstudentST{intnum;
intscore;ST*next;};#defineLENsizeof(ST)
intn;宏定義ST,以后書寫簡單求出結(jié)構(gòu)體類型占用的字節(jié)數(shù)全局量,n表示結(jié)點(diǎn)的個(gè)數(shù)ST*creat(void){ST*head,*p1,*p2;n=0;head=NULL;p1=(ST*)malloc(LEN);
scanf(“%d%d”,&p1->num,&p1->score);while(p1->num!=0){n=n+1;if(n==1)head=p1;elsep2->next=p1;p2=p1;p1=(ST*)malloc(LEN);
scanf(“%d%d”,&p1->num,&p1->score);}
p2->next=NULL;return(head);}head201014281570NULLp1p232642010201010951428n012320101428208630820014281570NULL1570157032642.輸出鏈表voidlist(ST*head){ST*p;p=head;while(p!=NULL){printf(“%3d%4d\n”,p->num,p->score);
p=p->next;
}}head201014281570201010951428208615703082NULLp201014281570NULLp120101428num20p22010head20101428157020101095142828615703082NULL1570n323.鏈表的刪除ST*del(ST*head,intnum){ST*p1,*p2;p1=head;while((num!=p1->num)&&(p1->next!=NULL)){p2=p1;p1=p1->next;}if(num==p1->num){if(p1==head)head=p1->next;elsep2->next=p1->next;
free(p1);n=n-1;
printf(“deleted!\n”);}else
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。
最新文檔
- 2024年建筑工人勞動(dòng)合同樣本
- 2024年度互聯(lián)網(wǎng)金融服務(wù)平臺(tái)技術(shù)開發(fā)與運(yùn)營合同
- 2024年工程文件保密與轉(zhuǎn)讓協(xié)議
- 2024醫(yī)療器械銷售及市場推廣合同
- 2024年公共交通乘車意外傷害保險(xiǎn)合同
- 2024年度居民搬家服務(wù)定制合同
- 2024年工程建設(shè)的擔(dān)保協(xié)議
- 2024年勞動(dòng)力外包合作協(xié)議
- 2024年度股權(quán)轉(zhuǎn)讓合同模板
- 2024人工智能技術(shù)研發(fā)合同-科技創(chuàng)新合作
- 2023年事故序列模型介紹
- 兒童免疫性疾病課件
- 中圖版八年級(jí)地理上冊(cè)《世界氣候》復(fù)習(xí)課件
- 無損檢測通用作業(yè)指導(dǎo)書
- 2023年中考語文復(fù)習(xí):150個(gè)文言實(shí)詞-課件(共183張PPT)
- 車輛維修服務(wù)方案先進(jìn)性
- 2020年1月上海春招英語聽力(含試題、MP3、答案及錄音)
- GB/T 17639-2023土工合成材料長絲紡粘針刺非織造土工布
- 發(fā)行企業(yè)債法律盡職調(diào)查之訪談問題清單
- 拍賣合作協(xié)議
- 白改黑施工組織設(shè)計(jì)
評(píng)論
0/150
提交評(píng)論