2

私のアプリケーションでは、Map を使用して POJO オブジェクトを格納しました。要件に従って、マップのキーセットを反復処理し、変更を必要としないオブジェクトを削除する必要があります。

以下のコードを検討してください。

 public void remove(Map<String,User> removeUser){
  Set<String> keySet = removeUser.keySey();
  User user = null;

  for(String key : keySet){
      user = (user) removeUser.get(key);

       if(!user.isActive()){
                removeUser.remove(key);
       }
  }

 }

上記のコードでは、オブジェクトの削除後にユーザー オブジェクトを取得しようとすると、ConcurrentModificationException が発生します。

なぜそれが起こっているのか誰か教えてもらえますか?

私はマルチスレッドを使用していないため、ConCurrentModification Exception が生成された場所から理解できません。

HashMap と Hashtable を試してみましたが、問題はまだあります。

4

3 に答える 3

10

ConCurrentModification Exception を生成した場所から。

Mapそれは、要素を繰り返し処理しながら要素を削除しようとしている行から来ましたKeySet

if(!user.isActive()){
     removeUser.remove(key);  // This is the problem
}

あなたはそれをすべきではありません。Collectionまたはを変更する場合Mapは、 を使用しiteratorます。


この非常に素晴らしい投稿を参照してください-あなたが反復するコレクションを変更する際に発生する可能性のある問題を説明している効率的な同等の要素を削除するための要素-while-iterating-the-collection 。


ここでの使用方法を説明する簡単なコードを次に示します。

    Map<String, Integer> map = new HashMap<String, Integer>() {
        {
            put("a", 1);
            put("b", 2);
            put("c", 3);
        }
    };

    Iterator<String> iterate = map.keySet().iterator();

    while  (iterate.hasNext()) {
        int i = map.get(iterate.next());

        if(i > 1) {
            iterate.remove();
        }
    }

    System.out.println(map);

出力: -

{a=1}
于 2012-11-19T11:53:11.670 に答える
4

ConcurrentHashMap を使用すると、ConcurrentModificationException は生成されません。

より一般的な解決策は、Iterator を使用して remove() を実行することです。

public void removeInactiveUsers(Map<String, User> map) {
    for (Iterator<User> iter = map.values().iterator(); iter.hasNext(); ) 
        if (!user.isActive())
            iter.remove();
}

keySet()注:のみに関心があるため、 は必要ありません。values()

于 2012-11-19T11:56:38.553 に答える
2

反復子を使用してSetを反復処理し、を使用すると、反復処理中にコレクションから要素を削除するiterator.remove()ことはできません。ConcurrentModification Exceptionが発生します。

あなたの例外の根本的な原因はここにあります:

        removeUser.remove(key);

イテレータを使用して、このようにセットを反復処理します。

Iterator<String> itr = keySet .iterator();
while(itr.hasNext){
   String s = itr.next();
   itr.remove(); // to remove the current element.
 }
于 2012-11-19T11:53:53.960 に答える