Please Explain the ambiguity in pointers in C?
#include<stdio.h>
main()
{ int x[3][5]={{1,2,10,4,5},{6,7,1,9,10},{11,12,13,14,15}};
printf("%d\n",x);
printf("%d\n",*x); }
Here first printf will print the address of first element. So why not the second printf prints the value at the address开发者_如何学Python x i.e the first value. To print the value I need to write **x.
For pointers, x[0]
is the same as *x
. It follows from this that *x[0]
is the same as **x
.
In *x[0]
:
x
is a int[3][5]
, which gets converted to int(*)[5]
when used in expression. So x[0] is lvalue of type int[5]
(the first 5-element "row"), which gets once again converted to int*
, and dereferenced to its first element.
*x
is evaluated along the same lines, except the first dereference is done with an asterisk (as opposed to indexing), and there is no second dereference, so we end up with lvalue of type int[5]
, which is passed to printf
as a pointer to its first element.
Arrays, when used as arguments to functions, decay into pointers to the first element of the array. That being said, the type of object that x
decays into is a pointer to the first sub-array, which is a pointer to an array of int
, or basically int (*)[5]
. When you call printf("%d\n",*x)
, you are not feeding an integer value to printf
, but rather a pointer to the first sub-array of x
. Since that sub-array will also decay to a pointer to the first sub-array's element, you can do **x
to dereference that subsequent pointer and get at the first element of the first sub-array of x
. This is effectively the same thing as *x[0]
, which by operator precedence will index into the first sub-array of x
, and then dereference the pointer to the first sub-array's element that the first sub-array will decay into.
Because of type of *x
is 'pointer to array of 5 ints'. So, you need one more dereference to get the first element
PS:
#include <typeinfo>
#include <iostream>
typedef int arr[5]; // can't compile if put arr[4] here
void foo(arr& x)
{
}
int main()
{
int x[3][5]={{1,2,10,4,5},{6,7,1,9,10},{11,12,13,14,15}};
std::cout << typeid(*x).name() << std::endl;// output: int [5]
foo(x[0]);
return 0;
}
Think about a 2-d array as an array of pointers, with each element in the array pointing to the first element in another array. When you dereference x
, you get the value that is in the memory location pointed to by x... a pointer to the first int
in an array of int
s. When you dereference that pointer, you will get the first element.
精彩评论