ConcurrentModificationException using Iterator

前端 未结 2 1897
迷失自我
迷失自我 2021-01-27 23:24

I\'m using an iterator to loop over a collection as follows:

Iterator entityItr = entityList.iterator(); 

    while (entityItr.hasNext())
    {
           


        
2条回答
  •  粉色の甜心
    2021-01-28 00:10

    You must be modifying the list either:

    1. inside your iterator in the pollKeyboard method, without using the add or remove methods on the iterator; or
    2. in another thread

    Therefore your exception is the expected behaviour. From the docs, if you have a single thread iterating the list:

    if the list is structurally modified at any time after the iterator is created, in any way except through the iterator's own remove or add methods, the iterator will throw a ConcurrentModificationException

    and if multiple threads uses the list at one time:

    Note that this implementation is not synchronized. If multiple threads access an ArrayList instance concurrently, and at least one of the threads modifies the list structurally, it must be synchronized externally

    Solution:

    If only one thread accesses the list, make sure you use the entityItr.remove or add methods to modify the list.

    For the multi-threaded case you can use Collections.synchronizedList if you do not have a locking object available.

    First store a single central reference to your list as:

    entityList = Collections.synchronizedList(theOriginalArrayList);
    

    And then access it (with all readers and writers) as:

    synchronized (entityList) {
      // Readers might do:
      itr = entityList.iterator();
      while (i.hasNext())
        ... do stuff ...
    }
    

    There are other ways to sync multi-threaded access, including copying the list to an array (inside a sync block) and iterating it for reading, or using a ReadWrite lock. They all depend on your exact requirement.

提交回复
热议问题