我有一个Object的ArrayList,我正在尝试编辑其中一个对象的字段,但是当我这样做时,我收到了ConcurrentModificationException。我已经读过我需要使用Iterator,但即便如此,我仍然收到错误消息。
我的代码:
if(summedEmotionValuesArrayList.size() == 0){
summedEmotionValuesArrayList.add(newEmotionValuesDataset);
}else {
for (Iterator<EmotionValuesDataset> currentEmotionValuesDataset = summedEmotionValuesArrayList.iterator(); currentEmotionValuesDataset.hasNext(); ) {
EmotionValuesDataset emotionValuesDataset = currentEmotionValuesDataset.next();
if (emotionValuesDataset.getEmotionName().equals(newEmotionValuesDataset.getEmotionName())) {
double newValue = emotionValuesDataset.getEmotionValue() + newEmotionValuesDataset.getEmotionValue();
emotionValuesDataset.setEmotion_value(newValue);
} else {
summedEmotionValuesArrayList.add(newEmotionValuesDataset);
}
}
}
此代码在for循环中执行多次。此行发生错误消息
EmotionValuesDataset emotionValuesDataset = currentEmotionValuesDataset.next();
非常感谢任何帮助。
答案 0 :(得分:2)
summedEmotionValuesArrayList.add(newEmotionValuesDataset);
这行产生问题,你应该创建一些其他列表(将其命名为yourTempList)并在那里添加元素,在退出for循环之后只需使用
summedEmotionValuesArrayList.addAll(yourTempList)
答案 1 :(得分:2)
您正尝试将值基本上添加到arraylist summedEmotionValuesArrayList
。如果您研究add
的实施方式,
public void add(E e) {
checkForComodification();
try {
int i = cursor;
ArrayList.this.add(i, e);
cursor = i + 1;
lastRet = -1;
expectedModCount = modCount;
} catch (IndexOutOfBoundsException ex) {
throw new ConcurrentModificationException();
}
}
而且,如果你看一下checkForComodification()
的实现,你可以看到它检查modCount
。
因此,基于此以及https://docs.oracle.com/javase/9/docs/api/java/util/AbstractList.html的文档,您可以看到以下内容。
如果此字段的值意外更改,则为迭代器(或列表) 迭代器)会抛出一个ConcurrentModificationException来响应 下一步,删除,上一步,设置或添加操作。这提供了 失败的行为,而不是面部的非确定性行为 迭代期间的并发修改。
因此,您可以通过创建新的临时列表来解决此问题。这已经得到了解答。无论如何,
ArrayList<EmotionValuesDataset> tempList = new ArrayList();
for(...){
//use your logic, but instead of summedEmotionValuesArrayList.add(newEmotionValuesDataset);
tempList.add(newEmotionValuesDataset);
}
//outside of forloop
summedEmotionValuesArrayList.addAll(tempList)
我希望它有所帮助!
答案 2 :(得分:1)
迭代ArrayList时,迭代器始终将modCount检查为迭代开始时保存的值。此值随每次添加,删除,设置......而变化,如果在迭代期间发生变化,则会抛出ConcurrentModificationException
。
如果要删除当前所在的项目,可以使用Iterator #remove方法,该方法知道更新了expectedModCount。在向ArrayList添加值时,可以将它们保存在临时列表中,然后在迭代结束时将所有这些元素添加到原始列表中。
for(...) {
...
temp.add(newValue);
...
}
summedEmotionValuesArrayList.addAll(temp);