Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Explicit decay of an array into a pointer

What is the most concise and idiomatic way of explicitly decaying an array into a pointer?


For example, consider the case where you need to be able to guide SFINAE or be explicit about an overload:

template<typename T, std::size_t N> void foo(T(&x)[N]);
template<typename T>                void foo(T *x); 
//
int x[2] = {0, 1};
foo(x);
like image 962
mockinterface Avatar asked Apr 11 '14 12:04

mockinterface


People also ask

What does it mean to decay an array to a pointer?

The loss of type and dimensions of an array is known as array decay. It occurs when we pass the array into a function by pointer or value. First address is sent to the array which is a pointer. That is why, the size of array is not the original one.

Can we assign array to pointer?

It is legal to use array names as constant pointers, and vice versa. Therefore, *(balance + 4) is a legitimate way of accessing the data at balance[4]. In the above example, p is a pointer to double, which means it can store the address of a variable of double type.

Can you pass an array as a pointer in C?

Array can be passed to function in C using pointers and because they are passed by reference changes made on an array will also be reflected on the original array outside function scope.

What is the relationship between array and pointer give example?

An array is represented by a variable that is associated with the address of its first storage location. A pointer is also the address of a storage location with a defined type, so D permits the use of the array [ ] index notation with both pointer variables and array variables.


Video Answer


3 Answers

You may use one of the following:

foo(x + 0);
foo(+x);
foo(&x[0]); // assuming operator& has not been overloaded for T
foo(std::addressof(x[0])); // since C++11
like image 120
Jarod42 Avatar answered Oct 21 '22 22:10

Jarod42


The most concise and idiomatic ? I would say taking the address of the first element

foo(&x[0]);

UPDATE

Since c++11 there's a standard way of saying the above:

auto a = std::addressof(x[0]); // a will be * to int

adressof has the following signature

template<class T> T* addressof(T& arg);

and Obtains the actual address of the object or function arg, even in presence of overloaded operator&

Another idea (which also has the advantage of the above) would be to write

auto a = std::begin(x); // a will be * to int

additionally this works with arrays of incomplete types because it requires no application of [0]

UPDATE 2

Since c++ 14 there's even more explicit functionality on this : std::decay

like image 5
Nikos Athanasiou Avatar answered Oct 21 '22 21:10

Nikos Athanasiou


The stock &x[0] always felt awkward to me because the array in question can be an array of incomplete types, and it is of course invalid to apply a subscript operator to one. Consider this instead,

foo(&*x);

this is only one more characters to type than foo(+x) which is far less readable and harder to grok.

like image 2
mockinterface Avatar answered Oct 21 '22 21:10

mockinterface