I've just written the following code, and was very surprised it doesn't compile:
std::deque<int> container;
// filling the container...
for (auto it = container.rbegin(); it != container.rend(); ++it)
if (*it == 5)
{
container.erase(it);
break;
}
As you can see, I want to delete the last element matching a certain criteria, if any.
The error is
no matching function for call to std::deque::erase(std::reverse_iterator...
At first I didn't believe it was caused by the reverse iterator, but that is indeed the case since replacing rbegin
/rend
with begin
/end
solves it.
So, 2 questions:
All of the iterators, and references, which are after the deletion point, are invalidated. Same as like insert or erase. All iterators and the references are invalidated if the inserted item is not inserted at the end of the deque.
C++ Iterators Reverse IteratorsA reverse iterator is made from a bidirectional, or random access iterator which it keeps as a member which can be accessed through base() . To iterate backwards use rbegin() and rend() as the iterators for the end of the collection, and the start of the collection respectively.
I figure that the quantity of additional overloads that would need to be added throughout the standard library make this an unseemly task, when there is no "need" for it.
Sure, the "most elegant" workaround is hardly expressive:
container.erase((it+1).base());
…but there is one, and reverse iterators are likely not used often enough to warrant all the extra noise that would be caused by having overloads everywhere that do nothing but wrap the above line of code.
If you find yourself using it a lot, you can wrap the more general solution yourself:
template <typename ReverseIterator>
auto AsForwardIterator(ReverseIterator rit)
{
std::advance(rit, 1);
return rit.base();
}
Then it's just:
container.erase(AsForwardIterator(it));
And, quite frankly, the simplicity of this seems worth not having all those overloads in every container.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With