位欄位
按位運算有多貴?假設一個簡單的非位欄位結構:
struct foo {
unsigned x;
unsigned y;
}
static struct foo my_var;
在以後的一些程式碼中:
my_var.y = 5;
如果 sizeof (unsigned) == 4
,則 x 儲存在結構的開頭,y 儲存在 4 個位元組中。生成的彙編程式碼可能類似於:
loada register1,#myvar ; get the address of the structure
storei register1[4],#0x05 ; put the value '5' at offset 4, e.g., set y=5
這很簡單,因為 x 不與 y 混合。但想象一下用位域重新定義結構:
struct foo {
unsigned x : 4; /* Range 0-0x0f, or 0 through 15 */
unsigned y : 4;
}
x
和 y
都將分配 4 位,共享一個位元組。結構因此佔用 1 個位元組而不是 8 個。考慮元件現在設定 y
,假設它最終在高位半位元組中:
loada register1,#myvar ; get the address of the structure
loadb register2,register1[0] ; get the byte from memory
andb register2,#0x0f ; zero out y in the byte, leaving x alone
orb register2,#0x50 ; put the 5 into the 'y' portion of the byte
stb register1[0],register2 ; put the modified byte back into memory
如果我們有數千或數百萬個這樣的結構,這可能是一個很好的權衡,它有助於將記憶體保留在快取中或防止交換 - 或者可能使可執行檔案變得臃腫,從而惡化這些問題並減慢處理速度。和所有事情一樣,要善於判斷。
裝置驅動程式的使用: 避免使用位欄位作為裝置驅動程式的巧妙實現策略。位元欄位儲存佈局在編譯器之間不一定是一致的,使得這種實現不可移植。對設定值的讀取 - 修改 - 寫入可能無法執行裝置所期望的操作,從而導致意外行為。