Это:
vLine[i].erase();
не стирает vLine[i]
из вектора.Выражение vLine[i]
возвращает ссылку на элемент с индексом i
.Таким образом, предполагая, что vLine
имеет тип std::vector<std::string>
, вызов функции erase()
фактически вызывает string::erase()
для элемента, а не vector::erase()
для вектора.Все, что вы делаете, это делаете этот конкретный элемент пустым.
То, что вам, вероятно, нужно, выглядит примерно так:
vLine.erase(vLine.begin() + i);
Это фактически удаляет элемент из вектора.Теперь это делает недействительными все текущие итераторы для вектора, и индексы больше не будут правильными.Это ситуация, когда вам действительно нужно использовать итераторы.
std::vector<std::string>::iterator i = vLine.begin();
while(i != vLine.end())
{
if(i->find(';', 0) != std::string::npos)
{
i = vLine.erase(i);
}
else
{
++i;
}
}
Но есть еще более простой способ сделать это: использовать стандартный алгоритм std::remove_if()
с функтором, а затем вызвать vLine.erase()
.
struct HasSemicolon
{
bool operator()(const std::string& s)
{
return s.find(';', 0) != std::string::npos;
}
};
// ...
vLine.erase(std::remove_if(vLine.begin(), vLine.end(), HasSemicolon()), vLine.end());
Если вы можете использовать компилятор C ++ 11, то вы также можете использовать лямбда-выражения, чтобы быть еще более кратким.