0
#include <iostream>
using namespace std;
int main(){
    int a[5][5]={{2,4,6,8,10},{12,14,16,18,20}};
    cout <<sizeof(*(a))<<endl;
    cout <<sizeof(*(a+0))<<endl;
}

I am confused as to why the sizeof the pointer to a is 20. I thought *a gives you the address of a[0][0]. Is this giving us the size of the actual pointer or the size of the address the pointer is pointing to?

  • 2
    2D arrays are actually arrays of arrays. `*a` gives you the first element of `a`, which is `a[0]` - an array of 5 integers. So, `sizeof(int) * 5` is 20. – Adrian Mole Apr 11 '22 at 14:39
  • @AdrianMole answers should be posted as an answer, not a comment. – Mark Ransom Apr 11 '22 at 14:42
  • If you're thinking that you'll get array-to-pointer decay, then that doesn't apply to the arguments of the `sizeof` operator. [Why does decay to pointer for array argument appear not to apply to sizeof()?](https://stackoverflow.com/q/11283361/10871073) – Adrian Mole Apr 11 '22 at 14:43
  • 2
    @MarkRansom I suspected a duplicate, so went looking ... – Adrian Mole Apr 11 '22 at 14:44
  • Not an answer to your question, but a short explanation of what I suspect your underlying confusion is: Arrays *decaying* to pointers does not mean that they **are** pointers. –  Apr 11 '22 at 14:44
  • So what exactly does `cout << a;` return? If `cout << &(a[0][0]) < – Bint Euler Apr 11 '22 at 14:45
  • "why the sizeof the pointer to a is 20" --> `*(a)` is not a _pointer_ to `a`. – chux - Reinstate Monica Apr 11 '22 at 14:56
  • @BintEuler `cout << &(a[0][0]) < – Peter Apr 11 '22 at 15:15

1 Answers1

2

I am confused as to why the sizeof the pointer to a is 20.

The size of a pointer to a is typically not 20.

I thought *a gives you the address of a[0][0]

It does not. The unary * is the indirection operator. When you indirect through a pointer, you get the pointed value. It's the opposite operation of getting an address.

Now, a is not a pointer. It is an array. But an array can implicitly convert to a pointer to the first element. So, a which is an array of 5 arrays of 5 ints implicitly converts to a pointer to an array of 5 ints. When you indirect through that pointer, the result is an lvalue to an array of 5 ints that is the first element of a.

You are printing the size of an array of 5 ints. That happens to be 20 on your system.

Does that mean that a itself stores all the memory for all 5 integers ...

An array stores all of its elements within itself. a stores all the memory of all 5 arrays, and each of the arrays contains the memory of all 5 integers each (25 in total).

but [cout << a;] only prints the address of the first one?

There are no stream insertion operator overloads for arrays. But, there is a stream insertion operator overload for void*, and array can implicitly convert to a pointer to first element which can implicitly convert to void*. So, you are printing the address of the first element of the array.

eerorika
  • 232,697
  • 12
  • 197
  • 326