sizeof操作符的結果型別爲
size_t(The sizeof keyword gives the amount of storage, in bytes,
associated with a variable or a type (including aggregate types). This
keyword returns a value of type size_t.)
(它在標頭檔案用typedfe定義爲unsigned int型別),計算的是分配空間的實際位元組數。
strlen結果型別也爲
size_t(size_t strlen( const char *string ))
但strlen是計算的空間中字元的個數(不包括‘\0’)。
另外,sizeof不能計算動態分配空間的大小如:
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
int main()
{
char str[20] = "hello world";
char *s = (char *)malloc(20);
strcpy(s, str);
printf("strlen(str)=%d\n",strlen(str));
printf("sizeof(str)=%d\n",sizeof(str));
printf("strlen(s)=%d\n",strlen(s));
printf("sizeof(s)=%d\n",sizeof(s));
free(s);
return 0;
}
結果爲:
最後的sizeof計算的是指針(sizeof(char *)) 的大小,爲4。
首先看幾個例子 :
第一個例子:
char* s = "0123456789";
sizeof(s); //結果 4 ===》s是指向字串常數的字元指針
sizeof(*s); //結果 1 ===》*s是第一個字元
strlen(s); //結果 10 ===》有10個字元,strlen是個函數內部實現是用一個回圈計算到\0爲止之前
strlen(*s); //結果 10 ===》錯誤
char s[] = "0123456789";
sizeof(s); //結果 11 ===》s是陣列,計算到\0位置,因此是10+1
strlen(s); //結果 10 ===》有10個字元,strlen是個函數內部實現是用一個回圈計算到\0爲止之前
sizeof(*s); //結果 1 ===》*s是第一個字元
char s[100] = "0123456789";
sizeof(s); //結果是100 ===》s表示在記憶體中的大小 100×1
strlen(s); //結果是10 ===》strlen是個函數內部實現是用一個回圈計算到\0爲止之前
int s[100] = "0123456789";
sizeof(s); //結果 400 ===》s表示再記憶體中的大小 100×4
strlen(s); //錯誤 ===》strlen的參數只能是char* 且必須是以‘\0‘結尾的
char q[]="abc";
char p[]="a\n";
sizeof(q),sizeof(p),strlen(q),strlen(p);\\結果是 4 3 3 2
char p[] = {'a','b','c','d','e','f','g','h'};
char q[] = {'a','b','c','d,'\0','e','f','g'};
sizeof(p); //結果是8 ===》p表示在記憶體中的大小 8×1
strlen(p); //爲一個隨機值,結果與編譯器有關,不同編譯器結果一般不同
sizeof(q); //結果是8 ===》p表示在記憶體中的大小 8×1
strlen(q); //結果爲4 ===》存在'\0',遇到'\0'計算停止。
第二個例子
struct Stu
{
int i;
int j;
char k;
};
Stu stu;
printf("%d\n",sizeof(Stu)); //結果 12 ===》記憶體補齊
printf("%d\n",sizeof(stu));; //結果 12 ===》記憶體補齊
這個例子是結構體的記憶體對齊所導致的,計算結構變數的大小就必須討論數據對齊問題。爲了CPU存取的速度最快(這同CPU取數操作有關,詳細的介紹可以參考一些計算機原理方面的書),C語言在處理數據時經常把結構變數中的成員的大小按照4或8的倍數計算,這就叫數據對齊(data alignment)。
這樣做可能會浪費一些記憶體,但理論上速度快了。當然這樣的設定會在讀寫一些別的應用程式生成的數據檔案或交換數據時帶來不便。