Erasing() an element in a vector doesn't work
If there are at least 3 items in the vector, to delete the last 3 items is simple -- just call pop_back 3 times:
#include <vector>
#include <iostream>
int main()
{
std::vector<float> v = { 1, 2, 3, 4, 5 };
for (int i = 0; i < 3 && !v.empty(); ++i)
v.pop_back();
for ( const auto &item : v ) std::cout << item << ' ';
std::cout << '\n';
}
Output:
1 2
It is undefined behavior to pass the end()
iterator to the 1-parameter erase()
overload. Even if it weren't, erase()
invalidates iterators that are "at and after" the specified element, making d
invalid after the 1st loop iteration.
std::vector
has a 2-parameter erase()
overload that accepts a range of elements to remove. You don't need a manual loop at all:
if (X.size() >= 3)
X.erase(X.end()-3, X.end());
Live Demo
You could use a reverse_iterator
:
#include <iostream>
#include <vector>
using namespace std;
int main()
{
vector<float> X = {1.1, 2.2, 3.3, 4.4, 5.5, 6.6};
// start the iterator at the last element
vector<float>::reverse_iterator rit = X.rbegin();
// repeat 3 times
for(size_t i = 0; i < 3; i++)
{
rit++;
X.erase(rit.base());
}
// display all elements in vector X
for(float &e: X)
cout << e << '\n';
return 0;
}
There are few things to mention:
reverse_iterator rit
starts at the last element of thevector X
. This position is calledrbegin
.erase
requires classiciterator
to work with. We get that fromrit
by callingbase
. But that new iterator will point to the next element fromrit
in forward direction.- That's why we advance the
rit
before callingbase
anderase
Also if you want to know more about reverse_iterator
, I suggest visiting this answer.