我有一个填充了对象的向量:
std::vector<Stuff*> stuffVector;
我正在尝试使用清理功能删除它的所有元素
void CleanUp()
{
for (std::vector<Stuff*>::size_type i = 0 ; i < stuffVector.size() ; i++)
{
stuffVector.erase(stuffVector.begin()+i);
}
cout << stuffVector.size() << endl;
if (stuffVector.size() == 0) cout << "Vector Emptied" << endl;
}
这总是向量报告,但是矢量中有很多对象的大小,实际上似乎根本没有删除任何东西。这很奇怪,因为类似的函数在别处可以从向量中删除特定对象:
void DestroyStuff()
{
if (stuffVector.size() > 1)
{
for (std::vector<Stuff*>::size_type i = 0 ; i < stuffVector.size() ; i++ )
{
if(stuffVector[i]->CanDestroy())
{
stuffVector.erase (stuffVector.begin()+i);
}
}
}
}
以上工作正常,但CleanUp()没有。为什么会发生这种情况?
答案 0 :(得分:2)
擦除元素时,矢量的大小会发生变化。因此,在erase()
和i++
的某些迭代中,您的循环正在跳过元素。
此外,要删除vector
clear()
函数的每个元素,都很有用。此外,循环遍历向量中所有元素的标准方法是使用迭代器。您的代码应如下所示:
void CleanUp()
{
for (std::vector<Stuff*>::iterator it = stuffVector.begin() ; it != stuffVector.end() ; it++)
{
/* .. do something to each element to prepare it for removal */
delete *it; // clean up resources?
}
stuffVector.clear();
cout << stuffVector.size() << endl;
if (stuffVector.size() == 0) cout << "Vector Emptied" << endl;
}
和
void DestroyStuff()
{
for (std::vector<Stuff*>::iterator it = stuffVector.begin() ; it != stuffVector.end() ; /*done inline*/)
{
if((*it)->CanDestroy())
{
it = stuffVector.erase(it);
}
else
++it;
}
}
这个循环有效,因为erase()
将迭代器返回到列表中的下一个元素。
答案 1 :(得分:1)
stuffvector.clear();
(min.length bah!)
答案 2 :(得分:0)
这是错误的:
for (std::vector<Stuff*>::size_type i = 0 ; i < stuffVector.size() ; i++)
{
stuffVector.erase(stuffVector.begin()+i);
}
想象一下,向量中包含元素0, 1, 2, 3, 4
。在第一次擦除(i==0
)之后,它将是1, 2, 3, 4
。使用i==1
进行的第二次删除会将其呈现为1, 3, 4
,最后,它将最终为1, 3
。
清除矢量的最佳选择是
stuffVector.clear()
,如果这不合适:
stuffVector.swap(std::vector<Stuff*>());
或
while(!stuffVector.empty()) stuffVector.pop_back();
或
stuffVector.erase(stuffVector.begin(), stuffVector.end());
删除矢量内容的其他方法留给读者练习:)
如果你想在清除它们之前用元素做其他事情(...就像删除指针指向的对象一样)我建议单独执行此操作,然后将矢量清除为单独的操作。或者使用空向量进行交换,并使用交换的向量执行任何操作。
答案 3 :(得分:0)
您的CleanUp()问题是vector :: erase()不会调用delete来释放指针或对象析构函数。它只会丢弃指针并泄漏内存。
答案 4 :(得分:0)
在itertaor上调用erase将使迭代器无效
stuffVector.erase(stuffVector.begin()+i);
后面跟着for循环
i++
删除后的指针甚至可能无法读取或复制。销毁使迭代器无效 以下可能会有所帮助
for(it = Entities.begin(); it != Entities.end();)
{
if(...) //Conditional deletion
{
delete * it;
it = Entities.erase(it);
}
else
{
it++;
}
}