迭代时从 std::list 中删除
Removing from std::list while iterating
我有以下代码:
bool resetTypeBit = true;
for (auto it = eventsList.begin(); it != eventsList.end(); ++it) {
CreatureEvent* curEvent = *it;
if (curEvent == event) {
it = eventsList.erase(it);
} else if (curEvent->getEventType() == type) {
resetTypeBit = false;
}
}
所以我有以下场景:eventList
包含 01 项,然后,一旦 for
语句第一次通过并满足it = eventsList.erase(it);
行,it
变量就变得无效,导致 for
语句的下一次迭代出现分段错误。
任何可能导致问题的原因的线索?
如果删除的项目是列表中的最后一项,则 erase
方法将返回 end()
。然后,您的for
循环将尝试增加该迭代器,这会导致未定义的行为。
您尚未遇到的另一个问题是,如果您删除的项目不是列表中的最后一项,您最终将跳过以下项(因为迭代器递增到erase
返回的项(。您可以将erase
视为一个增量操作,它恰好首先擦除项目。
解决方案是稍微重构循环,将增量移动到末尾(并且仅在未调用erase
的情况下(:
bool resetTypeBit = true;
for (auto it = eventsList.begin(); it != eventsList.end(); ) {
CreatureEvent* curEvent = *it;
if (curEvent == event) {
it = eventsList.erase(it);
}
else {
if (curEvent->getEventType() == type) {
resetTypeBit = false;
}
++it; // move the increment to here
}
}
正如现在所写的那样,即使在erase
分支中,您也会递增迭代器,这意味着您总是在擦除元素之后跳过该元素。这既不正确,如果最后一个元素恰好是要删除的元素,则会导致严重问题。要修复,如果您已经通过将it
设置为已删除元素后面的元素来修复则不必递增。
bool resetTypeBit = true;
for (auto it = eventsList.begin(); it != eventsList.end(); ) {
CreatureEvent* curEvent = *it;
if (curEvent == event) {
it = eventsList.erase(it);
continue;
} else if (curEvent->getEventType() == type) {
resetTypeBit = false;
}
++it;
}
相关文章:
- 从嵌套循环中的 std::list 中删除将返回访问冲突
- 使用容器中元素的别名删除带有 std::list::remove 的元素是否正确?
- 如何通过存储在 std::list 中的指针删除对象?
- 通过引用从 std::list 中删除元素
- 为什么具有 list<struct type>::itrator 的 struct 不能通过 clear() 删除?
- 将 std::list<std::unique_ptr> 移动到向量中会尝试引用已删除的函数
- 如何从 std::list 中删除元素?
- 从 std::list 中删除 std::tuple
- std::list - 删除元素
- 在迭代器时从 std::list 中删除条目
- 在C++中有条件地删除Singly Linked List中的元素
- 从 std::list 中删除对象
- 不应该像这样从 stl::list 中删除进入无限循环
- std::list remove_if删除节点
- 有效地从 std::list 中删除最后一个元素
- (C++) list.error 方法和使用指针删除内存
- std::list.remove 正在调用析构函数,但不删除它
- 迭代时从 std::list 中删除
- 如何正确删除 std::list 中的指针
- 正在从Singly Linked Circular List中删除特定节点