關於STL的list,vector等用迭代器iterator,用erase刪除元素出現的問題。

做個測試,隨便搞個類,頭文件加入

#include <vector>
#include <list>
using namespace std;

typedef std::vector<CString> CStringVector;

 

 

然後在一個可執行到的方法中加入如下代碼:

CStringVector vctCString;
vctCString.push_back(_T("1111"));
vctCString.push_back(_T("2222"));
vctCString.push_back(_T("3333"));
vctCString.push_back(_T("4444"));
vctCString.push_back(_T("5555"));


CStringVector::iterator it = vctCString.begin();
for (; it != vctCString.end(); it++)
{
    CString strTemp = *it;
    if (strTemp == _T("1111"))
    {
        vctCString.erase(it);
    }
}

很明顯,當erase那個it後,再執行it++就會失敗,這是最常見的問題,erase之後會導致it失效,怎麼解決呢?

erase的返回值是下一個元素的位置,讓這個值重新付給it就行了。但是粗心的人會這麼寫:

CStringVector vctCString;
vctCString.push_back(_T("1111"));
vctCString.push_back(_T("1111"));
vctCString.push_back(_T("3333"));
vctCString.push_back(_T("4444"));
vctCString.push_back(_T("5555"));


CStringVector::iterator it = vctCString.begin();
for (; it != vctCString.end(); it++)
{
    CString strTemp = *it;
    if (strTemp == _T("1111"))
    {
        CStringVector::iterator itTemp = vctCString.erase(it);
        it = itTemp;
    }
}
這麼寫對嗎?也不對,但不會崩潰,也就是解決了前面的問題,但是帶來了新的問題,這樣寫的話會導致這個for循環少循環一次,也就少判斷了一次,哪一次呢?就是if成立後的下一個元素,沒有判斷到,原因就不用說了吧。

最正確的寫法是:

CStringVector vctCString;
vctCString.push_back(_T("1111"));
vctCString.push_back(_T("1111"));
vctCString.push_back(_T("3333"));
vctCString.push_back(_T("4444"));
vctCString.push_back(_T("5555"));


CStringVector::iterator it = vctCString.begin();
for (; it != vctCString.end(); )
{
    CString strTemp = *it;
    if (strTemp == _T("1111"))
    {
        CStringVector::iterator itTemp = vctCString.erase(it);
       it = itTemp;
    }
    else
    {
        it++;
    }
}

什麼意思?for小括號裏的it++不寫了,放到裏面來,這樣當if有效的時候,其實已經是it++過了,所以這種情況不需要小括號內再++了,再++就加多了,當if無效的時候正常執行else的it++。明白了不?不明白給我發郵件吧。[email protected]


 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章