# How does subtracting an address reference work?

I think the value of `z` should be 40 because `a[5]` has 20 elements, and the space between it and `a[3]` also has 20 elements. However, the actual value of `z` is 2.

Can anyone explain this concept?

``````#include <stdio.h>

int main()
{
int a[10][20];
int z = &a[5] - &a[3];
printf("%d\n", &a[3]); // the address information is 6421740
printf("%d\n", &a[5]); // the address information is 6421900
printf("%d\n", z);     // z value is 2. why?
}
``````

Solution

• According to the C Standard (6.5.2.1 Array subscripting)

2 A postfix expression followed by an expression in square brackets [] is a subscripted designation of an element of an array object. The definition of the subscript operator [] is that E1[E2] is identical to (*((E1)+(E2))). Because of the conversion rules that apply to the binary + operator, if E1 is an array object (equivalently, a pointer to the initial element of an array object) and E2 is an integer, E1[E2] designates the E2-th element of E1 (counting from zero).

So the expression `a[3]` is evaluated like `*( a + 3 )`. As a result the expression `&a[3]` is equivalent to the expression `&*( a + 3 )` that in turn is equivalent to `( a + 3 )`.

The same way the expression `&a[5]` is equivalent to the expression `( a + 5 )`.

So the difference `&a[5] - &a[3]` is evaluated like `( a + 5 ) - ( a + 3 )` that yields `2`. That is between these two addresses `&a[5]` and `&a[3]` there are only two elements of the type `int[20]`.

On the other hand if you would write `( int * )&a[5] - ( int * )&a[3]` that is if the array would be interpreted as a one-dimensional array of the type `int` you would get `2 * 20` that yields the expected by you value `40`.