千萬要小心STL的iterator失效[難度:初級]

來源:互聯網
上載者:User

 iterator中文經常被譯為“泛型指標”,在實際的使用中卻需要比指標更加小心翼翼。如果沒有注意到iterator失效,那麼產生的錯誤可能比普通指標更隱蔽,當然也可能會引起一般的程式異常。iterator失效主要有兩種情況:
 1、iterator變數已經變成了“懸null 指標”,對它進行*,++,--都會引起程式記憶體操作異常;
 2、iterator所指向的變數已經不是你所以為的那個變數了。
 所以在使用iterator是必須要時刻牢記“容器的插入和刪除元素”可能引起iterator失效!普遍遇到的幾個問題:

 1、剛剛使用STL的很多人會為這個問題困擾:在迴圈遍曆一個容器時,需要根據條件刪除其中的某個元素,如何處理iterator?答案是:對於序列式容器標準寫法是這樣:
 //vector<int> con;
 for(vector<int>::iterator iter=con.begin();
  iter!=con.end();)
 {
  if((*iter) == 99)
   iter=con.erase(iter);
  else
   ++iter;
 }
 對於關聯容器是這樣:
 //map<int,int> con;
 for(map<int,int>::iterator iter=con.begin();
  iter!=con.end();)
 {
  if(iter->second == 99)
   con.erase(iter++);
  else
   ++iter;
 }

 2、使用一個iterator變數時往往是危機重重,我在剛開始使用STL的時候,就範了一個較難測試出來的錯誤,類似這樣:
 int DoSomething(vector<int>& con)
 {
  vector<int>::iterator iter = find(con.begin(),con.end(),99);

  ... ...//做了一些insert操作

  return *iter;//如果vector的記憶體沒有重新分配,那麼*操作會成功,但是已經不保證是99了!
 }
 
 3、下面這個錯誤則要更隱蔽一些、在大一些的類庫中更難以控制:
 有一個介面系統,一個window類,用來封裝自身的操作、繪圖功能,並管理它的所有子視窗:
 class Window
 {
  Window*  m_pParent;
  list<Window*> m_children;
 public:
  void RemoveChild(Window *pChild)
  {
   m_children.remove(pChild);
  }
  virtual void Update()
  {
   for(list<Window*>::iter=m_children.begin();
    iter=m_children.end();++iter)
   {
    (*iter)->Update();
   }//endof for
  }
 };
 
 這個Window::Update()函數負責處理視窗邏輯,結果在某個視窗的Update寫成了這樣:
 class MyDlg : public Window
 {
 public:
  virtual void Update()
  {
   if(m_bClosed)
    m_pParent->RemoveChild(this);
   else
    Window::Update();
  }
 };
 當一個模組的邏輯比上述例子複雜很多時,這種情況更難以掌握,為了防止模組客戶的代碼產生類似的行為,我不得不把代碼寫成這樣:
 class Window
 {
  Window*  m_pParent;
  list<Window*> m_children;
  bool  m_bLock;
 public:
  void RemoveChild(Window *pChild)
  {
   ASSERT(!m_bLock);
   m_children.remove(pChild);
  }
  virtual void Update()
  {
   m_bLock=true;
   for(list<Window*>::iter=m_children.begin();
    iter=m_children.end();++iter)
   {
    (*iter)->Update();
   }//endof for
   m_bLock=false;
  }
 };

參考資料:
 《C++標準程式庫》,候捷、孟岩譯,2002

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.