There are two existing questions about replacing vector elements that are not assignable:
A typical reason for an object to be non-assignable is that its class definition includes const
members and therefore has its operator=
deleted.
std::vector
requires that its element type be assignable. And indeed, at least using GCC, neither direct assignment (vec[i] = x;
), nor a combination of erase()
and insert()
to replace an element works when the object is not assignable.
Can a function like the following, which uses vector::data()
, direct element destruction, and placement new with the copy constructor, be used to replace the element without causing undefined behaviour?
template <typename T>
inline void replace(std::vector<T> &vec, const size_t pos, const T& src)
{
T *p = vec.data() + pos;
p->~T();
new (p) T(src);
}
An example of the function in use is found below. This compiles in GCC 4.7 and appears to work.
struct A
{
const int _i;
A(const int &i):_i(i) {}
};
int main() {
std::vector<A> vec;
A c1(1);
A c2(2);
vec.push_back(c1);
std::cout << vec[0]._i << std::endl;
/* To replace the element in the vector
we cannot use this: */
//vec[0] = c2;
/* Nor this: */
//vec.erase(begin(vec));
//vec.insert(begin(vec),c2);
/* But this we can: */
replace(vec,0,c2);
std::cout << vec[0]._i << std::endl;
return 0;
}