目录
代码1:
#include<stdio.h>
int main()
{
int a[] = { 1,2,3,4 };
printf("%d\n", sizeof(a));//16 a是数组名;计算的是整个数组大小;
printf("%d\n", sizeof(a + 0));//4 a+0是首元素地址;
printf("%d\n", sizeof(*a));//4 a是数组首元素地址,解引用后是首元素;
printf("%d\n", sizeof(a + 1));//4 a+1 是第二个元素的地址;
printf("%d\n", sizeof(a[1]));//4
printf("%d\n", sizeof(&a));//4 a是整个数组的地址,只要是地址,大小就是4或8;
printf("%d\n", sizeof(*&a));//16 解引用可以访问的大小,*这里访问的是数组:int [4];==sizeof(a)先取后解;
printf("%d\n", sizeof(&a + 1));//4
printf("%d\n", sizeof(&a[0]));//4
printf("%d\n", sizeof(&a[0] + 1));//4
return 0;
}
代码1分析:
sizeof(a)这里a代表整个数组,求的是整个数组的大小:16;sizeof(a+0),这里a代表首元素地址,求的是首元素地址的大小:4;sizeof(*a),这里a代表首元素地址,对它进行解引用,求的是首元素的大小:4;sizeof(a+1),这里a代表首元素地址,求的是第二个元素地址的大小:4;sizeof(a[1]),这里a[1]代表第二个元素,求的是第二个元素的大小:4;sizeof(&a),这里a代表整个数组,求的是整个数组地址的大小:4;sizeof(*&a),这里有两种理解:第一种取地址解引用相当于 a,sizeof(a)求的是整个数组的大小:16;第二种&a是整个数组的地址,*解引用访问的是整个数组的大小:16;sizeof(&a+1)这里a代表整个数组,求的是跨越一个数组后的地址大小:4;sizeof(&a[0])这里a代表整个数组,a[0]代表第一个元素,&a[0]代表第一个元素的地址,求的是第一个元素地址的大小:4;sizeof(&a[0])这里&a[0]代表数组第一个元素的地址,+1代表第二个元素的地址,求的是第二个元素地址的大小:4;
运行结果:
代码2:
#include<stdio.h>
#include<string.h>
int main()//要分的清arr是整个数组还是指针,arr只有在sizeof 和 & 后面才是整个数组;
{
char arr[] = { 'a','b','c','d','e','f' };
printf("%d\n", sizeof(arr));//sizeof (arr)这时arr是整个数组,6 arr的类型 arr [6]
printf("%d\n", sizeof(arr + 0));//;//第一个元素的地址 4 类型 char*
printf("%d\n", sizeof(*arr));//对arr解引用,这是arr是第一个元素的地址 1 类型char
printf("%d\n", sizeof(arr[1]));// 第二个元素的大小 1 类型 char
printf("%d\n", sizeof(&arr));//整个数组的地址 4 类型char*[6]
printf("%d\n", sizeof(&arr + 1));//数组最后一个元素的后一个元素的地址 4 类型char*[6]
printf("%d\n", sizeof(&arr[0] + 1));//第二个元素地址 4 类型char*
return 0;//注意: sizeof里面的内容不会计算,只关注类型;
}
代码2分析:
sizeof(arr),这里arr代表整个数组,求的是整个数组的大小,结果为6;sizeof(arr),这里arr代表整个数组,求的是整个数组的大小,结果为6;sizeof(arr+0),这里arr代表数组第一个元素的地址,求的是第一个元素地址的大小,结果为4;sizeof(*arr),这里arr代表首个元素的地址,对其解引用求的是数组第一个元素的大小,结果为1;sizeof(arr[1]),这里arr代表整个数组,arr[1]是数组低二个元素,求的是整个数组第二个元素的大小,结果为1;sizeof(&arr),这里arr代表整个数组,求的是整个数组的地址,结果为4;sizeof(&arr+1),这里arr代表整个数组,求的是跨越整个数组的地址的大小,结果为4;sizeof(&arr[0]+1),这里arr代表整个数组,arr[0]是第一个元素,求的是数组第二个元素地址的大小,结果为4;
运行结果:
代码3:
#include<stdio.h>
#include<string.h>
int main()//要分的清arr是整个数组还是指针,arr只有在sizeof 和 & 后面才是整个数组;
{
char arr[] = { 'a','b','c','d','e','f' };//strlen 统计的是字符串中在\0之前的元素个数,如果没有\0就会一直找;
// strlen 需要的是一个地址;从提供地址往后访问;
printf("%d\n", strlen(arr));//随机 arr是表示首元素地址;
printf("%d\n", strlen(arr + 0));//随机 arr表示首元素地址;
//printf("%d\n", strlen(*arr));//随机 *arr表示第一个元素;ascii是97;当从97开始访问时,非法访问; error
//printf("%d\n", strlen(arr[1]));// 随机 表示第二个元素; error
printf("%d\n", strlen(&arr));// 随机//首元素的地址;类型char(*)[6],传过去就被强制转换成所需类型了;
//数组地址和数组首元素地址值一样,但类型不一样;
printf("%d\n", strlen(&arr + 1));//随机//第二个数组的首元素地址;
printf("%d\n", strlen(&arr[0] + 1));//随机 //第二个元素的地址;
return 0;//注意: sizeof里面的内容不会计算,只关注类型;
}
代码3分析:
strlen函数里面输入一个地址,从这个地址往后,一直到 \0 ,结果是 \0 之前的元素个数;strlen(arr)这里arr是首元素地址,但不知道\0的位置,所以结果是随机值;strlen(arr+0)这里arr是首元素地址,arr+0还是首元素地址,但不知道\0的位置,所以结果是随机值;strlen(*arr)这里arr是首元素地址,*arr是首元素,strlen要求输入地址,所以是error;strlen(arr[1])这里arr[1]是第二个元素,strlen要求输入地址,所以是error;strlen(&arr)这里arr是整个数组,&arr是整个数组的地址,类型是char(*)[],进入以后,地址类型就被转换成所需要的地址类型,但不知道\0的位置,所以结果是随机值;strlen(&arr+1)这里arr是整个数组,&arr+1是跨越整个数组的地址,但不知道\0的位置,所以结果是随机值;strlen(&arr[0]+1)这里arr是整个数组,&arr[0]+1是数组第二个元素的地址,但不知道\0的位置,所以结果是随机值,不过这个值应与strlen(&arr)差1;
运行结果:
代码4:
#include<stdio.h>
#include<string.h>
int main()//要分的清arr是整个数组还是指针,arr只有在sizeof 和 & 后面才是整个数组;
{
char arr[] = "abcdef";//元素包括\0 {a,b,c,d,e,f,\0}
printf("%d\n", sizeof(arr));//7 sizeof判断出后面的类型就行;
printf("%d\n", sizeof(arr + 0));//4
printf("%d\n", sizeof(*arr));//1 *arr=arr[0]
printf("%d\n", sizeof(arr[1]));//1
printf("%d\n", sizeof(&arr));//4
printf("%d\n", sizeof(&arr + 1));//4
printf("%d\n", sizeof(&arr[0] + 1));//4
printf("%d\n", strlen(arr));//6 strlen后面要加一个地址;
printf("%d\n", strlen(arr + 0));//6
printf("%d\n", strlen(*arr));//err
printf("%d\n", strlen(arr[1]));//err
printf("%d\n", strlen(&arr));//6
printf("%d\n", strlen(&arr + 1));//随机值;
printf("%d\n", strlen(&arr[0] + 1));//5
return 0;//注意: sizeof里面的内容不会计算,只关注类型;
}
代码4分析:
arr数组的元素包括:a,b,c,d,e,f,\0;sizeof(arr),这里arr代表整个数组,求的是整个数组的大小,结果是:7;sizeof(arr+0),这里arr代表首元素地址,求的是首元素地址的大小,结果是:4;sizeof(*arr),这里arr代表首元素地址,解引用求的是首元素的大小,结果是:1;sizeof(arr[1]),这里arr[1]代表首元素,求的是首元素的大小,结果是:1;sizeof(&arr),这里arr代表整个数组,求的是整个数组地址的大小,结果是:4;sizeof(&arr+1),这里arr代表整个数组,求的是跨越整个数组的地址的大小,结果是:4;sizeof(&arr[0]+1),这里&arr[0]+1代表第二个数组元素地址,求的是数组第二个元素的地址的大小,结果是:4;
strlen(arr),这里arr代表数组首元素地址,与\0之间的元素个数是6;strlen(arr+0),这里arr+0代表数组首元素地址,与\0之间的元素个数是6;strlen(*arr),这里arr代表数组首元素地址,*arr代表首元素,不是地址,所以是error;strlen(arr[1]),这里arr[1]代表数组第二个元素,不是地址,所以是error;strlen(&arr),这里arr整个数组,&arr代表整个数组地址,也是数组首元素地址,与\0之间的元素个数是6;strlen(&arr+1),这里arr是整个数组,&arr+1代表跨越数组的地址,从这个地址往后找\0,不知道\0的位置,与\0之间的元素个数随机值;strlen(&arr[0]+1),这里&arr[0]+1是数组第二个元素地址,从这个地址往后找\0,与\0之间的元素个数为5;
运行结果:
代码5:
#include<stdio.h>
#include<string.h>
int main()//要分的清arr是整个数组还是指针,arr只有在sizeof 和 & 后面才是整个数组;
{
char* p = "abcdef";//是把首字符 a 的地址放到 p里面了
printf("%d\n", sizeof(p));// 4 p是a的地址,p是char* 指针类型;
printf("%d\n", sizeof(p + 1));// 4 b的地址 char*指针类型;
printf("%d\n", sizeof(*p));// 1 解引用 指向的是 字符a
printf("%d\n", sizeof(p[0]));// 1 a==*(p+0)==*p //指针[i]==*(指针+i)
//char** p =&p;
printf("%d\n", sizeof(&p));//4 p是char**型 &p指向p变量所存储的第一个字节;
printf("%d\n", sizeof(&p + 1));//4 &p+1指向p变量后面的变量所存储的第一个字节,&p+1相当于跳过一个char*的对象;
printf("%d\n", sizeof(&p[0] + 1));// 4 //p[0]==*(p+0)==*p==a,&p[0] + 1相当于跳过一个p[0]的元素;指向b;
printf("%d\n", strlen(p));// 6
printf("%d\n", strlen(p + 1));//5 p+1跳过一个char类型的数据;
//printf("%d\n", strlen(*p));//err
//printf("%d\n", strlen(p[0]));//err
printf("%d\n", strlen(&p));//随机 char** x==&p &p实在p里面找\0
printf("%d\n", strlen(&p + 1));//随机 &p+1实在p里面找\0,p里面后面前面的元素都不知道;&p+1后面的元素也不知道;
printf("%d\n", strlen(&p[0] + 1));// &p[0] + 1 p[0]==*p==a,&a+1=&b 5
return 0;//注意: sizeof里面的内容不会计算,只关注类型;
}
代码5分析:
字符串的返回值是首元素地址;sizeof(p)这里p是首元素a的地址,结果:4;sizeof(p+1)这里p是首元素a的地址,p+1是第二个元素b的地址,结果:4;sizeof(*p)这里p是首元素a的地址,*p是第二个元素b,结果:1;sizeof(p[0])这里p是首元素a的地址,p[0]==*(p+0)==*p,是第一个元素,结果:1;sizeof(&p)这里p是首元素a的地址,&p是a元素地址的地址,指向p变量所存储的第一个字节,结果:4;sizeof(&p+1)这里p是首元素a的地址,&p是a元素地址的地址,&p+1指向p变量后面的第一个变量所存储的第一个字节,结果:4;sizeof(&p[0]+1),p[0]==*(p+0)==*p==a,&a是a的地址,&a+1是b的地址,结果:4;
strlen(p),p是a的地址,与\0之间的元素个数是6;strlen(p+1),p+1是b的地址,与\0之间的元素个数是5;strlen(*p),p是a的地址,*p是第一个元素a,不是地址,结果是:error;strlen(p[0]),p[0]==*(p+0)==a,不是地址,结果是:error;strlen(&p),&p指向的是p地址的第一个字节,\0的位置不知道,是随机值;strlen(&p+1),&p+1指向的是p地址往后4个字节后的第一个字节,\0的位置不知道,是随机值;strlen(&p[0]+1),p[0]==*(p+0)==*p==a,&p[0]+1指向的是b,与\0之间的元素个数:5;
运行结果:
代码6:
#include<stdio.h>
#include<string.h>
int main()//要分的清arr是整个数组还是指针,arr只有在sizeof 和 & 后面才是整个数组;
{
int a[3][4] = { 0 };//二维数组可以把一行看作一个元素;一维数组的数组;访问的时间必须加j;
//a要么是整个数组,要么是第一行的地址;
printf("%d\n", sizeof(a));//48 a是整个数组;
printf("%d\n", sizeof(a[0][0]));//4 0行0列 一个元素;
printf("%d\n", sizeof(a[0]));// 16 第一行数组的数组名,计算的整个数组的大小;
printf("%d\n", sizeof(a[0] + 1));//4 第一行第二个元素的地址;
printf("%d\n", sizeof(*(a[0] + 1)));//4 第二行数组的第一个元素的内容;
printf("%d\n", sizeof(a + 1));//4 a+1 首元素地址,第二行地址;int(*)[4]
printf("%d\n", sizeof(*(a + 1)));//16 *(a+1)==a[1],(a+1)是数组指针,解引用访问是数组; 是第二行的地址;
printf("%d\n", sizeof(&a[0] + 1));//4 a[0]==*(a+0) &a[0]==a 是第一行数组的数组名,取地址是整个数组的地址,+1是第二行数组的地址,即a[2]
printf("%d\n", sizeof(*(&a[0] + 1)));//16 第二行地址解引用访问的是第二行数组;
printf("%d\n", sizeof(*a));//16 a是数组首元素的地址,即第一行的地址,解引用访问数组 *a==a[0]
printf("%d\n", sizeof(a[3]));//a[3]=*(a+3) 类型是int(*)[4] 不会真正访问,只会判断类型;
return 0;//注意: sizeof里面的内容不会计算,只关注类型;
}
代码6分析:
sizeof(a),这里a是整个数组,求的是整个数组的大小,结果是:48;sizeof(a[0][0]),这里a[0][0]是数组第一个元素,求的是数组的第一个元素的大小,结果是:4;sizeof(a[0]),a[0]==*(a+0)==*(a),这里a是数组第一个元素地址,但这里二维数组的第一个元素是第一行数组,a[0]也可以当作第一行数组的数组名,放在sizeof后面代表整个数组,求的是第一行数组的大小,结果是:16;sizeof(a[0]+1),a[0]==*(a+0)==*(a),这里a是数组第一个元素,但这里二维数组的第一个元素是第一行数组,a+1,是第二行数组的首元素地址,结果是:4;sizeof(*(a[0]+1)),a[0]==*(a+0)==*(a),这里a是数组第一个元素地址,但这里二维数组的第一个元素是第一行数组,a[0]+1,是第二行数组的首元素地址,解引用,是第二行数组的首元素,结果是:4;sizeof(a+1),这里a是第一行数组的地址,a+1是第二行数组的地址,结果是:4;sizeof(*(a+1)),a+1是第二行数组的地址,对其解引用得到的是第二行数组,结果是:16;sizeof(&a[0]+1)),a[0]==*(a+0)==*a,得到的是第一行数组,&a[0]得到第一行数组地址,+1得到第二行数组地址结果是:4;sizeof(*(&a[0]+1)+1),对第二行进行访问,结果是:16;sizeof(*a),*a==a[0],求的是第一行数组的大小,结果是:16;sizeof(a[3]),a[3]==*(a+3),a+3的类型是int(*)[4],解引用后的类型是int[4],结果是:16,sizeof不会真的访问,只是计算类型的大小;
运行结果:
标签:arr,判别,元素,地址,数组,printf,大小,sizeof,指针 From: https://blog.csdn.net/qq_54029068/article/details/136990410