如何在C编译器内部处理数组和指针类型?(int*a;与int a [];)

Rob*_*nes 2 c arrays pointers language-lawyer

我需要一位有权威资源的语言律师.

看看下面的测试程序,它在gcc下干净地编译:

#include <stdio.h>


void foo(int *a) {
    a[98] = 0xFEADFACE;
}

void bar(int b[]) {
    *(b+498) = 0xFEADFACE;
}

int main(int argc, char **argv) {

int a[100], b[500], *a_p;

*(a+99) = 0xDEADBEEF;
*(b+499) = *(a+99);

foo(a);
bar(b);

printf("a[98] == %X\na[99] == %X\n", a[98], a[99]);
printf("b[498] == %X\nb[499] == %X\n", b[498], b[499]);

a_p = a+98;
*a_p = 0xDEADFACE;

printf("a[98] == %X\na[99] == %X\n", a[98], a[99]);

}
Run Code Online (Sandbox Code Playgroud)

它产生我期望的输出:

anon@anon:~/study/test_code$ gcc arrayType.c -o arrayType
anon@anon:~/study/test_code$ ./arrayType 
a[98] == FEADFACE
a[99] == DEADBEEF
b[498] == FEADFACE
b[499] == DEADBEEF
a[98] == DEADFACE
a[99] == DEADBEEF
Run Code Online (Sandbox Code Playgroud)

a和b是同一类型吗?被int *a视为同一类型的处理int a[]在编译器在内部?

从实际的角度来看,int a[100], b[500], *a_p, b_a[];所有类似的都是同一类型.在上面的例子中,我很难相信编译器会在各种情况下不断调整这些类型.我很高兴被证明是错的.

有人能否明确地详细解决这个问题?

Mar*_*off 9

a和b是同一类型吗?int*是否在编译器内部处理与int a []相同的类型?

comp.lang.C常见问题:

...只要数组出现在表达式中,编译器就会隐式生成指向数组第一个元素的指针,就像程序员编写了&a [0]一样.(例外情况是数组是sizeof或&运算符的操作数,或者是字符数组的字符串文字初始值设定项...)

...给定一个数组a和指针p,a [i]形式的表达式会导致数组衰减成指针,遵循上面的规则,然后被下标,就像表达式p中的指针变量一样[i](虽然最终的内存访问会有所不同......

鉴于.的声明

char a[] = "hello";
char *p = "world";
Run Code Online (Sandbox Code Playgroud)

...当编译器看到表达式时a[3],它会发出代码从该位置开始a,向后移动三个,然后在那里获取该字符.当它看到表达式时p[3],它会发出代码从该位置开始,在p那里获取指针值,向指针添加三个,最后获取指向的字符.换句话说,a[3]是指定对象的过去(开始)的三个位置a,而p[3]过去指向的对象是三个位置p.

重点是我的.最大的区别似乎是当指针是指针时获取指针,而如果它是数组则没有指向fetch的指针.

  • 链接中的这句话最简洁地说:"它的指针算法和数组索引在C中是等价的,指针和数组是不同的." (2认同)