数组名称和数组名称的地址如何打印相同的值?

时间:2018-03-13 16:53:08

标签: c arrays memory-address

请考虑以下代码段。

int main(){
    int x[2];
    x[0]=100;
    x[1]=200;
    printf("%d\n",x);
    printf("%d\n",&x);
    printf("%d\n",*x);
}   

输出为(三行)

6487616  6487616 100

我读过数组名是指向数组第一个元素的指针。因此,'x'的值打印内存地址。但是,如果我尝试打印保存数组第一个元素的地址的指针的地址,为什么还打印相同的内存地址?不应该打印另一个内存地址,因为为了让变量存储一个内存地址,它应该是一个指针,而指针变量在RAM中也有一个内存地址。

int main(){
   int y = 10;
   int *p = &y;

   printf("%d\n",&y);
   printf("%d\n",&p);   
}

上面的代码将输出显示为

6487628 6487616

那么为什么在数组方面这不起作用呢?

4 个答案:

答案 0 :(得分:4)

与您可能听到的相反,数组和指针不是一回事。数组是给定类型的一个或多个元素的序列,而指针指向存储器位置(可以是数组的第一个元素)。因此,数组的地址与第一个元素的地址相同。

混淆的地方在于,在大多数表达式中,数组衰减成指向第一个元素的指针。这种衰减没有发生的一种情况是当数组是地址运算符&的主语时。

在第一段代码中,首先打印x。暂时忽略您应该使用%p来打印指针而不是%d,此处x会衰减成指向第一个元素的指针,并且该地址是打印的。在下一次调用printf时,您会传入&x。它具有与x相同的值(转换为指针时)但具有不同的类型,即x具有类型int [2](衰减到int *)和{{ 1}}的类型为&x

在第二个示例中,int (*)[2]yintp。这些是单独的变量,因此每个变量都有不同的地址。

答案 1 :(得分:0)

首先,要打印内存地址,应使用%p代替%d;使用%d实际上是未定义的行为,即使它经常有效:

int main(){
    int x[2];
    x[0]=100;
    x[1]=200;
    printf("%p\n",(void*)x);
    printf("%p\n",(void*)&x);
    printf("%d\n",*x);
}

其次,&x不会引入新的对象/变量,而是使用对象x的地址。使用x衰减到指向数组对象x的第一个元素的指针,这相当于&x&x[0]。同样的对象 - >相同的地址,因此,x&x&x[0]会为您提供相同的地址。

在另一个示例中,您引入了一个新对象p,它与对象x不同。这就是&p&x提供不同地址的原因

答案 2 :(得分:-1)

你听到的内容有些不正确。

数组不是"常量指针"。数组是一个数组。

在表达式中使用数组时,得到的是指向数组第一个元素的指针。

该指针将具有相同的值(尽管是不同的类型)作为指向整个数组的指针。

这些事实说明了你看到的结果。

答案 3 :(得分:-1)

您应该使用%p打印内存地址

#include <stdio.h>

int main(){
   int y = 10;
   int *p = &y;

   printf("%p\n",&y);
   printf("%p\n",&p);
}

输出:

0x7ffeed2dd6fc

0x7ffeed2dd6f0

顺便说一下

int main(){
    int x[2];
    x[0]=100;
    x[1]=200;
    printf("%p\n",x); // u should use %p here
    printf("%p\n",&x); // this is the address of the array same as upper
    printf("%d\n",*x); // this is the value of x it's same as x[0]
}