关于数组的sizeof 和 strlen 问题

首先:

     要明白    sizeof( )  是个运算符,用来计算 计算一个类型或变量所占空间的大小 单位是:字节

strlen( )是个函数,用来计算字符串的长度  参数是一个指针(地址)

     所以只需知道    sizeof( )注重  类型            strlen( )注重   地址

int a[] = {1,2,3,4};
printf("%d\n",sizeof(a));      //a是在sizeof 内部,所以计算的是整个数组的大小,4*4=16
printf("%d\n",sizeof(a+0));  //a+0虽然和a的意义一样但它不是单独在sizeof内部,所以这里的a+0是首元素的地址,而地址的大小是  4/8
printf("%d\n",sizeof(*a));  //a是首元素地址,*a就是首元素 1   它的大小是 4
printf("%d\n",sizeof(a+1));  //a+1是第二个元素的地址,地址的大小是 4/8
printf("%d\n",sizeof(a[1]));  //a[1]是第二个元素 2  它的大小是 4
printf("%d\n",sizeof(&a));  //&a是整个数组的地址,地址的大小是 4/8
printf("%d\n",sizeof(*&a));  //*直接和&抵消 sizeof(a)里就只剩个a,那不就和第一个一样了  16
printf("%d\n",sizeof(&a+1));  //&a+1还是地址   4/8
printf("%d\n",sizeof(&a[0]));  //&a[0]是第一个元素的地址  4/8
printf("%d\n",sizeof(&a[0]+1));  //&a[0]+1是第二个元素的地址  4/8

char arr[] = {'a','b','c','d','e','f'};
printf("%d\n", sizeof(arr));  //sizeof里直接是数组名,就直接算整个数组的大小  1*6=6
printf("%d\n", sizeof(arr+0));  //a+0虽然和a的意义一样但它不是单独在sizeof内部,所以这里的a+0是首元素的地址,而地址的大小是  4/8
printf("%d\n", sizeof(*arr));  //*arr是第一个字符 a   根据它是char 类型 它的大小是 1
printf("%d\n", sizeof(arr[1]));  //arr[1]是第二个字符,它的大小是 1
printf("%d\n", sizeof(&arr));  //&arr是整个数组的地址,它还是地址啊   4/8
printf("%d\n", sizeof(&arr+1));  //&arr+1是跳过整个数组的地址   4/8
printf("%d\n", sizeof(&arr[0]+1));  //&a[0]+1是第二个元素的地址  4/8

char arr[] = {'a','b','c','d','e','f'};

printf("%d\n", strlen(arr));  //arr是首元素地址,所以从第一个元素访问,到 /0 停止,但此时可以看到,这种初始化方式你并不知道 /0 在哪,所以可能在后面的某处,因此它的值为随机值
printf("%d\n", strlen(arr+0));  //arr+0还是首元素地址,往后找 /0 ,值是随机值
printf("%d\n", strlen(*arr));  //*arr是首元素'a',它的ASCII码值为97,此时就是那97作为初始地址向后访问 /0 ,此时属于非法访问了,所以程序错误
printf("%d\n", strlen(arr[1]));  //arr[1]是第二个元素'b',和上条性质一样,程序错误
printf("%d\n", strlen(&arr));  //&arr是整个数组的地址,向后找/0 是 随机值
printf("%d\n", strlen(&arr+1));  //&arr+1是跳过整个数组的地址,向后找/0  随机值
printf("%d\n", strlen(&arr[0]+1));  //&arr[0]+1是第二个元素的地址,向后找/0  随机值

char arr[] = "abcdef";  a b c d e f /0
printf("%d\n", sizeof(arr));  //arr是在sizeof 内部,所以计算的是整个数组的大小,而'/0'也是个字符,所以它的大小为  1*7=7
printf("%d\n", sizeof(arr+0));  //arr+0是第一个元素的地址,是地址  4/8
printf("%d\n", sizeof(*arr));  //*arr是第一个元素, char类型  1
printf("%d\n", sizeof(arr[1])); //arr[1]是第二个元素,1
printf("%d\n", sizeof(&arr));  //&arr是整个元素的地址,它还是地址啊   4/8
printf("%d\n", sizeof(&arr+1));  //&arr+1是跳过整个数组的地址   4/8
printf("%d\n", sizeof(&arr[0]+1));  //&a[0]+1是第二个元素的地址  4/8

char arr[] = "abcdef";  a b c d e f /0

printf("%d\n", strlen(arr));  //arr是首元素地址,从此处向后找 /0   长度为6
printf("%d\n", strlen(arr+0));  //arr+0还是首元素地址,和上面一样      6
printf("%d\n", strlen(*arr));  //*arr是第一个元素 'a',它的ASCII码值为97,此时就是那97作为初始地址向后访问 /0 ,此时属于非法访问了,所以程序错误
printf("%d\n", strlen(arr[1]));  //arr[1]是第二个元素'b',和上条性质一样,程序错误
printf("%d\n", strlen(&arr));  //&arr是整个数组的地址,从此处找 /0     6
printf("%d\n", strlen(&arr+1));//&arr+1是跳过整个数组的地址,从此处找 /0 只可能开后面哪个位置了    随机值


printf("%d\n", strlen(&arr[0]+1));  //&arr[0]+1是第二个元素的地址,从此处向后找 /0  5

char *p = "abcdef";
printf("%d\n", sizeof(p));  //右边其实是常量字符串,p里存的是它的首元素a的地址,它是地址  4/8
printf("%d\n", sizeof(p+1));  //p+1是第二个元素的地址  4/8
printf("%d\n", sizeof(*p));  //*p是第一个元素 a  它的大小是   1
printf("%d\n", sizeof(p[0]));  //p[0]是相当于*(p+0)  就是第一个元素  a    1
printf("%d\n", sizeof(&p));  //&p 是这个变量p的地址 是地址  4/8
printf("%d\n", sizeof(&p+1));  //&p+1 是p的地址向后走一个字节的地址    4/8
printf("%d\n", sizeof(&p[0]+1));p[0]是相当于*(p+0) ,  加个&  与*  抵消  所以最后剩个p+1 和第二个一样  4/8

char *p = "abcdef";  a b c d e f /0

printf("%d\n", strlen(p));  //p里存的是a的地址,从此处向后找 /0,长度为6
printf("%d\n", strlen(p+1));  //p+1是第二个元素b的地址,从此处向后找 /0,长度为5
printf("%d\n", strlen(*p));  //*p是第一个元素 a,它的ASCII码值为97,此时就是那97作为初始地址向后访问 /0 ,此时属于非法访问了,所以程序错误
printf("%d\n", strlen(p[0]));   //p[0]相当于 *(p+0) 就是*p,和上一个一样,程序错误
printf("%d\n", strlen(&p));  //相当于从p的地址处,向后找 /0        随机值


printf("%d\n", strlen(&p+1));//&p+1 是p的地址向后走一个字节的地址  随机值
printf("%d\n", strlen(&p[0]+1));//;p[0]是相当于*(p+0) ,  加个&  与*  抵消  所以最后剩个p+1 和第二个一样  5

int a[3][4] = {0};       二维数组可以看作是一维数组的数组
printf("%d\n",sizeof(a));  //a是在sizeof 内部,所以计算的是整个数组的大小,  3*4*4=48
printf("%d\n",sizeof(a[0][0]));  //a[0][0]是第一行第一个元素,  4
printf("%d\n",sizeof(a[0]));  //a[0]是第一行的数组名,数组名放sizeof内部就是计算整个第一行这个一维数组的大小  4*4=16
printf("%d\n",sizeof(a[0]+1));  //a[0]+1  a[0]是第一行数组名,它此时是第一行首元素的地址,它+1就是第一行第二个元素的地址,是地址,   4/8
printf("%d\n",sizeof(*(a[0]+1)));  //a[0]+1是一行第二个元素的地址,解引用后就是第二个元素    4

printf("%d\n",sizeof(a+1));  //a是二维数组数组名,也就是首元素的地址,而把二维数组看作一维数组时,它的首元素地址就是第一行的地址,是地址   4/8
printf("%d\n",sizeof(*(a+1)));  //a+1是第一行的地址,解引用后就是第一行(一维数组)的元素 16
printf("%d\n",sizeof(&a[0]+1));  //a[0]是第一行这个一维数组的数组名,就是第一行首元素的地址,&a[0]相当于取整个一维数组的地址,+1跳过第一行这个一维数组的地址,也就是第二行的地址,是地址   4/8
printf("%d\n",sizeof(*(&a[0]+1)));  //解引用第二行的地址,就是第二行这个一维数组的全部元素  16
printf("%d\n",sizeof(*a));  //a是二维数组的首元素地址,相当于第一行的地址,   16
printf("%d\n",sizeof(a[3]));  //a[3]看起来是数组越界了,但无关紧要,我sizeof()只看是啥类型啊,a[3]   ->  int  [4]  这个数组类型的,所以就是  4*4=16

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值