C語言結(jié)構(gòu)體struct詳解
結(jié)構(gòu)體的概念
結(jié)構(gòu)體是由一系列具有相同類型或不同類型的數(shù)據(jù)構(gòu)成的數(shù)據(jù)集合。組成結(jié)構(gòu)型數(shù)據(jù)的每個數(shù)據(jù)稱為結(jié)構(gòu)型數(shù)據(jù)的“成員”。結(jié)構(gòu)體通常用來表示類型不同但是又相關(guān)的若干數(shù)據(jù)。
結(jié)構(gòu)體類型的聲明
結(jié)構(gòu)體類型的聲明要使用 s t r u c t \color{#0000FF}{ struct} struct關(guān)鍵字,舉個例子,比如我要定義一個學(xué)生的結(jié)構(gòu)體類型,學(xué)生有姓名,年齡,學(xué)號等等。那么我就可以這樣聲明一個學(xué)生的結(jié)構(gòu)體類型:
struct stu { char name[20];//姓名 int age;//年齡 char id[15];//學(xué)號 };
我在聲明學(xué)生這個結(jié)構(gòu)體的時候,只寫了姓名,年齡和學(xué)號。如果想定義其它的變量也可以在結(jié)構(gòu)體里面定義。struct stu就是結(jié)構(gòu)體類型,不能省略struct。結(jié)構(gòu)的成員可以是標(biāo)量、數(shù)組、指針,甚至是其他結(jié)構(gòu)體。
結(jié)構(gòu)體變量的創(chuàng)建
struct stu { char name[20];//姓名 int age;//年齡 char id[15];//學(xué)號 }s1,s2,s3;//全局變量 int main() { //局部變量 struct stu s4; struct stu s5; return 0; }
看上面這段代碼,結(jié)構(gòu)體變量的定義可以在聲明結(jié)構(gòu)體類型的時候直接創(chuàng)建,如果直接創(chuàng)建就像s1,s2,s3。那么s1,s2,s3就是全局變量。也可以在主函數(shù)中通過struct stu這個結(jié)構(gòu)體類型創(chuàng)建結(jié)構(gòu)體變量,像s4和s5,在主函數(shù)中創(chuàng)建的結(jié)構(gòu)體變量就是局部變量。
typedef關(guān)鍵字
給大家再補充一個知識點,就是 typedef關(guān)鍵字。我相信大家在學(xué)習(xí)結(jié)構(gòu)體或者數(shù)據(jù)結(jié)構(gòu)的時候也見過這個關(guān)鍵字,一般都是配合結(jié)構(gòu)體使用,所以 我們還是要掌握typedef關(guān)鍵字。
typedef用新的類型名代替原有的類型名。簡單點來說typedef就是一個重命名的關(guān)鍵字。
看下面這段代碼:
#include<stdio.h> typedef int data;//將data定義成int類型 int main() { data a = 5; printf("%d", a); return 0; }
我用typedef將data變成了int類型,那么我就可以使用data創(chuàng)建的變量就是一個整型的變量,此時輸出的結(jié)果就是5,沒有任何問題。
不光是數(shù)據(jù)類型可以使用typedef進行重命名,結(jié)構(gòu)體也是可以的。在結(jié)構(gòu)體中使用typedef關(guān)鍵字一般有兩種寫法。
#include<stdio.h> typedef struct stu { char name[20];//姓名 int age;//年齡 char id[15];//學(xué)號 }Stu; int main() { struct stu s4; struct stu s5; Stu s6; return 0; }
像這種寫法,就是直接對結(jié)構(gòu)體進行重命名,但是此時就無法創(chuàng)建結(jié)構(gòu)體的全局變量。在主函數(shù)中可以通過結(jié)構(gòu)體類型來創(chuàng)建變量,也可以通過重命名后的名字直接創(chuàng)建變量。我們來看另外一種寫法。
#include<stdio.h> struct stu { char name[20];//姓名 int age;//年齡 char id[15];//學(xué)號 }s1,s2,s3; typedef struct stu Stu; int main() { struct stu s4; struct stu s5; Stu s6; return 0; }
像這種創(chuàng)建的方法就可以創(chuàng)建全局變量,其實兩種方法的原理差不多,都是**typedef struct stu Stu;**只是位置不同罷了。
結(jié)構(gòu)體的嵌套
結(jié)構(gòu)體的嵌套就是在一個結(jié)構(gòu)體里面再放一個結(jié)構(gòu)體。舉個例子:
struct score { float Chinese; float Math; float Enlish; float ave; }; struct stu { char name[20];//姓名 int age;//年齡 char id[15];//學(xué)號 struct score Score; }s1, s2, s3;
我在學(xué)生這個結(jié)構(gòu)體里面嵌套了一個分?jǐn)?shù)的結(jié)構(gòu)體,結(jié)構(gòu)體的嵌套還是挺簡單的,不過有一點需要注意, 結(jié)構(gòu)體的嵌套是有順序的。 \color{#0000FF}{結(jié)構(gòu)體的嵌套是有順序的。} 結(jié)構(gòu)體的嵌套是有順序的。 因為我是再學(xué)生這個結(jié)構(gòu)體里面嵌套的分?jǐn)?shù)這個結(jié)構(gòu)體,所以我要先聲明分?jǐn)?shù)這個結(jié)構(gòu)體,如果把它放在學(xué)生結(jié)構(gòu)體的下面,代碼就會報錯。
結(jié)構(gòu)體變量的初始化
結(jié)構(gòu)體的初始化是用{}進行初始化,如果是嵌套的結(jié)構(gòu)體里面也要用{},給大家演示一下,很簡單,一看就能看懂。
#include<stdio.h> struct score { float Chinese; float Math; float Enlish; }Score1={63.4,56.8,51.3}; struct stu { char name[20];//姓名 int age;//年齡 char id[15];//學(xué)號 struct score Score2; }s1, s2, s3; int main() { struct stu s4 = { "張三", 15, "20220805", {63.4,56.8,51.3} }; struct stu s5; return 0; }
可以在創(chuàng)建成員變量時直接初始化,也可以在主函數(shù)中進行初始化。
結(jié)構(gòu)體成員的訪問
結(jié)構(gòu)體成員的訪問有兩種方式,一種是 '.’,一種是’->'。舉個例子:
#include<stdio.h> struct score { float Chinese; float Math; float Enlish; }Score1={63.4,56.8,51.3}; struct stu { char name[20];//姓名 int age;//年齡 char id[15];//學(xué)號 struct score Score2; }s1, s2, s3; int main() { struct stu s4 = { "張三", 15, "20220805", {63.4,56.8,51.3} }; struct stu s5; printf("%s\n", s4.name); printf("%d\n", s4.age); printf("%.1f\n", s4.Score2.Chinese); return 0; }
如果要輸出結(jié)構(gòu)體的成員的值,那么就可以通過結(jié)構(gòu)體變量.結(jié)構(gòu)體成員進行輸出。
下面來看另外一種訪問方式,通過->進行訪問通常是結(jié)構(gòu)體指針->結(jié)構(gòu)體成員。
#include<stdio.h> struct stu { char name[20];//姓名 int age;//年齡 char id[15];//學(xué)號 struct score Score2; }s1, s2, s3; void print(struct stu* sp) { printf("%s", sp->name); } int main() { struct stu s4 = { "張三", 15, "20220805", {63.4,56.8,51.3} ,5}; print(&s4);; return 0; }
這些內(nèi)容都不是很難,大家多多練習(xí)應(yīng)該就可以掌握。
結(jié)構(gòu)體的傳參
先看下下面這段代碼:
#include<stdio.h> struct stu { char name[20];//姓名 int age;//年齡 char id[15];//學(xué)號 }s1, s2, s3; void print1(struct stu sp1) { printf("%s\n", sp1.name); } void print2(struct stu* sp2) { printf("%s\n", sp2->name); } int main() { struct stu s4 = { "張三", 15, "20220805" }; print1(s4); print2(&s4); return 0; }
那么對于print1 和 print2這兩個函數(shù),哪一個好點?
答案是print2函數(shù)
函數(shù)傳參的時候,參數(shù)是需要壓棧的。
如果傳遞一個結(jié)構(gòu)體對象的時候,結(jié)構(gòu)體過大,參數(shù)壓棧的的系統(tǒng)開銷比較大,所以會導(dǎo)致性能的 下降。
結(jié)論:結(jié)構(gòu)體傳參的時候,要傳結(jié)構(gòu)體的地址。
總結(jié)
結(jié)構(gòu)體這部分比較簡單,不過也是學(xué)習(xí)數(shù)據(jù)結(jié)構(gòu)的過程中很重要的一部分,大家還是要熟練掌握結(jié)構(gòu)體。
到此這篇關(guān)于C語言結(jié)構(gòu)體struct詳解的文章就介紹到這了,更多相關(guān)C語言結(jié)構(gòu)體內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
C語言字符串函數(shù)與內(nèi)存函數(shù)精講
這篇文章主要介紹一些c語言中常用字符串函數(shù)和內(nèi)存函數(shù)的使用,并且為了幫助讀者理解和使用,也都模擬實現(xiàn)了他們的代碼,需要的朋友可以參考一下2022-04-04C++面試八股文之std::string實現(xiàn)方法
這篇文章主要介紹了C++面試八股文:std::string是如何實現(xiàn)的,本文給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下2023-06-06C語言實現(xiàn)打印九九乘法表的四種方式小結(jié)
這篇文章主要為大家介紹了C語言實現(xiàn)打印九九乘法表的四種方式,文中的示例代碼講解詳細(xì),簡潔易懂,感興趣的小伙伴可以跟隨小編一起學(xué)習(xí)一下2023-07-07