先介绍strlen():
strlen()是函数,要在运行时才能计算。参数必须是字符型指针(char*)。当数组名作为参数传入时,实际上数组就退化成指针了。它的功能是:返回字符串的长度。该字符串可能是自己定义的,也可能是内存中随机的,该函数实际完成的功能是从代表该字符串的第一个地址开始遍历,直到遇到结束符NULL。返回的长度大小不包括NULL。
sizeof() 是运算符,参数可以是数组(编译时分配的数组空间大小)、指针(存储该指针所用的空间大小)、类型(该类型所占的空间大小)、对象(对象的实际占用空间大小)、函数(函数的返回类型所占的空间大小,函数的返回类型不能是void)等。它的功能是获得保证能容纳实现所建立的最大对象的字节大小。
关于数组在使用时的要点:
1.数组名单独放在sizeof()内部时,数组表示整个数组。
2.&数组名,数组名表示整个数组。ex:&arr表示数组的地址。
字符数组:
int main()
{
char arr[] = { 'a', 'b', 'c', 'd', 'e', 'f' };
printf("%d\n", sizeof(arr)); //6 整个数组大小
printf("%d\n", sizeof(arr + 0)); //4 arr[0]地址大小
printf("%d\n", sizeof(*arr)); //1 arr[0]的大小
printf("%d\n", sizeof(arr[1])); //1 arr[1]的大小
printf("%d\n", sizeof(&arr)); //4 数组的地址(也是地址)
printf("%d\n", sizeof(&arr + 1)); //4 整个数组地址+1,跳出数组,依然是地址
printf("%d\n", sizeof(&arr[0] + 1)); //4 第一个元素地址+1,代表第二个元素地址
printf("%d\n", strlen(arr)); // 从a的地址开始,遇到\0结束,生成随机数
printf("%d\n", strlen(arr + 0)); // 同上
//printf("%d\n", strlen(*arr)); // strlen()参数必须是字符型指针
//printf("%d\n", strlen(arr[1])); // 同上
printf("%d\n", strlen(&arr)); // 警告!整个数组的地址,遇到\0结束,生成随机数
printf("%d\n", strlen(&arr + 1)); // 警告!数组的地址+1,跳出数组,依然是遇到\0结束,生成随机数
printf("%d\n", strlen(&arr[0] + 1)); // 第一个元素地址+1,第二个元素的地址,遇到\0结束,生成随机
return 0;
}
字符串:
char *p = "abcdef"; //字符串 需注意后面有 \0
printf("%d\n", sizeof(p)); //4 指针Pa的地址
printf("%d\n", sizeof(p + 1)); //4 a的地址+1,b的地址
printf("%d\n", sizeof(*p)); //1 对a地址的截引用,为char类型大小
printf("%d\n", sizeof(p[0])); //1 a,char类型
printf("%d\n", sizeof(&p)); //4 p字符串的头指针
printf("%d\n", sizeof(&p + 1)); //4 p的指针+1,跳出p,依然为指针
printf("%d\n", sizeof(&p[0] + 1)); //4 首元素地址+1,依然是指针
printf("%d\n", strlen(p)); //6 从a的地址,遇到\0结束,但不包括\0
printf("%d\n", strlen(p + 1)); //5 从b的地址开始,遇到\0结束
//printf("%d\n", strlen(*p)); // 必须为地址
//printf("%d\n", strlen(p[0])); // 同上
printf("%d\n", strlen(&p)); // p的地址,二级指针,有警告,级别不同,生成随机数
printf("%d\n", strlen(&p + 1)); // p的地址+1,跳出p,二级指针,有警告,级别不同,生成随机数
printf("%d\n", strlen(&p[0] + 1)); //5 b的地址,从b开始,遇\0结
整形数组:
int a[] = { 1, 2, 3, 4 };
printf("%d\n", sizeof(a)); //16 数组名单独放在sizeof中代表整个数组,求数组大小,以字节为单位
printf("%d\n", sizeof(a + 0)); //4 数组名不是单独放在sizeof中,代表数组第一个元素的地址
printf("%d\n", sizeof(*a)); //4 *为截引用符号,a代表首元素地址,对首元素地址截引用就是首元素,int类型
printf("%d\n", sizeof(a + 1)); //4 a不是单独在sizeof中,a代表首元素地址,a+1代表第二个为元素地址,指针类型
printf("%d\n", sizeof(a[1])); //4 代表第二个元素,是int类型
printf("%d\n", sizeof(&a)); //4 数组地址的地址
printf("%d\n", sizeof(&a + 1)); //4 数组地址+1,就跳出这个数组的地址,仍然为地址
printf("%d\n", sizeof(&a[0])); //4 对首元素取地址,等价于a
printf("%d\n", sizeof(&a[0] + 1)); //4 首元素地址+1,第二个元素的地址
二维数组:
int a[3][4] = { 0 };
printf("%d\n", sizeof(a)); //48 数组大小
printf("%d\n", sizeof(a[0][0])); //4
printf("%d\n", sizeof(a[0])); //16 把a[0]看成数组名,单独在sizeof中,代表整个数组a[0]
printf("%d\n", sizeof(a[0] + 1)); //4 a[0][1]地址
printf("%d\n", sizeof(a + 1)); //4 第二行地址a[1][]
printf("%d\n", sizeof(&a[0] + 1)); //4 对第一行元素取地址,+1后还是地址,等价于a+1
printf("%d\n", sizeof(*a)); //16 a代表第一行元素,*截引用,为第一行元素
printf("%d\n", sizeof(a[3])); //16 越界,但是编译不占内存,大小为16