Я использую функцию vector :: erase (), чтобы удалить первый элемент в векторе, пока он не станет пустым, но мой компилятор выдает ошибку «Invalid Pointer Operation».
У меня есть вектор объектов, определенных классом, foo, называемый bar.
Я удаляю элементы один за другим, вот так:
for(int i = 0; i < bar.size(); i++){
if(!bar.empty()){
bar.erase(bar.begin());
}
}
Когда я запускаю свою программу, она выполняет только одну итерацию (независимо от ее размера) и останавливается на второй.
В частности, это нарушает функцию STL _Destroy
template<class _TyDtor> inline
void _Destroy(_TyDtor _FARQ *_Ptr)
{ // destroy object at _Ptr
_DESTRUCTOR(_TyDtor, _Ptr);
}
* заметьте, я знаю, что есть четкая функция, которая сделает это более аккуратно, но это всего лишь упрощенный пример чего-то другого, что я пытаюсь сделать
Как всегда при изменении диапазона при обходе диапазона, вы не можете безусловно увеличить счетчик цикла.
Рассмотрим простой пример двухэлементного набора. когда i
является 0
удаляешь первый элемент и увеличиваешь i
, Сейчас i
является 1
а также bar.size()
является 1
и цикл завершается, не удаляя второй элемент.
Стандартное решение состоит в том, чтобы сделать прирост условным не изменение контейнера:
for (int i = 0; i < bar.size(); /* no increment here */) {
if (!bar.empty()) {
bar.erase(bar.begin());
} else {
++i;
}
}
Когда вы изменяете контейнер, стирая элемент, i
остается неизменным, но диапазон перемещается на один элемент ближе к нему. Также увеличивается i
будет двойной счет.
(Это очень распространенная ошибка, хотя обычно она выражается в терминах итераторов, например, Вот или же Вот или же Вот.)
Проблема в условной части цикла bar.size()
который постоянно меняется на каждой итерации, то есть уменьшается в этом примере на 1.
Трудно сказать, чего именно вы пытаетесь достичь в цикле, но если вы хотите выполнить цикл bar-size ()
затем используйте следующую логику:
const size_t vecSize = bar.size ()
for(int i = 0; i < vecSize ; i++)
{ ..... }
В противном случае, если вы хотите выполнить цикл до bar-size ()
пуст, затем используйте while
цикл следующим образом:
while (bar.size > 0)
{ ..... }