从int*转换后,我的char指针指向无效值

May*_*ari 51 c arrays pointers

我正在学习C编程语言,我刚开始用指针学习数组.我在这个问题上有问题,我希望输出必须是5但是2,有人可以解释原因吗?

int main(){
   int arr[] = {1, 2, 3, 4, 5};
   char *ptr = (char *) arr;
   printf("%d", *(ptr+4));
   return 0;
}
Run Code Online (Sandbox Code Playgroud)

And*_*ter 80

假设一个小的endian架构,其中int是32位(4字节),单个字节int arr[]看起来像这样(较低地址的最低有效字节.所有十六进制值):

|01 00 00 00|02 00 00 00|03 00 00 00|04 00 00 00|05 00 00 00
Run Code Online (Sandbox Code Playgroud)
char *ptr = (char *) arr;
Run Code Online (Sandbox Code Playgroud)

现在,ptr指向第一个字节 - 因为你已经转换为char*,它被视为char数组向前:

|1|0|0|0|2|0|0|0|3|0|0|0|4|0|0|0|5|0|0|0
 ^
 +-- ptr
Run Code Online (Sandbox Code Playgroud)

然后,*(ptr+4)访问char数组的第五个元素并返回相应的char值:

|1|0|0|0|2|0|0|0|3|0|0|0|4|0|0|0|5|0|0|0
         ^
         +-- *(ptr + 4) = 2
Run Code Online (Sandbox Code Playgroud)

因此,printf()打印2.

Big Endian系统中,每个字节中的字节顺序int相反,从而产生

|0|0|0|1|0|0|0|2|0|0|0|3|0|0|0|4|0|0|0|5
         ^
         +-- *(ptr + 4) = 0
Run Code Online (Sandbox Code Playgroud)

  • 谢谢先生,你的答案给了我最好的视觉表现,.... :) (4认同)
  • 你混合你的endianess,little endian具有最低的内存位置. (3认同)
  • 你对`printf()`如何处理这种情况的描述是不正确的.它将第5个字符的值作为整数,而不是指向它的指针.此外,正如约阿希姆所说,你的字节顺序被翻转了. (3认同)

Som*_*ude 13

这是因为大小char是1,大小int是4.这意味着添加4ptr使结果指向int数组中的第二个条目.

如果你在一个大端系统上编译它,你会打印33554432.

  • @Bathsheba Endianess绝对是一个整数问题. (9认同)
  • 只要存在使用超过1个字节的类型,就会出现存储字节的顺序的问题. (5认同)
  • ...而且,我认为你是对的:在big endian上,结果应该为零,因为你正在访问第五个字节为`char`而且这个字节为零......对不起...... . (3认同)
  • @JoachimPileborg +1 - 我记得我总是把它搞乱:D (2认同)