[这个问题是我在Sem-2考试中提出的。问题要求我们提供所需的输出。
int main(void)
{
int a[] = {10,20,30,40,50,60};
int (*p1)[2]=a , (*p2)[3]= a;
if(sizeof(p1)==sizeof(p2))
printf("%d",*(*p1+2));
if(sizeof(*p1)==sizeof(*p2))
printf("%d",*(*(p2+1)));
return(0);
}
编译器警告:
Warning: initialization from incompatible pointer type [-Wincompatible-pointer-types]
initialization from incompatible pointer type [-Wincompatible-pointer-types]
我期望的输出:20
运行时得到的输出:30
使用:gcc(Ubuntu 7.4.0-1ubuntu1〜18.04.1)7.4.0
让我们忽略未定义的行为以找出可能发生的情况。
[p1
和p2
都都指向a[0]
(忽略不兼容的指针类型)。
p1
和p2
都是指针。指向对象类型的指针通常具有相同的大小(假设是这种情况),因此sizeof(p1)==sizeof(p2)
为true。
p1
的类型为int (*)[2]
,因此*p1
的类型为int[2]
。在大多数表达式中,数组将衰减为其第一个元素的指针,因此在表达式*(*p1+2)
中,*p1
将衰减为int *
并指向a[0]
。因此,*p1+2
将指向a[2]
。因此,*(*p1+2)
将与a[2]
相同,其值为30
。因此,程序将打印30
。
当数组是sizeof
运算符的操作数时,它不会衰减到指针。 *p1
的类型为int[2]
,*p2
的类型为int[3]
,因此sizeof(*p1)==sizeof(*p2)
等效于sizeof(int[2])==sizeof(int[3])
,这是错误的。因此,不评估第二次打印printf
值的*(*p2+1)
调用。
(假设第二个printf
被调用,并且对*(*p2+1)
进行求值。*p2
的类型为int[3]
,在此表达式中,它衰减为指向int *
的a[0]
。因此,*p2+1
指向a[1]
。因此,*(*p2+1)
与a[1],
相同,其值为20
。)