C結構體的記憶體對齊

2022-06-05 10:12:08 字數 1335 閱讀 1859

pack 可以指定記憶體對齊值,單位是位元組,這個是值需要時2的次冪(1,2,4,6,8)。如不設定也有預設值,這個值我理解的是作業系統的字長。

#pragma pack(8)
結構體第乙個成員放在struct offset 0 的位置。

計算每個成員的對齊值,計算方式:min(size(成員), 預設對齊值)。

計算總體的對齊值,計算方式:min(max(所有成員的大小), 預設對齊值)。

上面的說明較為籠統,下面使用乙個例子來解釋。

# include # pragma pack(8)     # 手動設定對齊值。如不手動設定這個值,不同環境這個值不同,不方面我們接下來的計算。

struct tag1 ;

首先將double型別的a,存放在tag1結構體offset=0的位址上,double型別長度是8,更新offset是8.

計算int b變數的對齊值,min(size(int), 預設對齊值) = min(4, 8) = 4, 然後判斷offset是4的正整數倍數,顯然是。將b變數放置在9的位置,此時offset變更成12.

計算char c變數的對齊值,min(size(char), 預設對齊值) = 1, 然後判斷offset是不是4的整數倍呢?12是1的正整數倍,將c變數放置在13位置。

最後,計算總的對齊值,min(max(double、int、char), 預設對齊值) = min(8, 8) = 8, 13不是8的正整數倍數,填充到16。

最終 c語言的sizeof(struct tag1) 的最終值是 16.

接下來將double 與 int的順序修改下

# include # pragma pack(8)     # 手動設定對齊值。如不手動設定這個值,不同環境這個值不同,不方面我們接下來的計算。

struct tag1 ;

首先將int型別b,放在tag1結構體offset=0的位址上,更新offset=4.

接下來計算變數double a的對齊值,min(8, 8) = 8, 判斷offset=4不是8的整數倍,填充到16(為什麼是16?因為需要是8的最小正整數倍),此時offset=16。

接下來計算變數char c的對齊值,min(1, 8) = 1, 判斷offset=16是1的整數倍,將c變數放在17的位置。

最後計算總的對齊值,min(max(int、double、char), 預設對齊值) = min(8, 8) = 8, 17不是8的正數倍,填充到24.

最終 sizeof(struct tag1) 的值是 24.

主要流程差不多,把內部的結構體當作乙個變數,先計算這個變數的sizeof。

結構體對齊(記憶體對齊

有的時候,在腦海中停頓了很久的 顯而易見 的東西,其實根本上就是錯誤的。就拿下面的問題來看 structt 使用sizeof t 將得到什麼樣的答案呢?要是以前,想都不用想,在32位機中,int是4個位元組,char是1個位元組,所以t一共是5個位元組。實踐出真知,在vc6中測試了下,答案確實8個位...

記憶體對齊 結構體對齊

現在已知32位機器上各種資料型別的長度如下 char 1 有符號無符號同 short 2 有符號無符號同 int 4 有符號無符號同 long 4 有符號無符號同 float 4 double 8 重要規則 1,複雜型別中各個成員按照它們被宣告的順序在記憶體中順序儲存,第乙個成員的位址和整個型別的位...

結構體的記憶體對齊

原則一 結構體中元素是按照定義順序乙個乙個放到記憶體中去的,但並不是緊密排列的。從結構體儲存的首位址開始,每乙個元素放置到記憶體中時,它都會認為記憶體是以它自己的大小來劃分的,因此元素放置的位置一定會在自己寬度的整數倍上開始 以結構體變數首位址為0計算 原則二 在經過第一原則分析後,檢查計算出的儲存...