迭代时出现Java“ConcurrentModificationException”运行时错误.next()

根据运行时错误消息,exception发生在以下行中;

VirusData v = iteratorVirusDB.next(); 

VirusData是一个带有构造函数和重载构造函数的类,其中包含有关数据库中每种病毒的特定信息,例如;

  • 字符串vName
  • 字符串vDefinition

重载

  • 具有标记化定义的数组(以xLength分组分隔)
  • 带LCS令牌的数组
  • 漂浮等级

类型 iteratorVirusDB的.iterator(),如下所示:

 Iterator iteratorVirusDB = virusDB.iterator(); 

VirusDB是和类型的ArrayList,我存储病毒对象(此时名称和def),以便我以后可以使用它们。

 ArrayList  virusDB = new ArrayList(); 

最后,在使用上述所有解释的方法中发生错误:

 private void selectDabataseMouseClicked(java.awt.event.MouseEvent evt) { while(iteratorVirusDB.hasNext()) { VirusData v = iteratorVirusDB.next(); //ERROR LINE String vSig = v.signature; v.tokens = tokenize.raw(vSig, true, tLength); ... } ... } 

我可以真正做一些帮助和建议,如何解决这个问题,以使程序成功运行。 Bellow,完整的StackTrace:

 run: Exception in thread "AWT-EventQueue-0" java.util.ConcurrentModificationException at java.util.AbstractList$Itr.checkForComodification(AbstractList.java:372) at java.util.AbstractList$Itr.next(AbstractList.java:343) at project_clean.Main.selectDabataseMouseClicked(Main.java:275) at project_clean.Main.access$100(Main.java:11) at project_clean.Main$2.mouseClicked(Main.java:76) at java.awt.AWTEventMulticaster.mouseClicked(AWTEventMulticaster.java:253) at java.awt.Component.processMouseEvent(Component.java:6270) at javax.swing.JComponent.processMouseEvent(JComponent.java:3267) at java.awt.Component.processEvent(Component.java:6032) at java.awt.Container.processEvent(Container.java:2041) at java.awt.Component.dispatchEventImpl(Component.java:4630) at java.awt.Container.dispatchEventImpl(Container.java:2099) at java.awt.Component.dispatchEvent(Component.java:4460) at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4577) at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4247) at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4168) at java.awt.Container.dispatchEventImpl(Container.java:2085) at java.awt.Window.dispatchEventImpl(Window.java:2478) at java.awt.Component.dispatchEvent(Component.java:4460) at java.awt.EventQueue.dispatchEvent(EventQueue.java:599) at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:269) at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:184) at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:174) at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:169) at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:161) at java.awt.EventDispatchThread.run(EventDispatchThread.java:122) 

显而易见的解释是您在virusDB调用之间修改了virusDB 。 在使用迭代器进行迭代时,不得修改向量(通过Iterator / ListIterator方法除外)。

这段代码将始终抛出ConcurrentModificationException

 import java.util.*; class VirusData { } public class Test { public static void main(String[] args) { List list = new ArrayList() {{ add(new VirusData()); add(new VirusData()); add(new VirusData()); }}; Iterator iterator = list.iterator(); iterator.next(); list.remove(0); VirusData s = iterator.next(); } } 

ConcurrentModificationException的文档:

例如,一个线程通常不允许修改Collection,而另一个线程正在迭代它。 通常,在这些情况下,迭代的结果是不确定的。 如果检测到此行为,某些Iterator实现(包括JRE提供的所有通用集合实现的实现)可能会选择抛出此exception。 执行此操作的迭代器称为故障快速迭代器,因为它们快速且干净地失败,而不是在未来的未确定时间冒着任意的,非确定性行为的风险。

请注意,此exception并不总是表示某个对象已被另一个线程同时修改。 如果单个线程发出违反对象合同的一系列方法调用,则该对象可能会抛出此exception。 例如,如果线程在使用失败快速迭代器迭代集合时直接修改集合,则迭代器将抛出此exception。

如果您打算每次调用该方法时遍历整个数据库,我建议您这样做

 private void selectDabataseMouseClicked(java.awt.event.MouseEvent evt) { Iterator iteratorVirusDB = virusDB.iterator(); while(iteratorVirusDB.hasNext()) { VirusData v = iteratorVirusDB.next(); String vSig = v.signature; 

当您在同时迭代它时修改它时会发生并发修改exception。 因此,如果要修改列表,请检查代码,并在迭代时发生。