問題描述
我有一個 std::vector m_vPaths;我將迭代這個向量并隨時調用 ::DeleteFile(strPath) .如果我成功刪除了文件,我會將其從向量中刪除.我的問題是我可以避免使用兩個向量嗎?是否有不同的數據結構可能更適合我需要做的事情?
I have a std::vector m_vPaths; I will iterate this vector and call ::DeleteFile(strPath) as I go. If I successfully delete the file, I will remove it from the vector. My question is can I get around having to use two vectors? Is there different data structure that might be better suited for what I need to do?
示例:使用迭代器幾乎可以滿足我的要求,但問題是一旦使用迭代器擦除,所有迭代器都將無效.
example: using iterators almost does what I want, but problem is once you erase using an iterator, all iterators become invalid.
std::vector<std::string> iter = m_vPaths.begin();
for( ; iter != m_vPaths.end(); iter++) {
std::string strPath = *iter;
if(::DeleteFile(strPath.c_str())) {
m_vPaths.erase(iter);
//Now my interators are invalid because I used erase,
//but I want to continue deleteing the files remaining in my vector.
}
}
我可以使用兩個向量并且不再有問題,但是有沒有更好、更有效的方法來做我想做的事情?
I can use two vectors and I will no longer have a problem, but is there a better, more efficient method of doing what I'm trying to do?
順便說一句,如果不清楚,m_vPaths 是這樣聲明的(在我的班級中):
btw, incase it is unclear, m_vPaths is declared like this (in my class):
std::vector<std::string> m_vPaths;
推薦答案
查看 std::remove_if
:
#include <algorithm> // for remove_if
#include <functional> // for unary_function
struct delete_file : public std::unary_function<const std::string&, bool>
{
bool operator()(const std::string& strPath) const
{
return ::DeleteFile(strPath.c_str());
}
}
m_vPaths.erase(std::remove_if(m_vPaths.begin(), m_vPaths.end(), delete_file()),
m_vPaths.end());
使用 std::list
停止無效迭代器問題,盡管您失去了隨機訪問.(和緩存性能,一般)
Use a std::list
to stop the invalid iterators problem, though you lose random access. (And cache performance, in general)
為了記錄,您實現代碼的方式是:
For the record, the way you would implement your code would be:
typedef std::vector<std::string> string_vector;
typedef std::vector<std::string>::iterator string_vector_iterator;
string_vector_iterator iter = m_vPaths.begin();
while (iter != m_vPaths.end())
{
if(::DeleteFile(iter->c_str()))
{
// erase returns the new iterator
iter = m_vPaths.erase(iter);
}
else
{
++iter;
}
}
但是你應該使用 std::remove_if
(重新發明輪子不好).
But you should use std::remove_if
(reinventing the wheel is bad).
這篇關于迭代向量,邊走邊刪除某些項目的文章就介紹到這了,希望我們推薦的答案對大家有所幫助,也希望大家多多支持html5模板網!