c – 为什么“*(&arr 4)”与“&arr [4]”不同?

int arr[] = { 0,1,2,3,4,5 };

我正在执行地址操作测试,以增加我对ref和deref的理解.
这里有很多困惑.

我发现& *(arr 4)使用与& arr [4]相同的地址,但我从未遇到过& *这样的分配

另外我认为*(& arr 4)使用与& arr 4相同的地址,但它对我没有任何意义.

我找不到相关信息,所以我在这里问一下,为什么*(& arr 4)使用与& arr 4相同的地址,为什么*(& arr 4)与& arr [4]不同]?

解决方法

arr是一个数组:

arr: int[6]
[0|1|2|3|4|5]

当在sizeof arr或& arr之外的表达式中使用时,数组会衰减到指向数组的第一个元素的指针:

(arr+0): int *
[*]
 |
 v
[0|1|2|3|4|5]

一个整数值被添加一个指针时,你得到一个指向地址的指针(sizeof(T))* n个字节后面的内存(其中T是指针指向的类型,n是添加的整数值)到指针):

(arr+4): int *
        [*]
         |
         v
[0|1|2|3|4|5]

取消引用指针后,您将获得指向的值:

*(arr+4): int
          4 /* specifically,the 4 in the fifth position in `arr` */
[0|1|2|3|[4]|5]

获取int的地址时,您会得到一个指向该int的指针:

&*(arr+4): int *
        [*] /* notice,this is the same as (arr+4) */
         |
         v
[0|1|2|3|4|5]

数组索引等效于指针添加,然后是解除引用:

arr[4] == *(arr+4) /* see above for deFinition of *(arr+4) */

所以是的……& *(arr 4)和& arr [4]是等价的.

获取数组的地址时,您将获得指向数组的指针:

&arr: int (*)[6]
[*] /* points to the array as a whole,not the first element of the array */
 |
 v
 [0|1|2|3|4|5]

当您递增该指针时,相同的规则适用于上述:

&arr + 4: int(*)[6]
               /*points into some memory that*/    [*]
               /* isn't part of the array... */     |
               /*  undefined behavIoUr       */     v
[0|1|2|3|4|5][x|x|x|x|x|x][x|x|x|x|x|x][x|x|x|x|x|x][x|x|x|x|x|x]

由于这具有未定义的行为,因此您无法在不参考底层机器体系结构和编译器实现的情况下对其进行推理.

如果我们想象它已被很好地定义(如果arr是更大阵列的一部分那样的情况)……我们可以继续.取消引用指向数组的指针会再次给出数组:

/*the 5th array in this array of arrays*/ *(&arr+4): int[6]
   [0|1|2|3|4|5][x|x|x|x|x|x][x|x|x|x|x|x][x|x|x|x|x|x][[x|x|x|x|x|x]]

您会发现*(& arr 4)和(& arr 4)具有相同的地址,因为*(& arr 4)衰减为指向*(& arr 4)的第一个元素的指针,并且数组从它的第一个元素开始,因此指向数组开头的指针和指向数组第一个元素的指针是相同的.

*(& arr 4)与& arr [4]不同,因为它指的是完全不同的东西(见上文).

相关文章

本程序的编译和运行环境如下(如果有运行方面的问题欢迎在评...
水了一学期的院选修,万万没想到期末考试还有比较硬核的编程...
补充一下,先前文章末尾给出的下载链接的完整代码含有部分C&...
思路如标题所说采用模N取余法,难点是这个除法过程如何实现。...
本篇博客有更新!!!更新后效果图如下: 文章末尾的完整代码...
刚开始学习模块化程序设计时,估计大家都被形参和实参搞迷糊...