2012-11-23 16 views
1

可能重複:
java.util.ConcurrentModificationException on ArrayList的Java併發修改例外,從列表中刪除項目時

我試圖從一個線程內部列表中刪除項目。我得到ConcurrentModificationException。我從這link讀取它與刪除列表中的項目有關。我在下面放置示例代碼。我如何在沒有這種例外的情況下正確地做到這一點。

try 
{ 
    for(Game game:appDeleg.getGlobalGames().getGames()) 
    { 
     if(game.getOwner().getId().equals(params[0])) 
     { 
      synchronized (appDeleg.getGlobalGames().getGames()) 
      { 
       appDeleg.getGlobalGames().getGames().remove(game); 
      } 
     } 

    } 
} 

catch (Exception e) 
{ 
    e.printStackTrace(); 
    return "noconnection"; 
} 

回答

5

使用迭代:

Iterator<Game> i = appDeleg.getGlobalGames().getGames().iterator(); 

Game game; 
while(i.hasNext()) { 
    game = i.next(); 
    if(game.getOwner().getId().equals(params[0])) 
      i.remove(); 
    } 
} 
+0

我認爲你必須使用'Iterator 我= appDeleg.getGlobalGames()。getGames()。iterator();'得到迭代器 – Patton

+0

正確的,是急於得到一個投票:) –

1

將要刪除的項目收集到一個新列表中,並在通過原始列表後將其刪除。

+0

或從迭代器中刪除項目本身而不是收集。 –

+0

這兩個有效的解決方案 – WarrenFaith

1

synchornized關鍵字不會保護你在這裏。
您可以通過單線程應用程序訪問此異常事件(是的 - 您可能聲稱異常的名稱是誤導性的)。
這應該使用迭代器遍歷列表,
(這將允許您在達到要刪除的值時調用remove),
或將要刪除的元素收集到單獨的列表中,然後在其上運行removeAll方法。

1

在迭代無法刪除列表中的項目,它拋出ConcurrentModificationException

如果列表在任何時間以任何方式從結構上修改創建迭代器之後, 除非通過迭代器自身的remove或添加方法,迭代器 將引發ConcurrentModificationException。因此,面對併發的修改,迭代器快速而乾淨地失敗,而不是在將來某個未確定的時間冒任意的,不確定的行爲。

文檔 - >link

您應Iterator從列表中刪除項。

1

增強循環使用的迭代器。迭代器可以拋出一個異常,如果某個東西在迭代它時修改了集合。

在你的情況下,你是通過集合刪除項目,而不是通過迭代器。

嘗試使用循環的標準並且不使用隱含的迭代器。 假設你的集合是一個數組列表。

ArrayList games = appDeleg.getGlobalGames().getGames(); 
for(int i=0;i<games.size();i++){ 
     Game game = games.get(i); 
     if(game.getOwner().getId().equals(params[0])){ 
     games.remove(i); 

     } 
}