What is array-to-pointer conversion aka. decay? Is there any relation to array pointers?
C++ Arrays – Understanding Array-to-Pointer Conversion (Decay)
arraysc++pointers
Related Solutions
C 2011 6.3.2.1 3:
Except when it is the operand of the sizeof operator,… or the unary & operator, or is a string literal used to initialize an array, an expression that has type “array of type” is converted to an expression with type “pointer to type” that points to the initial element of the array object and is not an lvalue.
In other words, arrays usually decay to pointers. The standard lists the cases when they do not.
One might think that arrays act as arrays when you use them with subscripts, such as a[3]
. However, what happens here is actually:
a
is converted to a pointer.- The subscript operator acts on the pointer and the subscript to produce an lvalue designating the object. (In particular,
a[3]
is evaluated as*((a)+(3))
. That is,a
is converted to a pointer, 3 is added to the pointer, and the ***** operator is applied.)
Note: The C 2011 text includes “the _Alignof operator.” This was corrected in the C 2018 version of the standard, and I have elided it from the quote above. The operand of _Alignof
is always a type; you cannot actually apply it to an object. So it was a mistake for the C 2011 standard to include it in 6.3.2.1 3.
void test(int* array);
void test(int array[]);
void test(int array[3]);
All these variants are the same. C just lets you use alternative spellings but even the last variant explicitly annotated with an array size decays to a pointer to the first element.
That is, even with the last implementation you could call the function with an array of any size:
void test(char str[10]) { }
test("test"); // Works.
test("let's try something longer"); // Still works.
There is no magic solution, the most readable way to handle the problem is to either make a struct
with the array + the size or simply pass the size as an additional parameter to the function.
LE: Please note that this conversion only applies to the first dimension of an array. When passed to a function, an int[3][3]
gets converted to an int (*)[3]
, not int **
.
Best Answer
It's said that arrays "decay" into pointers. A C++ array declared as
int numbers [5]
cannot be re-pointed, i.e. you can't saynumbers = 0x5a5aff23
. More importantly the term decay signifies loss of type and dimension;numbers
decay intoint*
by losing the dimension information (count 5) and the type is notint [5]
any more. Look here for cases where the decay doesn't happen.If you're passing an array by value, what you're really doing is copying a pointer - a pointer to the array's first element is copied to the parameter (whose type should also be a pointer the array element's type). This works due to array's decaying nature; once decayed,
sizeof
no longer gives the complete array's size, because it essentially becomes a pointer. This is why it's preferred (among other reasons) to pass by reference or pointer.Three ways to pass in an array1:
The last two will give proper
sizeof
info, while the first one won't since the array argument has decayed to be assigned to the parameter.1 The constant U should be known at compile-time.