问题
map删除元素时,报错java.util.ConcurrentModificationException
源码
public void remove() {
if (lastRet == -1)
throw new IllegalStateException();
checkForComodification();
try {
AbstractList.this.remove(lastRet);
if (lastRet < cursor)
cursor--;
lastRet = -1;
expectedModCount = modCount;
} catch (IndexOutOfBoundsException e) {
throw new ConcurrentModificationException();
}
}
final void checkForComodification() {
if (modCount != expectedModCount)
throw new ConcurrentModificationException();
}
原因
modCount
,每次对集合进行修改(增添 / 删除……)时都会modCount++。
expectedModCount
,对ArrayList修改次数的预期的数值,初始化与modCount
相等。但如果接下来如果集合进行修改modCount
改变,就会造成expectedModCount!=modCount
,此时就会抛出java.util.ConcurrentModificationException异常。
这样设计主要是为了防止多线程问题。
解决
使用iterator进行删除
Iterator<String> iterator = oneMap.keySet().iterator();
while(iterator.hasNext()){
String str = iterator.next();
if( str.equals("相同的字符串") )
{
iter.remove();
}
}
加锁
迭代前加锁
使用线程安全的数据结构
- ConcurrentHashMap
- CopyOnWriteArrayList
- ...
参考