对 STL 容器的哪些操作会使std::insert_iterator
引用该容器的 C++ 无效?insert_iterator
如果它的底层迭代器(受保护iter
的成员)符合通常的迭代器无效规则,那么它是有效的吗?
相关:std::insert_iterator 和 iterator invalidation给出了一个无效insert_iterator
但没有阐明规则的例子。
对 STL 容器的哪些操作会使std::insert_iterator
引用该容器的 C++ 无效?insert_iterator
如果它的底层迭代器(受保护iter
的成员)符合通常的迭代器无效规则,那么它是有效的吗?
相关:std::insert_iterator 和 iterator invalidation给出了一个无效insert_iterator
但没有阐明规则的例子。
当其底层迭代器(受保护的成员 iter)是时, insert_iterator 是否有效,
你是对的,这就是受保护成员在规范中列出的原因,并且在insert_iterator
(特别是operator=
,因为其余部分是无操作的)上工作的函数是根据访问的函数定义的iter
嗯,答案取决于你具体问的是什么。
(为了解决这个问题,我想立即指出您的“相关”链接完全不相关。该链接上的代码问题与失效完全无关。该问题insert_iterator
的作者误解了这个问题最后试图解决一个不存在的问题,而真正的问题仍然存在。我也为这个问题提供了一个额外的答案。)
如果你insert_iterator ins
从一个有效的迭代器创建一个container::iterator it
,然后独立地对容器做一些会使无效的事情it
,那么ins
也会被无效。这是很自然的事情。如果您独立进行,ins
则无法知道容器发生了什么事。
但同时在insert_iterator
用于插入时具有自修复特性。例如,如果您使用insert_iterator ins
将数据插入到 avector
中,ins
即使向量经过重新分配也仍然有效。即,即使向量重新分配是一个大规模的迭代器无效事件,它也不会损坏ins
(当然,假设重新分配是由通过 执行的插入触发的ins
)。
这遵循标准插入算法
it = container->insert(it, value);
++it;
存储在其中it
的底层插入点迭代器在哪里insert_iterator
。前插入和后插入迭代器也具有相同的“自愈”属性。可能无效的内部迭代器会立即重新验证。
为了说明差异,考虑这个简单的例子
std::vector<int> v(10);
std::vector<int>::iterator it = v.begin() + 5;
for (unsigned n = 20; n > 0; --n)
v.insert(it, rand());
此代码通常无效,因为容器很可能会在插入周期中重新分配,从而使it
所有进一步的插入无效并导致无效。
同时这段代码
std::vector<int> v(10);
std::vector<int>::iterator it = v.begin() + 5;
std::insert_iterator<std::vector<int> > it_ins(v, it);
for (unsigned n = 20; n > 0; --n)
*it_ins++ = rand();
无论向量是否重新分配,都保证可以正常工作。