- 定義:sizeof 是一個操作符(operator),其作用是返回一個對象或類型所占的內存字節數。
其返回值類型為size_t。(size_t在頭文件stddef.h中定義,它依賴于編譯系統的值,一般定義為 typedef unsigned int size_t;) - 語法:sizeof有三種語法形式:
1) sizeof (object); //sizeof (對象)
2) sizeof object; //sizeof 對象
3) sizeof (type_name); //sizeof (類型)
對象可以是各種類型的變量,以及表達式(一般sizeof不會對表達式進行計算)。
sizeof對對象求內存大小,最終都是轉換為對對象的數據類型進行求值。
sizeof (表達式); //值為表達式的最終結果的數據類型的大小
int i;
sizeof(int); //值為4
sizeof(i); //值為4,等價于sizeof(int)
sizeof i; //值為4
sizeof(2); //值為4,等價于sizeof(int),因為2的類型為int
sizeof(2 + 3.14); //值為8,等價于sizeof(double),因為此表達式的結果的類型為double
- 基本數據類型的sizeof
這里的基本數據類型是指short、int、long、float、double這樣的簡單內置數據類型。
由于它們的內存大小是和系統相關的,所以在不同的系統下取值可能不同。
(32位系統下)Size of char : 1;Size of int : 4;Size of short int : 2;Size of long int : 4;Size of float : 4;Size of double : 8; Size of *p : 4(指針); - 結構體的sizeof
為什么需要字節對齊?計算機組成原理教導我們這樣有助于加快計算機的取數速度,否則就得多花指令周期了。為此,編譯器默認會對結構體進行處理(實際上其它地方的數據變量也是如此),讓寬度為2的基本數據類型(short等)都位于能被2整除的地址上,讓寬度為4的基本數據類型(int等)都位于能被4整除的地址上,依次類推。這樣,兩個數中間就可能需要加入填充字節,所以整個結構體的sizeof值就增長了。
字節對齊的細節和編譯器的實現相關,但一般而言,滿足三個準則:
1) 結構體變量的首地址能夠被其最寬基本類型成員的大小所整除。
2) 結構體的每個成員相對于結構體首地址的偏移量(offset)都是成員大小的整數倍,如有需要,編譯器會在成員之間加上填充字節(internal adding)。
3) 結構體的總大小為結構體最寬基本類型成員大小的整數倍,如有需要,編譯器會在最末一個成員后加上填充字節(trailing padding)。
注意:空結構體(不含數據成員)的sizeof值為1。試想一個“不占空間“的變量如何被取地址、兩個不同的“空結構體”變量又如何得以區分呢,于是,“空結構體”變量也得被存儲,這樣編譯器也就只能為其分配一個字節的空間用于占位了。