我的程序的输出令人困惑。
问题出现的原因是对指针算术的错误理解。变量x
的类型是unsigned int[4][3]
,一个长度为4的数组,每个成员本身又是一个长度为3的数组。当我们计算x+3
时,实际上是在计算x
中最后一个成员的地址(记住x
的成员是数组)。因此,*(x+3)
本身就是一个数组。但是,当我们将数组作为函数参数传递时会发生什么呢?它们会被转换为指针。因此,你看到的是printf
中错误类型说明符导致的第一个元素地址的混乱。
好的,让我们来看看例如元素x[2][3]
。它将是一个这样的表达式:*(*(x+2)+3)
,它完全等价于*(&x[0][0] + 2*3 + 3)
。
为了解决这个问题,我们需要正确理解指针算术并使用正确的类型说明符。对于x[2][3]
这个例子,我们可以使用以下代码来打印正确的值:
printf("%d", x[2][3]);
问题的原因是在程序中使用了错误的格式说明符,并且需要将这些值强制转换为指针。出现这个问题的原因是,变量x是一个数组,并且其元素的类型是unsigned int[3],也就是x是一个unsigned int[3]数组的数组。首先,x + 3给出了数组中第四个元素的地址,也就是{10, 11, 12}的地址。这个数组在内存中的地址将是它的第一个元素10在内存中的地址。注意,这个值是int (*) [3]类型,即unsigned int[3]数组的地址。其次,* (x + 3)等价于x[3],也就是第四个元素,即unsigned int[3]类型的数组{10, 11, 12}。这个值指向数组{10, 11, 12}的第一个元素,也就是指向10。注意,这个值是unsigned int[3]类型。第三个表达式*(x+2) + 3中,*(x + 2)等价于x[2],它是一个unsigned int[3]类型的数组,即{7, 8, 9}数组,当你进行+3操作时,你再次得到的是10的地址。注意,这个值是unsigned int[3]类型。所以,可以看到,在这三种情况下,你的结果都是内存中存储10的地址,即使你在不同的时间表示了不同的东西;一开始是unsigned int (*)[3],然后是unsigned int[3]。