为什么允许擦除vector.end()
Why erasing vector.end() is allowed?
今天我做了一些代码,看起来像这样:
vec.erase(std::remove_if(vec.begin(), vec.end(), <lambda here>));
当上面的代码不应该擦除任何东西时,也就是说std::remove_if应该返回vec.end(),当我收到我的向量时,我非常惊讶,它的大小减少了一:最后一个元素被擦除了。通过将上面的更改为:解决了问题
vec.erase(std::remove_if(vec.begin(), vec.end(), <lambda here>), vec.end());
但问题仍然存在:如何
vec.erase(vec.end());
做什么工作?这不应该是不明确的行为吗?
编辑:显然,我从一开始就对训练不足行为的理解是错误的,我一直观察到的是UB。谢谢大家回答我的问题。
它是未定义的行为。特别是,这意味着你可能会看到尺寸减少了一个
有关UB 的更多信息
为什么允许擦除vector.end()?
这是不允许的。vector::erase(const_iterator)
的参数必须是向量中的有效可取消引用的迭代器。过去的结束迭代器是有效的,但不能取消引用。
[…]怎么能做任何工作?这不应该是不明确的行为吗?
为什么你认为它不能起作用,是不明确的行为?
你认为不明确的行为意味着什么?
首先,它不是
vec.erase(std::remove_if(<lambda here>), vec.end());
它真的是
vec.erase(std::remove_if(vec.begin(), vec.end(), <lambda here>), vec.end());
这与完全不同
vec.erase(vec.end());
后者,vec.erase(vec.end())
,当然是未定义的行为。前者不是。
std::remove_if(vec.begin(), vec.end(), <lambda here>)
这将删除向量中与lambda匹配的值,最重要的是,这将返回新序列的结束值。
vec.erase(first, last);
这将删除向量中从first
迭代器值开始的值,以及直到但不包括last
迭代器的值。
将两者放在一起,就可以从向量中删除匹配的值,然后相应地缩小向量。
相关文章:
- 如何使用vector.begin()和vector.end()遍历矩阵?
- 在不使用vector.end()的情况下迭代std::vector
- 在实现 std::vector 时,我必须拥有 end() 的"end"指针吗?
- C# 等效于 C++ std::<int>vector.end()
- vector.back()和vector.end()有什么区别
- 标准::复制失败,"cannot seek vector iterator after end"
- 为什么我允许我为std :: vector设置end()
- Segfault from Vector.end()?
- 使用end()--迭代到std::vector的最后一个元素
- Empty std::vector begin != end
- 如何为std::vector设置有效的.begin()和.end()而不使用.resize()
- 查找语句中的"!=vector.end()"是什么意思?
- C++ vector.end() 给出超出范围的结果 - 请告知
- 如何使用 vector.begin() 将向量的向量打印到 vector.end()
- 使用 std::vector 作为 std::map 的键在未找到和使用 reserve() 时不会返回 end()
- C ++擦除std::vector.end(),同时循环遍历所有迭代器
- 将 vector's end() 传递给 std::vector::erase 有效吗?
- 为什么允许擦除vector.end()
- 为什么编译器在C++中允许vector.begin()=vector.end()
- 向量迭代器 > vector.end() 即使向量不应该被重新分配