1:簡單理解,結構體就是數組的進一步發展,數據的優點和缺陷在於數據裡面是元素類型必須相同,但是結構體沒有這個要求,結構體裡面元素的類型可以相同也可以不同。
2:結構體的定義:
struct student
{
int age;
char name[20];
}s1;
上面這種方法是結構體定義的同時定義變量,結構體的定義有兩部分組成
struct studen:結構體的類型
s1:類型為struct student的結構體變量,當然還可以用struct studet s2;l來定義變量s2
注意結構體裡面的元素不能再創建的時候直接賦值,而是要通過外部訪問來對結構體進行填充
3:結構體裡面變量的訪問
結構體裡面的元素訪問方式有兩種,一種是 . 一種是->,但其實質上都是通過指針來訪問的。
C語言規定用結構體的變量來訪問結構體的時候是用 . 用結構體變量的指針來訪問結構體的時候用->
4:結構體的對齊訪問
首先要知道一點,我們使用 . 的方式來訪問結構體時是不同考慮結構體內存對齊問題的,這部分編譯器會幫我們處理,但是如果我們想通過指針方式來訪問結構體裡面的各元素的時候就需要考慮內存對齊的問題。結構體內存對齊訪問一個主要原因是硬件本身的物理限制,使用對齊訪問可以提高訪問的效率。但是內存對齊也會帶來內存空間浪費的問題,所以內存對齊訪問實際上是通過犧牲內存空間來換取的速度。
5:結構體對齊的規則和運算
編譯器本身可以設置內存對齊的規則,但是一下幾點規則需要記住
(1)32位編譯器,一般米、默認是4字節對齊
(2)結構體整體本身必須安置在4字節對齊處,也就是結構體的首地址必須是4整數的倍數(如果編譯設置為n字節對齊訪問,則首地址就是n的整數倍(n = 1 2 4 8 16 ...))
(3)結構體中每個元素本身必須對齊存放
(4)整個結構體的所占的內存空間必須是4的整數倍(同樣如果是n字節對齊就是n的整數倍)
struct mystruct1
{ //1字節對齊 //4字節對齊
int a; // 4 // 4
char b; //1 // 2
short c; //2 // 2
}mystr1;
struct mystruct2
{ //1字節對齊 //4字節對齊
char a; // 1 // 4 (1+3)3字節填充
int b; //4 // 4
short c; //2 // 4 (2 +2)2字節填充
}mystr2;
分析:
首先是整個結構體,整個結構體變量4字節對齊是由編譯器保證的,然後再是第一個元素a,a的開始抵制就是整個結構體的開始地址,所以自然就是4字節對齊的,但是的結束地址此時是不確定的,得由下一個元素決定;
第二個元素b,因為上一個元素a本身占4字節,其本身就是對齊的,所以留給b的開始地址也是4字節對齊,所以b就可直接存放(b存放的開始位置就決定a要占多少個字節,這裡因為元素a字節剛好滿足4字節對齊,不需要進行填充,所以這裡a就占4字節),b的起始地址決定後,結束地址的確定需要依賴於下一個元素,原因是可能要進行填充,並且下一個元素的類型不通,則需要填充的字節數也是不同的;