'Moving the last element of a vector
What is the most efficient way to obtain the last (heavy) element from a vector and remove it, and make as few copies as possible? Is it
template <typaname T>
T moveLastElement (std::vector<T>& vec) {
T t = std::move(vec.back());
vec.pop_back();
return t;
}
Solution 1:[1]
Since we're talking about copy elision, and specifically NVRO, and I'm assuming @presto that you're compiling for (at minimum) C++17, there's an interesting edge case.
Suppose you have a function like this:
heavy_object fox_this_compiler ()
{
heavy_object h1;
heavy_object h2;
return (some_condition_that_cant_be_evaluated_at_compile_time) ? h1 : h2;
}
Now the compiler's in a quandry, because it can't construct both h1 and h2 at the call site, and that's what NVRO depends on. So (and I just ran a quick test), it returns a copy (and one of you language lawyers can tell me why).
So this is a case where explicitly moving from the object you're returning is worthwhile, as you can see in the:
I'm not sure if there's some kind of type trait to let you know if you need to do this in any particular instance, but if there is I don't know about it.
Edit: turns out there is a way. Just stick the call to std::move in there and if you don't need it, gcc will warn you (but if you do, it won't). Nifty. But, sadly, it won't warn you when you do need it and you fail to put it in.
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
| Solution | Source |
|---|---|
| Solution 1 | Paul Sanders |
