結構體的記憶體對齊
:乙個結構體變數定義完之後,其在記憶體中的儲存並不等於其所包含元素的寬度之和。
例一:#include
使用命名空間性病;
結構x.
p1;void main()
比如例一中的結構體變數s1定義之後,測試發現sizeof(p1)= 16,其值不等於sizeof(p1.a)= 1,sizeof(p1.b)= 4和sizeof(p1.c)= 8三者之和,這裡面就存在儲存對齊問題。
原則一:結構體中元素是按照定義順序乙個乙個放到記憶體中去的
,但並不是緊密排列的從結構體儲存的首位址開始
,每乙個元素放置到記憶體中時,它都會認為記憶體是以它自己的大小來劃分的,因此元素放置的位置一定
會在自己寬度的整數倍上開始(以結構體變數首位址為0計算)。
上例中,首先系統會將字元型變數乙個存入第0個位元組;然後在存放整形變數b時,會以4個位元組為單位進行儲存,由於第乙個四位元組模組已有資料,因此它會存入第二個四位元組模組,也就是存入到4-8個位元組;接著存放雙精度實型變數ç時,由於其寬度為8,其存放時會以8個位元組為單位儲存,也就是會找到第乙個空的且是8的整數倍的位置開始儲存,此例中,由於頭乙個8位元組模組已被占用,所以將ç存入第二個8位元組模組。
例二:結構x.
p2;在例二中僅僅是將雙型的變數和int型的變數互換了位置。測試程式不變,測試結果卻截然不同,的sizeof(p2)= 24,不同於原則一計算出的8 + 8 + 4 = 20,這就引出了第二原則。
原則二:在經過第一原則分析後,檢查計算出的儲存單元是否為所有元素中最寬的元素的長度的整數倍,若是,則結束;否則,補齊為它的整數倍。
例二中,我們分析完後的儲存長度為20位元組,不是最寬元素長度8的整數倍,因此將它補齊到8的整數倍,也就是24。
。掌握了這兩個原則,就能夠分析所有資料儲存對齊問題了再舉例練習如下:
例:結構x.
p3;先按照第一原則分析,得到的位元組數為8 + 4 + 4 + 1 = 17;再按照第二原則補齊,則結結體變數p3所佔儲存空間為24但下例卻不同,
例: 結構x.
p4;同樣結合原則一和原則二分析,可知在p3的基礎上在結構體內部變數定義最後加入乙個int型變數後,結構體所佔空間並未增加,仍為24。
因為結構體所佔空間不但與其內部元素的型別有關,而且與不同型別元素的排列有關。因此在定義結構體時,在元素型別及數量確定之後,我們還應該注意一下其內部元素的定義順序。
位域:有些資訊在儲存時,並不需要占用乙個完整的位元組,而只需要佔幾個或乙個二進位制位例如在存放乙個開關變數時
,只有0,1兩種狀態,用一位二進位制位即可。為了節省儲存空間,並使處理簡單,c語言提供了一種資料結構,稱為「位域」或「位段」。所謂「位域」是把乙個位元組中的二進位制位劃分為
幾個不同的區域,每個區域有乙個網域名稱,並指定每個區域的位數,允許在程式中按網域名稱進行操作。
一,位域的定義和位域變數的說明位域定義與結構定義相仿,其形式為:
struct 位域結構名
;
其中位域列表的形式為:
型別說明符 位網域名稱:位域長度
位域變數的說明與結構變數說明的方式相同可採用先定義後說明,同時定義說明或者直接說明這三種方式例如。:
struct bs
data;
說明資料為bs變數,共佔兩個位元組。其中位域乙個佔8位,位域b佔2位,位域ç佔6位。
對於位域的定義有以下幾點說明:
1. 乙個位域必須儲存在同乙個位元組中
,不能跨兩個位元組
。如乙個位元組所剩空間不夠存放另一位域時
,應從下一單元起存放該位域。也可以有意使某位域從下一單元開始。
2.由於位域不允許跨兩個位元組,因此
位域的長度不能大於乙個位元組的長度。
3.
位域可以無位網域名稱
,這時它只用來作填充或調整位置。無名的位域是不能使用的。
二,位域的對齊
如果結構體中含有位域,準則是:
1)如果相鄰位域字段的型別相同,且其位寬之和小於型別的的sizeof大小,則後面的字段將緊鄰前乙個字段儲存,直到不能容納為止;
2)如果相鄰位域字段的型別相同,但其位寬之和大於型別的的sizeof大小,則後面的字段將從新的儲存單元開始,其偏移量為其型別大小的整數倍;
3)如果相鄰的位域字段的型別不同,則各編譯器的具體實現有差異,vc6採取不壓縮方式,dev-c ++和gcc都採取壓縮方式;
系統會先為結構體成員按照對齊方式分配空間和填塞,然後對變數進行位域操作。
結構體對齊(記憶體對齊
有的時候,在腦海中停頓了很久的 顯而易見 的東西,其實根本上就是錯誤的。就拿下面的問題來看 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計算 原則二 在經過第一原則分析後,檢查計算出的儲存...