C語言中構造類型一共有4種,它們分別是數(shù)組、結構體(struct)、共用體(union)、枚舉類型(enum)。
一、結構體類型
1、什么是結構體
在C語言中,結構體指的是一種數(shù)據(jù)結構,是C語言中聚合數(shù)據(jù)類型的一類。結構體可以被聲明為變量、指針或數(shù)組等,用以實現(xiàn)較復雜的數(shù)據(jù)結構。結構體同時也是一些元素的集合,這些元素稱為結構體的成員,且這些成員可以為不同的類型,成員一般用名字訪問。也就是說,結構體是由多種原宿所構成的數(shù)據(jù)結構。
2、定義結構體類型
struct 結構體
{
任意類型 任意變量;
任意類型 任意變量;
……
};
注意:這不是定義變量,而是自定義一種類型而已。如:
struct student
{
char name[10];//學生姓名
int height;//學生身高
bool sex;//學生性別 假設0表示女,1表示男。
};
3、 定義結構體變量
類型定義好以后,則可以定義該類型的變量。
?定義結構體變量:
struct student a,b;// struct可以省略。
可以在定義結構體變量的時候賦值。
如student a={”liudehua”,172,1},b={“l(fā)ixiaolong”,172,1};
?也可以在定義結構體變量以后賦值,但注意不能再用{}。如:
student a,b;
a={”liudehua”,172,1},b={“l(fā)ixiaolong”,172,1};//這是錯誤的。
?而應該是:
strcpy(a.name,”liudehua”);
a.height=172;
a.sex=1;
?可以在定義結構體類型的時候同時定義結構體變量并賦值。
struct student
{
char name[10];//學生姓名
int height;//學生身高
bool sex;//學生性別 假設0表示女,1表示男。
} a={”liudehua”,172,1},b={“aolong”,172,1};
4.訪問結構體
訪問結構體成員要用直接成員運算符“.”或間接成員運算符“->”。
#include < iostream >
struct student
{
char name[10];//學生姓名
int height;//學生身高
bool sex;//學生性別 假設0表示女,1表示男。
}a={"liudehua",182,1},b={"aolong",188,1};
int main()
{
struct student* x;
x=&a;
std::cout<
對于結構體變量,訪問其中的成員采取“結構體變量 . 成員”的形式;而對于結構體指針,訪問它所指向的結構體變量中的成員,則采取“結構體指針->成員”形式。
二、聯(lián)合體類型
1、什么是聯(lián)合體
聯(lián)合體也是一種自定義的復合類型,它可以包含多個不同類型的變量。這些變量在內(nèi)存當中共用一段空間。這段空間的size就是各變量中size最大的那個變量。
2、定義聯(lián)合體類型
union myunion
{
int num1;
double num2;
float num3;
};
定義了一個聯(lián)合體類型myunion。
myunion a,b;//定義了兩個myunion型變量。
也可以在定義聯(lián)合體類型的時候定義聯(lián)合體變量。如:
union myunion
{
int num1;
double num2;
float num3;
}a,b;
a占用的空間有多大呢?
Sizeof(a)結果即為8,即myunion占用8個字節(jié),和double型變量相同。
注意:任一時刻,只能訪問結構體里面的一個變量。
a.num1=2;
a.num2=3.154;
myunion *p;
p=&a;
p- >num3=5.6;
3、聯(lián)合體的使用
C++的聯(lián)合體(Union)與結構體相似,但它們的區(qū)別在于聯(lián)合體中只能同時存儲一個成員的值。這些成員共享同一個物理存儲空間,也就是說,一個聯(lián)合體的大小,等于它最大的成員變量所占據(jù)的空間。下面是一個示例代碼:
#include < iostream >
using namespace std;
??
union Person {
int age;
float height;
char name[50];
};
int main() {
union Person p1;
p1.age = 30;
cout < < "Age: " < < p1.age < < endl;
p1.height = 1.85;
cout < < "Height: " < < p1.height < < endl;
strcpy(p1.name, "John Doe");
cout < < "Name: " < < p1.name < < endl;
return 0;
}
在這個例子中,我們定義了一個名為“Person”的聯(lián)合體,包含三個不同數(shù)據(jù)類型的成員變量:整數(shù)、浮點數(shù)和字符數(shù)組。在main函數(shù)中,我們可以看到如何使用聯(lián)合體。在第一次賦值時,我們將age設置為30并輸出,然后我們將height設置為1.85并輸出,此時前一個賦值的值被覆蓋了。在最后一部分,我們使用strcpy函數(shù)將字符串賦給name成員變量并輸出。
需要注意的是,在實際應用聯(lián)合體時,必須小心使用,因為一個成員變量的更改會影響所有其他成員變量。同時,由于聯(lián)合體需要共享內(nèi)存,因此必須確保聯(lián)合體的大小能夠容納最大。
三、枚舉類型
1、什么是枚舉類型
枚舉類型是一種數(shù)據(jù)類型,它通常用來定義一個數(shù)字常量集合。在枚舉類型中,每個常量都有一個唯一的名稱和對應的數(shù)值。
2、枚舉類型的定義
枚舉類型也是一種自定義的復合類型。不過,枚舉類型中的成員都是常量。如
enum color
{
red,
green,
blue,
white,
black
}
枚舉類型中的成員默認值為從0開始,依次序遞增。此時red==1,green為2,blue為3,white為4,black為5.
也可以改變起默認值。如
enum color
{
red=1,
green=3,
blue=5,
white,
black
};
沒有初始化的枚舉類型成員的值將在它前面的成員基礎上遞增。所以,white的值為6,而black的值為7。
3、定義枚舉變量
color a1,a2;
4、給枚舉變量賦值:
a1=red;
a2=blue;
cout
雖然枚舉常量的值整數(shù),但是不能直接將整數(shù)值賦給枚舉變量。如
a1=1;//這是不對的。因為類型不匹配。一個是整型,一個是枚舉類型。
a1=(color)1;//正確
枚舉變量的size是一個整數(shù)的大小。
5、枚舉的使用
在C++中,枚舉類型可以用來定義一組常量。枚舉為程序員提供了一種方便的方式去定義一些有意義的名稱,而不是硬編碼數(shù)字,這樣代碼更易于理解和維護。下面是一個基本的枚舉示例:
#include < iostream >
using namespace std;
enum Weekday {
Monday = 1,
Tuesday,
Wednesday,
Thursday,
Friday,
Saturday,
Sunday
};
int main() {
Weekday today;
today = Tuesday;
if(today == Sunday){
cout< "Today is holiday!"<
在以上代碼中,我們定義了一個Weekday枚舉類型,將每個工作日映射到一個整數(shù)值上。默認情況下,第一個成員的值被設置為0,接著逐一自增,但我們可以使用顯式賦值來覆蓋它們。
在main函數(shù)中,我們聲明了一個名為today的變量,并且將其設置為Tuesday,通過if-else語句檢查是否為周日,然后輸出結果。需要注意的是,枚舉值可以與整數(shù)進行比較和賦值,因為每個成員都會被映射到一個整數(shù)值。
四、內(nèi)存對齊與內(nèi)存大小
1、內(nèi)存對齊
在C語言中,內(nèi)存對齊可以優(yōu)化程序的性能,而結構體是需要進行內(nèi)存對齊處理的數(shù)據(jù)類型。結構體的大小通常不僅取決于其中成員所占用的空間大小,還取決于操作系統(tǒng)和編譯器對于內(nèi)存對齊方式的處理。
具體地說,內(nèi)存對齊方式是為了符合硬件平臺訪問內(nèi)存數(shù)據(jù)的要求,并以此提高代碼的執(zhí)行效率。一般地,對于基本類型(如int、char、float等),系統(tǒng)通常會按照它們自身所占用的字節(jié)大小來進行內(nèi)存分配,并確保各個變量在內(nèi)存中的地址都是偶數(shù)或是四的倍數(shù)(這里假設系統(tǒng)采用的是32位架構)。
但如果結構體中的成員變量總大小不是4的倍數(shù),則在結構體中填充一些無用的字節(jié)使得結構體字節(jié)數(shù)是4的倍數(shù)。
2、結構體大小
舉例說明,假設有以下的結構體:
struct S1
{
char c1; // 1 byte
int i; // 4 bytes
char c2; // 1 bytes
};
int main()
{
std::cout< sizeof (S1)<
內(nèi)存對齊示意圖
它們總共占用的空間不是6字節(jié)(1+4+1),因為當前CPU硬件平臺一次最小訪問單位是4字節(jié),所以編譯器會自動進行內(nèi)存補齊,使得每個成員的地址都是4的倍數(shù),結構體的實際大小可能會是12字節(jié)(4字節(jié)對齊)或是8字節(jié)(1字節(jié)對齊)。所以,具體的內(nèi)存大小可能會因編譯器和硬件平臺的不同而異,并且有些編譯器可以通過一些指令來控制內(nèi)存對齊方式以提高程序效率。
對于這中浪費內(nèi)存的情況,作為程序員,我們在定義數(shù)據(jù)結構的時候完全可以避免。如下面:
struct S2
{
int i; // 4 bytes
char c1; // 1 byte
char c2; // 1 bytes
};
int main()
{
std::cout< sizeof (S2)<
**通過改變結構體里面變量的順序,避免內(nèi)存對齊帶來的空間浪費。內(nèi)存大小變?yōu)榱?,內(nèi)存節(jié)省了4個字節(jié)大小。
**
3、聯(lián)合體大小
C語言聯(lián)合體(union)的內(nèi)存大小取決于其中最大成員的大小。因為聯(lián)合體內(nèi)所有成員共用同一塊內(nèi)存區(qū)域,因此聯(lián)合體的大小必須足夠容納所有成員中最大的那個。
舉個例子,如果我們有一個聯(lián)合體定義如下:
union Example
{
int x;
char c;
double d;
};
那么這個聯(lián)合體的大小就是8個字節(jié)。因為這三個成員中最大的是double類型,占用8個字節(jié),其他成員對齊到8個字節(jié),所以整個聯(lián)合體大小是8個字節(jié)。
需要注意的是,聯(lián)合體的成員必須是同一種類型或者大小相同,這是因為它們會共用同一個內(nèi)存區(qū)域。如果不同類型的成員共存,可能會導致數(shù)據(jù)覆蓋或者讀取數(shù)據(jù)時出現(xiàn)未定義的行為。所以在使用聯(lián)合體時要特別小心,確保成員的類型和大小相同。
4、枚舉類型大小
在C語言中,枚舉類型(Enum)是一種自定義類型,用于表示有限個數(shù)的常量。在內(nèi)存中,枚舉類型通常被存儲為整數(shù)類型,其大小與int類型相同,即通常為4個字節(jié)或8個字節(jié)(取決于系統(tǒng)架構)。
當定義枚舉變量時,該變量的值由枚舉列表中對應常量的整數(shù)值來決定。在下面這個例子中,我們創(chuàng)建了一個Color枚舉類型,其中包含三個常量紅色、綠色和藍色,它們分別賦予值0、1和2。而變量c則被定義為Color類型并初始化為紅色。
#include< stdio.h >
enum Color {
RED,
GREEN,
BLUE
};
int main() {
enum Color c = RED;
printf("Sizeof enum: %d\\n", sizeof(enum Color)); //輸出為4或8字節(jié)
return 0;
}
需要注意的是,枚舉類型在內(nèi)存大小上可能會因為編譯器實現(xiàn)和程序運行的機器體系結構所影響。
-
C語言
+關注
關注
180文章
7614瀏覽量
137438 -
編譯器
+關注
關注
1文章
1642瀏覽量
49240 -
C++語言
+關注
關注
0文章
147瀏覽量
7021
發(fā)布評論請先 登錄
相關推薦
評論