For the following code:
int (*ptr)[10];
int a[10]={99,1,2,3,4,5,6,7,8,9};
ptr=&a;
printf(\"%d\",(*ptr)[1]);
What should
int *ptr[10];
This is an array of 10 int*
pointers, not as you would assume, a pointer to an array of 10 int
s
int (*ptr)[10];
This is a pointer to an array of 10 int
It is I believe the same as int *ptr;
in that both can point to an array, but the given form can ONLY point to an array of 10 int
s
int (*p)[10]
is a pointer to an array of 10 integers in each row i.e there can be any number of rows. basically it can be used to point to a 2D array and the dimensions can be accessed by incrementing i
for *(p+i)[10]
which is same as a[i][10]
, here 'i=1,2,3...'
to access 1,2,3.. rows
.
where as, int *p[10]
is an array of 10 integer pointers.
If array is two dimesional i.e, for example
b[2][10]={{0,1,2,3,4,5,6,7,8,9},{10,11,12,13,14,15,16,17,18,19}};
basically,
(*ptr)[10] // where the higher dimension index is omitted i.e, 2
can be used as two dimensional pointer to an array(containing 10 elements in each row i.e, the 1st dimension) like (*ptr)[10] = &b
.
In the printf("%d",(*ptr)[1]);
as provided (*ptr)
is same as *(ptr+0)
evaluates to the first dimension i.e, b[0][0]
which value is 0. like wise, to access the 2nd dimension of the array b[1][0]
the expression will be **(ptr+1)
or *(ptr+1)[0]
or *(*(ptr+i)+j);
// where i=1 and j=0
gives the first element of the 2nd dimension i.e, 10.
I've answered it long so to understand it easy.
int(*)[10]
is a pointer to an int array with 10 members. i.e it points to int a[10]
.
where as int *[10]
is array of integer pointers
#include <stdio.h>
int main()
{
int *ptr[10];
int a[10]={0,1,2,3,4,5,6,7,8,9};
printf("\n%p %p", ptr[0], a);
*ptr=a; //ptr[0] is assigned with address of array a.
printf("\n%p %p", ptr[0], a); //gives you same address
printf("\n%d",*ptr[0]); //Prints zero. If *ptr[1] is given then *(ptr + 1) i.e ptr[1] is considered which is uninitialized one.
return 0;
}
int (*p)[10] means that p is now a pointer to an integer array of size 10.
int *p[10] means that p is an array of 10 integer pointers .
int (*ptr)[10];
is a pointer to an array of 10 ints.
int *ptr[10];
is an array of 10 pointers.
Reason for segfault:
*ptr=a; printf("%d",*ptr[1]);
Here you are assigning the address of array a
to ptr
which would point to the element a[0]
. This is equivalent to: *ptr=&a[0];
However, when you print, you access ptr[1]
which is an uninitialized pointer which is undefined behaviour and thus giving segfault.
The only two use cases for (*ptr)[10]
are:
Since the first case was already explained above by Sree harsha Punyasamudram, I am going to explain the more exotic use case.
#include <stdio.h>
typedef int arr1d10[10];
typedef int arr2d3[3][3];
void test1d0(arr1d10 *arr)
{
/* This is the same as the case with function test1d1(). */
printf("Element: %d\n", (*arr)[0]);
}
void test1d1(int (*arr)[10])
{
/* As arr is a pointer to an array of 10 integers, pointer arithmetic will work with the size of an array of 10 integers, i.e.
when you increment arr it will increment by sizeof(arr1d10), which is 40 bytes.
That's why when you dereference it, you can't simply do arr[1], because it will increment arr by 40 bytes forward.
Also when dereferencing it, because it thinks it points to a whole array it will give you that array - it's address.
This is another reason you can't do just arr[i], because those will be just addresses.
The correct way is to dereference it once(*arr)), to get the address (think of implicitely casting to int*) and then you can do as usually (*arr)[1]).
*/
printf("Element: %d\n", (*arr)[1]);
}
void test2d0(arr2d3 *arr2d)
{
/* This is a little more complicated, but the principle is the same as above. */
printf("Element: %d\n", (*arr2d)[0][0]);
}
void test2d1(int (*arr2d)[3][3])
{
printf("Element: %d\n", (*arr2d)[0][1]);
}
int main(void)
{
arr1d10 arr1d = {0, 1, 2};
arr2d3 arr2d = { {0,1},{2,3},{3,4}};
int (*p1d)[10] = &arr1d;
int (*p2d)[3][3] = &arr2d;
printf("********** PRINT 1D array **********\n");
test1d0(&arr1d);
test1d1(&arr1d);
test1d0(p1d);
test1d1(p1d);
printf("********** PRINT 2D array **********\n");
test2d0(&arr2d);
test2d1(&arr2d);
test2d0(p2d);
test2d1(p2d);
return 0;
}