C語言 結構體內存對齊

2021-09-11 06:40:11 字數 1525 閱讀 7237

1、平台原因

不是所有硬體平台都能夠訪問任意位址上的任意資料的,某些硬體平台只能在某些位址處取某些特定型別的資料,否則丟擲硬體異常。

2、效能原因(主要原因)

資料結構(尤其是棧)應該盡可能地在自然邊界上對齊。 原因在於,為了訪問未對齊的記憶體,處理器需要作兩次記憶體訪問;而對齊的記憶體訪問僅需要一次訪問。

這裡我們舉個例子說明一下

注:記憶體對齊是以空間換時間的做法

1、結構體的第乙個變數必須放在結構體空間起始位置偏移量為0的位址處。

2、結構體的其餘變數必須放在某個對齊數整數倍處。

3、這個對齊數是結構體變數的大小與預設對齊數的較小值。

4、預設對齊數:vs下的預設對齊數是:8

linux gcc編譯器下的預設對齊數是:4

5、結構體的總大小必須是所有結構體變數對齊數的最大值的整數倍。

6、 如果巢狀了結構體的情況,巢狀的結構體對齊到自己的最大對齊數的整數倍處,結構體的整體大小就是所有結構體變數對齊數中最大對齊數(含巢狀結構體的對齊數)的整數倍。

下面我們來看幾個練習,深入了解一下結構體內存對齊的規則

//練習1

struct s1

;//練習2

struct s2

;int main()

在計算結構體大小之前,先在這裡介紹乙個巨集offsetof,用於計算結構體變數在結構體空間起始位置的偏移量,使用格式為

再來看兩個稍微複雜一點的練習

struct s3

;//總空間大小:0-15 共16位元組

//練習4-結構體巢狀問題

struct s4

;//總空間大小:0-31 共32個位元組

int main()

實現方法其實很簡單,只需要使用預處理命令#pragma pack(),將你想改的對齊數寫在括號中即可,修改預設對齊數。

看看**實現

//修改預設對齊數

#include #pragma pack(8)//設定預設對齊數為8

struct s1

;#pragma pack()//取消設定的預設對齊數,還原為預設

#pragma pack(1)//設定預設對齊數為1

struct s2

;#pragma pack()//取消設定的預設對齊數,還原為預設

int main()

C語言結構體內存對齊

1.效能原因 為了提高cup的效率訪問記憶體的速度,若是訪問未對齊的記憶體,處理器需要作兩次訪問 而訪問對齊的記憶體,則只需要一次訪問。2.編譯器相關 有的編譯器已經優化了記憶體對齊,所以記憶體對齊依賴於編譯器。參考 結構體對齊問題 說實話,規則看起來不太好理解,直接模仿下面步驟即可 以32位機器為...

C語言結構體內存對齊

記憶體中存放資料的時候要有一定的規則,這麼做得根本原因是要減少cpu訪問記憶體的次數。舉個例子,int型別為4個位元組,存放int型別的記憶體的起始位址就是4的倍數,這樣cpu訪問一次記憶體就能夠取到資料 跟cpu訪問記憶體的機制有關,加上cache的對映,一般cpu一次訪問64位元組的資料,也有1...

C語言結構體內存對齊

問題 求32bit環境下以下結構體所佔的位元組數 在32bit環境中,該結構體所佔的位元組數為16。先記住關於結構體內存對齊的三條原則 1 結構體變數的起始位址能夠被其最寬的成員大小整除。2 結構體每個成員相對於起始位址的偏移能夠被其自身大小整除,如果不能則在前乙個成員後面補充位元組。3 結構體總體...