为什么int的地址能够被视为指向int的指针?

时间:2012-10-13 21:57:26

标签: c pointers reference

我很困惑为什么这段代码有效。我被教导说指针是一个“胶囊”,上面有东西的地址。所以swapnum函数应该期待其中一个“胶囊”,而不是int的实际地址。它是否正在创建临时指针并将其设置为该地址?如果是这种情况,那么如果我通过int * c = &a; swapnum (&c...之类的引用传入指针会发生什么?

#include <stdio.h>

void swapnum(int *i, int *j) {
  int temp = *i;
  *i = *j;
  *j = temp;
}

int main(void) {
  int a = 10;
  int b = 20;

  swapnum(&a, &b);
  printf("A is %d and B is %d\n", a, b);
  return 0;
}

6 个答案:

答案 0 :(得分:3)

pointer只是地址的另一个词。关于它没有什么神奇之处,它只是一个包含数字的变量,该数字是它指向的东西的内存地址。

在您的示例中,内存可能如下所示:

0x00001004 - 10         # a
0x00001008 - 20         # b
0x0000100C - 0x0001004  # i
0x00001010 - 0x0001008  # j
0x00001014 - 00         # temp

ij都是int*,这意味着它们包含一个包含整数的地址。代码*i表示“返回i中地址的任何值,并假设它是int

所以,如果你看一下你的swapnum,会发生什么:

int temp = *i;
# take the value at 0x0001004 (10) and place it in 0x00001014

*i = *j;
# place the value at 0x0001008 (20) and place it in 0x00001004

*j = temp;
# place the value at 0x0001014 (10) and place it in 0x0001008

之后内存如下:

0x00001004 - 20         # a
0x00001008 - 10         # b
0x0000100C - 0x0001004  # i
0x00001010 - 0x0001008  # j
0x00001014 - 10         # temp

你当然可以这样做:

int* c = &a;
swapnum(c, &b);

您所做的就是获取a的地址,将其放入c,然后将其传递到需要地址的swapnum。指针只是一个地址。

答案 1 :(得分:2)

对象的地址是指向对象的指针!实际上,这就是指针的全部内容:它们现在处于对象所在的地址。使用地址而不是对象的重点是使用具有相同对象的地址。

答案 2 :(得分:1)

&item返回指向item的指针。

此外,在所有现代架构中,我知道指针只是项目的地址。

如果您指向指针并将其传递给swapnum,则会发生以下两种情况之一:

  1. 您的编译器会抱怨,因为指针的类型为int * ,而不是int
  2. 您将交换指针的值。至少如果指针的大小与整数相同

答案 3 :(得分:1)

main中,您使用地址 - &运算符将swapnum和{{1}的地址传递给a }}

实际指针的值是地址。根本没有“胶囊”! (也许,更容易将它们视为没有胶囊的普通地址!)。

如果您执行了b,则可以将c传递给int *c = &a而不是swapnum(),这样就可以了。您无法通过&a,因为您要传递&c,而该函数需要int **

答案 4 :(得分:1)

&a是一个表达式,在内存中被评估为a's地址。该值必须存储在类型指针的变量中。例如:

int* i = &a;

此处,iint pointer类型的变量,它充当分配给它的值的容器,一个包。但是,此胶囊本身不保留a值;它保留&a值。另外,作为一个胶囊是一般变量的直接结果;不一定是因为它是pointer类型的变量。

现在,这句话:

swapnum(&a, &b);

做一个非常正常的工作,将参数复制到一些局部变量 - 一个正常的值传递函数调用。在这种情况下,实际发生的是它将&a值(即a's地址)复制到局部变量i中,当然,需要将其定义为类型{{ 1}}。

如果您定义:

int pointer

然后致电:

int * c = &a; 

这不起作用,因为swapnum (&c... 将是c类型的变量;那么int pointer就是这样一个变量的地址;因此,应该将包含此地址的局部变量类型&c定义为此类值的容器;即它应该被定义为指向iint pointer

地址的类型指针的变量

这种函数调用没有相应地改变函数肯定会导致编译器时间错误。

答案 5 :(得分:0)

C ++是一种静态类型语言。这意味着每个表达式都有一个已知的编译时特定类型。 C ++标准告诉我们,如果表达式expr是内置类型T,则表达式&amp; expr的类型为T *(指向T的指针)。这都是......