Vincent
Vincent

Reputation: 60381

C array vs pointer : array is considered as a variable, array+0 is considered as a pointer?

I've made a container class in C++, and I have a constructor from iterators so I can write MyContainer<double> x(v.begin(), v.end()) where v is a std::vector<double>. I would like to be able to do the same with a c-array but :

double array[3] =  {1., 2. , 3.};
MyContainer<double> x(array, array+3); // Doesn't work : no matching function for call to ‘MyContainer<double>::MyContainer(double [3], double*)’
MyContainer<double> x(array+0, array+3); // Work

What is the origin of the problem and how to solve it ?

Thank you very much.

Upvotes: 2

Views: 165

Answers (2)

Potatoswatter
Potatoswatter

Reputation: 137810

Don't accept references to iterators, take them by value. It's trying to pass a reference to an array; the failing expression needs the array to decay to a pointer.

Presumably you have

template< typename Iter >
MyContainer( Iter const &first, Iter const &last );

but you need

template< typename Iter >
MyContainer( Iter first, Iter last );

Iterators need to be lightweight enough to pass by value; all the standard templates do so.

An array cannot be used as an iterator because it cannot be incremented. The storage is fixed. When you use an array in an expression like arr + 0 or pass it by value to a function, it is implicitly converted to a pointer to its first element. But that conversion doesn't happen when passing by reference.

Upvotes: 4

Sergey Kalinichenko
Sergey Kalinichenko

Reputation: 726559

The result of array+0 is a pointer, while array itself is not a pointer, it is an array. Your constructor does not have an overload that takes an array and a pointer, hence the compile fails.

The idiomatic way of dealing with the problem of making the beginning and the ending iterators from an array is using the begin(...) and end(...) functions:

MyContainer<double> x(std::begin(array), std::end(array));

The overload takes care of figuring out where the end of your array is, freeing you from the need to add array's length to the pointer.

Upvotes: 3

Related Questions