起初它被错误地发现但是我喜欢C的这个特征非常有趣。这样一个简单的程序:
#include <stdio.h>
#include <string.h>
main()
{
int array[5];
array[0] = 1;
printf("%d",0[array]);
}
将在C中没有编译错误,并且它不是我期望的。并且它将在输出中打印1。我发现这很神奇,所以我只是想知道周围,发现这个代码在C中也可以正常工作,这将在输出中打印10:
#include <stdio.h>
#include <string.h>
main()
{
int array[5];
array[0] = 1;
array[1] = 10;
printf("%d",0[array+1]);
}
我想知道为什么这两个没有编译错误,而且我想知道第二个是如何工作的。此外,任何有趣的使用此功能将不胜感激。
答案 0 :(得分:3)
您观察到的行为符合标准:
6.5.2.1数组下标
后缀表达式后跟方括号[]中的表达式是下标 指定数组对象的元素。下标运算符[]的定义 是 E1 [E2] 与(*((E1)+(E2)))相同。
因此,在您的示例中,0[array]
变为(*(0 + array))
,0[array+1]
变为(*(0 + array + 1))
。然后可以将它们分别减少到*array
和*(array+1)
,两者都是有效的陈述。
答案 1 :(得分:1)
方括号数组语法是一种易于使用的处理内存指针的方法,可以顺序分配内存块。
你发现的是指针运算在C中的工作方式。每个变量都存储在内存中的特定地址,而数组只是内存中一行中的几个变量(就代码而言) )。因此,数组的名称是指向内存中第一项的指针,而索引是偏移量。编译器将这些加在一起以获得最终地址,因此列出它们的顺序并不重要。
在C中,以下代码行将输出相同的三次:
int values[] = {0, 1, 2};
printf( "%d %d %d", values[1], 1[values], *(values + 1) );
第三种是访问存储器地址的手动方式。我们从指向数组中第一个字节的指针开始,并为索引添加一个偏移量。