對齊 (C11)
C 的其中一個低階功能是能夠指定記憶體中物件的精確對齊方式,以充分利用硬體架構。
當 CPU 將資料儲存在多個資料大小的位址時,CPU 會更有效率地讀取和寫入記憶體。 例如,如果 4 位元組整數儲存在 4 倍數的位址上,則會更有效率地存取 4 位元組整數。 當資料未對齊時,CPU 會執行更多位址計算工作來存取資料。
根據預設,編譯器會根據其大小來對齊資料: char
在 1 位元組界限、 short
2 位元組界限、 int
、 long
和 float
4 位元組界限上、 double
8 位元組界限等等。
此外,藉由將經常使用的資料與處理器的快取行大小對齊,您可以改善快取效能。 例如,假設您定義大小小於 32 個位元組的結構。 您可能想要使用 32 位元組對齊,以確保結構的所有實例有效率地快取。
通常,您不需要擔心對齊方式。 編譯器通常會根據目標處理器和資料大小,在自然界限上對齊資料。 資料會對齊 32 位處理器上最多 4 位元組的界限,以及 64 位處理器上的 8 位元組界限。 不過,在某些情況下,您可以為資料結構指定自訂對齊方式,以達到效能改善或省下記憶體。
使用 C11 關鍵字 _Alignof
取得類型或變數的慣用對齊方式,並 _Alignas
指定變數或使用者定義類型的自訂對齊方式。
在 中定義的便利宏 alignof
和 alignas
,分別對應至 _Alignof
和 _Alignas
。 <stdalign.h>
這些宏符合 C++ 中使用的關鍵字。 因此,如果您在兩種語言之間共用任何程式碼,使用宏而非 C 關鍵字可能會對程式碼可攜性有所説明。
alignas
和 _Alignas
(C11)
使用 alignas
或 _Alignas
指定變數或使用者定義類型的自訂對齊方式。 它們可以套用至結構、等位、列舉或變數。
alignas
語法
alignas(type)
alignas(constant-expression)
_Alignas(type)
_Alignas(constant-expression)
備註
_Alignas
無法在 typedef、bit-field、function、function 參數或以 register
規範宣告的物件中使用。
指定兩個乘冪的對齊方式,例如 1、2、4、8、16 等等。 請勿使用小於類型大小的值。
struct
和 union
型別的對齊方式等於任何成員的最大對齊方式。 填補位元組會新增在 內 struct
,以確保符合個別成員對齊需求。
例如,如果宣告中有數 alignas
個規範 (, struct
具有數個具有不同 alignas
規範的成員) ,則 的 struct
對齊方式至少會是最大規範的值。
alignas
範例
此範例會使用便利宏 alignof
,因為它可移植到 C++。 如果您使用 _Alignof
,則行為會相同。
// Compile with /std:c11
#include <stdio.h>
#include <stdalign.h>
typedef struct
{
int value; // aligns on a 4-byte boundary. There will be 28 bytes of padding between value and alignas
alignas(32) char alignedMemory[32]; // assuming a 32 byte friendly cache alignment
} cacheFriendly; // this struct will be 32-byte aligned because alignedMemory is 32-byte aligned and is the largest alignment specified in the struct
int main()
{
printf("sizeof(cacheFriendly): %d\n", sizeof(cacheFriendly)); // 4 bytes for int value + 32 bytes for alignedMemory[] + padding to ensure alignment
printf("alignof(cacheFriendly): %d\n", alignof(cacheFriendly)); // 32 because alignedMemory[] is aligned on a 32-byte boundary
/* output
sizeof(cacheFriendly): 64
alignof(cacheFriendly): 32
*/
}
alignof
和 _Alignof
(C11)
_Alignof
和其別名 alignof
會以指定類型的位元組傳回對齊方式。 它會傳回 類型的 size_t
值。
alignof
語法
alignof(type)
_Alignof(type)
alignof
範例
此範例會使用便利宏 alignof
,因為它可移植到 C++。 如果您使用 _Alignof
,則行為會相同。
// Compile with /std:c11
#include <stdalign.h>
#include <stdio.h>
int main()
{
size_t alignment = alignof(short);
printf("alignof(short) = %d\n", alignment); // 2
printf("alignof(int) = %d\n", alignof(int)); // 4
printf("alignof(long) = %d\n", alignof(long)); // 4
printf("alignof(float) = %d\n", alignof(float)); // 4
printf("alignof(double) = %d\n", alignof(double)); // 8
typedef struct
{
int a;
double b;
} test;
printf("alignof(test) = %d\n", alignof(test)); // 8 because that is the alignment of the largest element in the structure
/* output
alignof(short) = 2
alignof(int) = 4
alignof(long) = 4
alignof(float) = 4
alignof(double) = 8
alignof(test) = 8
*/
}
規格需求
使用 /std:c11
編譯。
Windows SDK 10.0.20348.0 (2104 版) 或更新版本。 請參閱 Windows SDK 以下載最新的 SDK。 如需安裝和使用 SDK 以進行 C11 和 C17 開發的指示,請參閱 在 Visual Studio 中安裝 C11 和 C17 支援。