c++vectoriteratorerasereverse-iterator

Erasing element from a vector – rbegin() vs begin()


I'm trying to solve a problem in C++, a part of which requires me to erase elements from a vector using the rbegin() member function. However, the compiler throws an error every time I write the below-mentioned code. What's wrong here?

int main() {

    int a = 1, b = 2;

    vector<int> V = {a, b};

    auto it = V.rbegin();
    V.erase(it);

    return 0;
}

ERROR:

It compiles just fine, however, if I access the same element using the begin() member function. The code below works fine.

int main() {

    int a = 1, b = 2;

    vector<int> V = {a, b};

    auto it = V.begin()+1;
    V.erase(it);

    return 0;
}

Solution

  • There is no std::vector::erase() overload for reverse_iterator. However, you can obtain the corresponding iterator from a reverse_iterator by calling its base() member function:

    auto rit = V.rbegin();
    auto it = rit.base();
    V.erase(it);
    

    This code does compile but results in undefined behavior because the iterator counterpart of rbegin() corresponds to end(). From std::vector::erase() documentation:

    iterator erase(const_iterator pos);
    

    The iterator pos must be valid and dereferenceable. Thus the end() iterator (which is valid, but is not dereferencable) cannot be used as a value for pos.


    rbegin().base() returns end(), not end() - 1. Nevertheless, you can advance rbegin() by one if you want a dereferencable iterator:

    auto it = (std::next(rit)).base();