我们(all)知道,通过迭代器擦除元素,指针使迭代器无效,例如:
std::map< .. > map_;
std::map< .. >::iterator iter;
// ..
map_.erase( iter ); // this will invalidate `iter`.
但是,怎么样:
map_.erase( map_.begin() );
这样安全吗? map_.begin()
是否是一个有效的迭代器,指向地图的(新)第一个元素?
“测试它”不是解决方案。 子>
答案 0 :(得分:3)
begin()
不是迭代器,但返回迭代器。擦除第一个元素后,begin()
返回另一个(有效)迭代器。
std::map<int, int> m;
m[1] = 2;
m[2] = 3;
m.erase(m.begin()); // <- begin() points to 1:2
std::cout << m.begin()->second; // <- begin() points to 2:3 now
答案 1 :(得分:3)
在cppreference上,我们看到:
所有迭代器(pos,first,last)必须有效且可解除引用, 也就是说,end()迭代器(它是有效的,但不是 dereferencable)不能使用。
这几乎可以回答你的问题。只要begin()
的迭代器返回有效且可解除引用,就可以在std::map::erase()
中使用它。检查begin()
是否可以在std::map::erase
中使用的好方法是检查它是否等于end()
:
if(map.begin() != map.end()) {
map.erase(map.begin());
}
或者,您也可以检查地图是否为空,如果不是,则使用std::map::erase
if(!map.empty()) {
map.erase(map.begin());
}
答案 2 :(得分:2)
答案 3 :(得分:1)
这样安全吗?
是。它使这个对begin()
的调用返回的临时迭代器无效,并且在语句结束时销毁了迭代器。
map_.begin()
是否是一个有效的迭代器,指向地图的(新)第一个元素?
是的,除非地图现在为空。擦除元素不会阻止您为其余元素创建新的迭代器;这将使地图无法使用。