簡體   English   中英

防止Java中出現偶發的ConcurrentModificationException的最佳實踐是什么?

[英]What is the best practice to prevent a sporadic ConcurrentModificationException in Java?

哪個用於迭代列表或映射的代碼序列可以防止ConcurrentModificationException? 我們的代碼中反復出現零星的ConcurrentModificationException。 有兩個原因導致此問題。

  1. 另一個線程在迭代時更改列表
  2. 循環中調用的方法正在更改列表。

問題1可以通過環回同步來解決。 但是,如果像原因2那樣在循環中調用外來代碼,這將是很糟糕的。

問題2可以通過列表或地圖的副本來解決。

這意味着列表或映射必須在循環之前在同步塊中復制。 有更好的解決方案嗎?

一些示例代碼:

public void todoSomeThings( Map<Abc, Object> map ){
    for( Abc abc : map.keySet() ){
        abc.todoSomeThings();
    }
}

您是否考慮過在java.util.concurrent使用並發集合? 老實說,很難提供比這更好的建議了……我們需要更多細節。

需要注意的一點是,如果您在線程之間共享了可變集合,並且可變集合暴露於大量代碼中,以至於您不知道在迭代時可能對其進行了變異,那么您可能需要考慮盡可能更改設計。 不可變的集合通常可以使事物保持整潔,有時(但不總是)以犧牲性能為代價。 從一開始它們可能比較難使用,但是您可能會發現以后對代碼進行推理更容易。

一個公平的警告:使用juc(java.util.concurrent)將消除錯誤,但您將遇到可能更糟的情況,例如,種族更新,陳舊的讀取等。最佳實踐是

了解您的數據結構,使用狀態...或至少(不是最好)使用鎖。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM