我刚开始讲指针,有点困惑。我知道&意味着一个变量的地址,*可以用在一个指针变量前面,以获得指针所指向的对象的值。但是当你使用数组、字符串或者使用变量的指针副本调用函数时,情况就不同了。很难看出其中的逻辑模式。

什么时候应该使用&和*?


当前回答

你有指针和值:

int* p; // variable p is pointer to integer type
int i; // integer value

使用*将指针转换为值:

int i2 = *p; // integer i2 is assigned with integer value that pointer p is pointing to

使用&将一个值转换为指针:

int* p2 = &i; // pointer p2 will point to the address of integer i

编辑: 在数组的情况下,它们被处理得非常像指针。如果你认为它们是指针,你将使用*来获取它们内部的值,就像上面解释的那样,但还有另一种更常见的使用[]操作符的方式:

int a[2];  // array of integers
int i = *a; // the value of the first element of a
int i2 = a[0]; // another way to get the first element

要得到第二个元素:

int a[2]; // array
int i = *(a + 1); // the value of the second element
int i2 = a[1]; // the value of the second element

所以[]索引操作符是*操作符的一种特殊形式,它是这样工作的:

a[i] == *(a + i);  // these two statements are the same thing

其他回答

简单地说

&表示地址,你会看到在C语言中修改参数变量的函数占位符中,参数变量是按值传递的,使用&表示按引用传递。 *表示指针变量的解引用,即获取该指针变量的值。

int foo(int *x){
   *x++;
}

int main(int argc, char **argv){
   int y = 5;
   foo(&y);  // Now y is incremented and in scope here
   printf("value of y = %d\n", y); // output is 6
   /* ... */
}

上面的例子说明了如何使用引用传递来调用函数foo,与此比较

int foo(int x){
   x++;
}

int main(int argc, char **argv){
   int y = 5;
   foo(y);  // Now y is still 5
   printf("value of y = %d\n", y); // output is 5
   /* ... */
}

下面是使用解引用的示例

int main(int argc, char **argv){
   int y = 5;
   int *p = NULL;
   p = &y;
   printf("value of *p = %d\n", *p); // output is 5
}

上面说明了我们如何获得y的地址并将其赋值给指针变量p。然后我们通过将*附加到p的前面来解引用p,以获得p的值,即*p。

好吧,看起来你的帖子被编辑了…

double foo[4];
double *bar_1 = &foo[0];

看看如何使用&来获取数组结构开头的地址?以下

Foo_1(double *bar, int size){ return bar[size-1]; }
Foo_2(double bar[], int size){ return bar[size-1]; }

会做同样的事情。

你有指针和值:

int* p; // variable p is pointer to integer type
int i; // integer value

使用*将指针转换为值:

int i2 = *p; // integer i2 is assigned with integer value that pointer p is pointing to

使用&将一个值转换为指针:

int* p2 = &i; // pointer p2 will point to the address of integer i

编辑: 在数组的情况下,它们被处理得非常像指针。如果你认为它们是指针,你将使用*来获取它们内部的值,就像上面解释的那样,但还有另一种更常见的使用[]操作符的方式:

int a[2];  // array of integers
int i = *a; // the value of the first element of a
int i2 = a[0]; // another way to get the first element

要得到第二个元素:

int a[2]; // array
int i = *(a + 1); // the value of the second element
int i2 = a[1]; // the value of the second element

所以[]索引操作符是*操作符的一种特殊形式,它是这样工作的:

a[i] == *(a + i);  // these two statements are the same thing

当你声明一个指针变量或函数形参时,使用*:

int *x = NULL;
int *y = malloc(sizeof(int)), *z = NULL;
int* f(int *x) {
    ...
}

注意:每个声明的变量都需要自己的*。

当你想获取一个值的地址时,使用&。当您想读写指针中的值时,请使用*。

int a;
int *b;
b = f(&a);
a = *b;

a = *f(&a);

数组通常就像指针一样。当你在函数中声明一个数组形参时,你可以很容易地声明它是一个指针(它的意思是一样的)。当你将一个数组传递给一个函数时,你实际上是在传递一个指向第一个元素的指针。

函数指针是唯一不完全遵循规则的东西。你可以不使用&而获取函数的地址,也可以不使用*而调用函数指针。

事实上,你已经掌握了,没有什么你需要知道的了:-)

我想补充以下几点:

这两种操作是截然相反的。&接受一个变量并给你地址,*接受一个地址并给你变量(或内容)。 将数组传递给函数时,数组“降级”为指针。 实际上你可以在间接上有多个层次(char **p表示p是指向一个char的指针的指针。

至于事情的运作方式不同,其实不是这样的:

如前所述,数组在传递给函数时降级为指针(指向数组中的第一个元素);它们不保存大小信息。 C语言中没有字符串,只有字符数组,按照惯例,表示以0(\0)字符结束的字符串。 当你将一个变量的地址传递给一个函数时,你可以去引用指针来改变变量本身(通常变量是按值传递的(数组除外))。