I have couple of snippets:
main()
{
int a[] = {1,2,3,45};
printf("%p\n", a); /* as expected print address of first element of array */
printf("%p\n", a 1); /* expecting it to print address after this array ends as type of a is int[4] and pointer arithmetic says size of type is added to it, i.e. 16 bytes but its printing address of second element of array a,
}
Similarly this snippet:
int main()
{
int *a[] = {0,1,2,3,4};
printf("arr0=%d\n", *a 0);
printf("arr1=%d\n", *a 1);
printf("arr2=%d\n", *a 2);
printf("arr3=%d\n", *a 3);
printf("arr4=%d\n", *a 4);
return 0;
}
It outputs:
0
4
8
12
16
But since pointer size is 8 bytes, and as every member of this array is pointer then why pointer size is not adding up to produce ?
0
8
16
24
32
CodePudding user response:
When an array in used in an expression, in most cases it will decay to a pointer to its first element.
Taking this example:
printf("%p\n", a 1);
First a
decays from type int[4]
to int *
so it points to the first element of the array. Adding 1 to this causes it to point to the second element of the array.
Had you done this:
printf("%p\n", &a 1);
The &
operator is one of the few cases where an array does not decay, so &a
has type int (*)[4]
i.e. a pointer to an array of size 4. Adding 1 to this results in a pointer pointing to just after the end of the array.
CodePudding user response:
Array designators used in expressions with rare exceptions are implicitly converted to pointers to their first elements.
So in the first code snippet in the call of printf
the array a
is converted to a pointer to its first element of the type int *
int a[] = {1,2,3,45};
//...
printf("%p\n", a 1)
Due to the pointer arithmetic the value of the expression a 1
is incremented relative to the expression a
by sizeof( int )
that is equal to 4
in your system.
In the second code snippet the expression *a
that is the same as a[0]
has the type int *
So the value of the expression *a 1
is also incremented by the value sizeof( int )
.
Pay attention to that using the conversion specifier %d with a pointer expression in statements like this
printf("arr0=%d\n", *a 0);
has undefined behavior. You have to write
printf("arr0=%p\n", ( void * )( *a 0 ));