定義和使用結構體變量
自己建立結構體類型
用戶自己建立由不同類型數據組成的組合型的數據結構,它稱爲結構體
聲明一個結構體類型的一般形式爲:
struct 結構體名
{ 成員表列 };
**************************
struct Student{
int num;
char name[20];
char sex;
int age;
float score;
char addr[30];
}
上面這個的結構體類型爲 :struct Student
它包括num,name,sex,age,score,addr等不同類型的成員
注:結構體的成員可以是結構體
struct Date{
int month; int day; int year; };
struct Stu {
int num;char name[20];struct Date birthday;
};
定義結構體類型變量
定義結構體類型變量有以下幾種方法
-
先聲明結構體類型,再定義該類型變量。
聲明結構體類型struct Student
struct Student student1,student2;
student1
10001 Zhang Xin 19 Shanghai -
在聲明類型的同時定義變量
struct Student
{ int num;
char name[20];
int age;
char addr[30];
} student1,student2;
- 不指定類型名而直接定義結構體類型變量
struct
{ 成員表列 }
變量名錶列;
注:
- 結構體類型與結構體變量是不同的概念,不要混同。只能對變量賦值、存取或運算,而不能對一個類型賦值、存取或運算。在編譯時,對類型是不分配空間的,只對變量分配空間。
- 結構體類型中的成員名可以與程序中的變量名相同(儘量不要重名),但二者不代表同一對象。
- 對結構體變量中的成員(即“域”),可以單獨使用,它的作用與地位相當於普通變量。
結構體變量的初始化和引用
定義結構體數組一般形式是
① struct 結構體名
{成員表列}
數組名[數組長度];
② 先聲明一個結構體類型,然後再用此類型定義結構體數組:
結構體類型 數組名[數組長度];
如:
struct Person leader[3];
直接看例子,就是定義一個學生信息的結構體,然後對他初始化輸出
#include <stdio.h>
int main( ){
struct Studen{
long int num;
char name[20];
char sex;
char addr[20];
}
a={10101,"Li Lin",'M',"Beijing"};
printf("NO.:%ld\nname:%s\n sex:%c\naddress:%s\n",
a.num,a.name,a.sex,a.addr);
return 0;
}
NO.:10101
name:Li Lin
sex:M
address:Beijing
下面這些是對上面的補充
a.num=10010; 對
printf(“%s\n”,a); 不對
struct Student b;
b=a; 對
b.num++; 對
scanf(″%ld″,&a.num); 對
printf(″%o″,&a); 對
scanf(“%ld,%s,%c,%s\n”,&a); 錯
a.birthday.month=12; 對
a.age=10; b.age=9; 對
sum=a.age+b.age; 對
使用結構體數組
定義結構體數組
還是從例題入手,理論多沒意思啊
例:有3個候選人,每個選民只能投票選一人,要求編一個統計選票的程序,先後輸入被選人的名字,最後輸出各人得票結果。
#include <string.h>
#include <stdio.h>
struct person // 聲明結構體類型struct person
{char name[20]; // 候選人姓名
int count; // 候選人得票數
}leader[3]={"Li",0,"Zhang",0,"Fun",0}; // 定義結構體數組並初始化
int main()
{int i,j;
char leader_name[20]; // 定義字符數組
for (i=1;i<=10;i++)
{scanf("%s",leader_name); // 輸入所選的候選人姓名
for(j=0;j<3;j++)
if(strcmp(leader_name,leader[j].name)==0) leader[j].count++;
}
printf("\nResoult:\n");
for(i=0;i<3;i++)
printf("%5s:%d\n",leader[i].name,leader[i].count);
return 0;
}
前面設了一個結構體,裏面包含name和count,後面leader是數組名3是數組長度
L、Z、S就是三個人的名字,有10個人投票,strcmp是判斷兩個字符是否i相等,是就爲0,不是就爲1。
結構體指針
指向結構體變量的指針
指向結構體對象的指針變量既可以指向結構體變量,也可以用來指向結構體數組中的元素。
指針變量的基類型必須與結構體變量的類型相同。例如:
struct Student *pt;
通過指向結構體變量的指針變量輸出結構體變量中成員的信息
#include <stdio.h>
#include <string.h>
int main(){
struct student
{long num;
char name[20];
char sex;
float score;
};
struct student stu_1; // 定義struct student類型的變量stu_1
struct student * p; // 定義指向struct student 類型數據的指針變量p
p=&stu_1; // p指向stu_1
stu_1.num=10101; // 對結構體變量的成員賦值
strcpy(stu_1.name,"Li Lin");
stu_1.sex='M';
stu_1.score=89.5;
printf("No.:%ld\nname:%s\nsex:%c\nscore:%5.1f\n",
stu_1.num,stu_1.name,stu_1.sex,stu_1.score); // 輸出結果
printf("\nNo.:%ld\nname:%s\nsex:%c\nscore:%5.1f\n",
(*p).num,(*p).name,(*p).sex, (*p).score);
return 0;
}
可以看到*p也是這個結構體的,p指向同一類型(student類型)的stu_1,下面兩種輸出方式結果是一樣的。*p就是取p存的內容,就是stu_1
指向結構體數組的指針
有3個學生的信息,放在結構體數組中,要求輸出全部學生的信息
#include <stdio.h>
struct student
{int num;
char name[20];
char sex;
int age;
};
struct student stu[3]={{10101,"Li Lin",'M',18},
{10102,"Zhang Fun",'M',19},
{10104,"Wang Min",'F',20}}; // 定義結構體數組並初始化
int main(){
struct student *p; //定義指向struct student結構體的數組
printf(" No. Name sex age\n");
for (p=stu;p<stu+3;p++)
printf("%5d %-20s %2c %4d\n",p->num, p->name, p->sex, p->age);
return 0;
}
爲了使用方便和直觀,C語言允許把(*p).num用p->num來代替
(*p).name等價於p->name
用指針處理鏈表
什麼是鏈表
鏈表是一種常見的重要的數據結構
它是動態地進行存儲分配的一種結構
鏈表必須利用指針變量才能實現
建立簡單的靜態鏈表
建立一個如圖所示的簡單鏈表,它由3個學生數據的結點組成,要求輸出各結點中的數據。
#include <stdio.h>
struct student // 聲明結構體類型struct student
{int num;
float score;
struct student *next;
};
int main()
{struct student a,b,c,*head,*p; // 定義3個結構體變量作爲鏈表的結點
a.num=10101; a.score=89.5; // 對結點a的num和score成員賦值
b.num=10103; b.score=90; // 對結點b的num和score成員賦值
c.num=10107; c.score=85; // 對結點c的num和score成員賦值
head=&a; // 將結點a的起始地址賦給頭指針head
a.next=&b; // 將結點b的起始地址賦給a結點的next成員
b.next=&c; // 將結點c的起始地址賦給a結點的next成員
c.next=NULL; // c結點的next成員不存放其他結點地址
p=head; // 使p也指向a結點
do
{printf("%ld %5.1f\n",p->num,p->score); // 輸出p指向的結點的數據
p=p->next; // 使p指向下一結點
}while(p!=NULL); // 輸出完c結點後p的值爲NULL,循環終止
return 0;
}
共用體類型
有時想用同一段內存單元存放不同類型的變量。
使幾個不同的變量共享同一段內存的結構,稱爲 “共用體”類型的結構。
定義共用體類型變量的一般形式爲:
union 共用體名
{ 成員表列
}變量表列;
union Data
{ int i;
char ch;
float f;
};
union Data a,b,c;
“共用體”與“結構體”的定義形式相似,但它們的含義是不同的。
結構體變量所佔內存長度是各成員佔的內存長度之和,每個成員分別佔有其自己的內存單元。而共用體變量所佔的內存長度等於最長的成員的長度。
引用共用體變量的方式
只有先定義了共用體變量才能引用它,但應注意,不能引用共用體變量,而只能引用共用體變量中的成員。
例如,前面定義了a,b,c爲共用體變量,下面的引用方式是正確的:
a.i a.ch a.f
共用體類型數據的特點
- 同一個內存段可以用來存放幾種不同類型的成員,但在每一瞬時只能存放其中一個成員,而不是同時存放幾個。
- 可以對共用體變量初始化,但初始化表中只能有一個常量。
- 共用體變量中起作用的成員是最後一次被賦值的成員,在對共用體變量中的一個成員賦值後,原有變量存儲單元中的值就取代。
- 共用體變量的地址和它的各成員的地址都是同一地址。
- 不能對共用體變量名賦值,也不能企圖引用變量名來得到一個值
- 以前的C規定不能把共用體變量作爲函數參數,但可以使用指向共用體變量的指針作函數參數。C99允許用共用體變量作爲函數參數。
- 共用體類型可以出現在結構體類型定義中,也可以定義共用體數組。反之,結構體也可以出現在共用體類型定義中,數組也可以作爲共用體的成員。
有若干個人員的數據,其中有學生和教師。學生的數據中包括:姓名、號碼、性別、職業、班級。教師的數據包括:姓名、號碼、性別、職業、職務。要求用同一個表格來處理。
#include <stdio.h>
#include <malloc.h>
#define LEN sizeof(struct student)
struct student
{long num;
float score; struct student *next;
};
int n;
struct student *creat()
{struct student *head;
struct student *p1,*p2;
n=0;
p1=p2=( struct student*) malloc(LEN);
scanf("%ld,%f",&p1->num,&p1->score);
head=NULL;
while(p1->num!=0)
{n=n+1;
if(n==1)head=p1;
else p2->next=p1;
p2=p1;
p1=(struct student*)malloc(LEN);
scanf("%ld,%f",&p1->num,&p1->score);
}
p2->next=NULL;
return(head);
}
void print(struct student *head)
{struct student *p;
printf("\nNow,These %d records are:\n",n);
p=head;
if(head!=NULL)
do
{printf("%ld %5.1f\n",p->num,p->score);
p=p->next;
}while(p!=NULL);
}
int main()
{struct student *head ;
head=creat();
print(head);
return 0;
}
算了我也沒懂嘿嘿這個用到再仔細研究吧。
畢竟是小白,從小白視角看可能不會太深,但像我一樣的小白應該都能看懂。
這篇博客主要是寫給新手的,希望大家都能學懂學好,嘿嘿,寫的不好還望大佬勿噴。