Chuẩn (9,6 của the working draft) nói điều này:
quy định cụ thể một chút trường; chiều dài của nó được đặt ra từ tên trường bit bằng dấu hai chấm. Thuộc tính trường bit không phải là một phần của loại thành viên lớp . Biểu thức hằng số phải là một biểu thức không đổi không đổi với một giá trị lớn hơn hoặc bằng không. Biểu thức hằng số có thể lớn hơn số bit trong biểu diễn đối tượng ( 3.9) của loại trường bit; trong trường hợp này, các bit phụ được sử dụng như các bit đệm và không tham gia vào biểu diễn giá trị ( 3.9) của trường bit. Phân bổ các trường bit trong một đối tượng lớp được xác định thực hiện. Căn chỉnh các trường bit là được thực hiện theo định nghĩa. Các trường bit được đóng gói vào một số đơn vị phân bổ địa chỉ . [Lưu ý: các trường bit phân bổ các đơn vị phân bổ trên một số máy chứ không phải trên các máy khác. Các trường bit được gán từ phải sang trái trên một số máy, từ trái sang phải trên các máy khác. lưu ý end]
(tôi nhấn mạnh)
Vì vậy, nó sẽ phụ thuộc vào trình biên dịch của bạn. Điều gì dường như đang xảy ra trong trường hợp của bạn - và tôi sẽ mô tả hành vi khá bình thường - là nó chỉ kết hợp các bitfield cùng loại và sau đó đóng gói cấu trúc đến một ranh giới 4 byte, vì vậy trong trường hợp đầu tiên chúng ta có:
struct a {
uint32_t foreColor_ : 32; // 4 bytes (total)
uint32_t backColor_ : 32; // 8 bytes
uint16_t lfHeight_ : 16; // 10 bytes
uint16_t flags_: 4; // 12 bytes
bool lfBold_: 1; // 13 bytes
bool lfItalic_: 1;
bool lfUnderLine_: 1;
bool lfDashLine_: 1;
bool lfStrike_: 1;
bool lfSubscript_: 1;
bool lfSuperscript_: 1; // still 13 bytes
};
đó là sau đó đệm đến 16 byte, và trong lần thứ hai chúng ta có:
struct a {
uint32_t foreColor_ : 32; // 4 bytes (total)
uint32_t backColor_ : 32; // 8 bytes
uint16_t lfHeight_ : 16; // 10 bytes
uint8_t flags_: 4; // 11 bytes
bool lfBold_: 1; // 12 bytes
bool lfItalic_: 1;
bool lfUnderLine_: 1;
bool lfDashLine_: 1;
bool lfStrike_: 1;
bool lfSubscript_: 1;
bool lfSuperscript_: 1; // still 12 bytes
};
Mà không cần đệm và vẫn ở mức 12 byte.
Nguồn
2013-09-04 10:33:26
Không sử dụng các loại như 'uint32_t' cho một trường bit một chút ngớ ngẩn? (Nói chung, chúng chỉ nên được sử dụng khi bạn cần khớp chính xác với định dạng bên ngoài, và thậm chí sau đó, việc sử dụng chúng không rõ ràng.) –