如何修复此错误 java.util.ConcurrentModificationException
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/11407621/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How can I fix this error java.util.ConcurrentModificationException
提问by aliplane
I get an error on the following line. I'm doing the process of adding to the jsonarray. Please help me.
我在以下行中收到错误消息。我正在做添加到 jsonarray 的过程。请帮我。
jsonArr=new JSONArray();
if(req.getSession().getAttribute("userses")!=null){
String name=(req.getParameter("name")==null?"":to_EnglishName(req.getParameter("name").toUpperCase()));
if(!name.equals("")){
for(Book c:GlobalObjects.bookList){
if(c.getBookName().startsWith(name)){
jsonObjec=new JSONObject();
jsonObjec.put("label",c.getBookName());
jsonObjec.put("value", c.getId());
jsonArr.add(jsonObjec);//java.util.ConcurrentModificationException
}
}
}
}
jsonArr.write(res.getWriter());
回答by C.c
This is an error I often met while reprogramming. the reason or detail of this exception are pretty clear. it is unallowed to modify the collection(you are adding a new element) while it is being iterated. At least the syntax for
DO NOT support do that.
这是我在重新编程时经常遇到的错误。此异常的原因或细节非常清楚。不允许在迭代时修改集合(您正在添加新元素)。至少语法for
不支持这样做。
To fix your problem, there have two way I think it is simple.
要解决您的问题,我认为有两种方法很简单。
1). rather than using for
statement to loop over, the better way is to use iterator to avoid ConcurrentModificationException.
1)。与使用for
语句循环相比,更好的方法是使用迭代器来避免 ConcurrentModificationException。
Iterator<Book> iterator = bookList.iterator();
while(iterator.hasNext()){
Book c = iterator.next();
if(c.getBookName().startsWith(name)){
jsonObjec=new JSONObject();
jsonObjec.put("label",c.getBookName());
jsonObjec.put("value", c.getId());
jsonArr.add(jsonObjec);
}
}
2). while looping it, don't add it.
2)。循环时,不要添加它。
List list = new ArrayList<>();
for(Book c:GlobalObjects.bookList){
if(c.getBookName().startsWith(name)){
jsonObjec=new JSONObject();
jsonObjec.put("label",c.getBookName());
jsonObjec.put("value", c.getId());
list.add(jsonObjec);//java.util.ConcurrentModificationException
}
}
jsonArr.addAll(list);
回答by Pramod Kumar
To fix this problem, make sure that If your collection is not thread safe then it must not get modified with another thread when some other thread is iterating over this collection
.
要解决此问题,请确保If your collection is not thread safe then it must not get modified with another thread when some other thread is iterating over this collection
.
There are two possible ways to fix this problem -
有两种可能的方法可以解决此问题 -
1) One solution is to synchronize all access to the collection
1)一种解决方案是同步所有对集合的访问
2) Use Thread safe collection like CopyOnWriteArrayList
2)使用线程安全集合,如 CopyOnWriteArrayList
From Java Doc -
来自 Java 文档 -
This exception may be thrown by methods that have detected concurrent modification of an object when such modification is not permissible.
For example, it is not generally permssible for one thread to modify a Collection while another thread is iterating over it. In general, the results of the iteration are undefined under these circumstances. Some Iterator implementations (including those of all the collection implementations provided by the JRE) may choose to throw this exception if this behavior is detected. Iterators that do this are known as fail-fast iterators, as they fail quickly and cleanly, rather that risking arbitrary, non-deterministic behavior at an undetermined time in the future.
当不允许此类修改时,检测到对象的并发修改的方法可能会抛出此异常。
例如,通常不允许一个线程修改一个集合,而另一个线程正在对其进行迭代。通常,在这些情况下迭代的结果是不确定的。如果检测到此行为,某些 Iterator 实现(包括 JRE 提供的所有集合实现的实现)可能会选择抛出此异常。这样做的迭代器被称为快速失败迭代器,因为它们快速而干净地失败,而不是冒着在未来不确定的时间出现任意、非确定性行为的风险。
回答by devang
You get ConcurrentModificationException when you are iterating over a collection and you modify the same collection within the loop. The given code snippet does not show that, so there is something else above or below modifying the collection. Try declaring the jsonArr right at the place where you instantiate it.
当您迭代一个集合并在循环中修改同一个集合时,您会得到 ConcurrentModificationException。给定的代码片段没有显示这一点,因此在修改集合的上方或下方还有其他内容。尝试在实例化它的地方声明 jsonArr 。
One possible reason could be the jsonArr instance Object is class level and is accessed by multiple threads. Declare the jsonArr object where it is instantiated.
一个可能的原因可能是 jsonArr 实例对象是类级别的并且由多个线程访问。在实例化的地方声明 jsonArr 对象。
Edit: Make jsonArr a local variable.
编辑:使 jsonArr 成为局部变量。
回答by Adarsh Gowda
Also one more way is there, ie insted of passing actual list , we can pass clone of list for iteration.
还有另一种方法,即不传递实际列表,我们可以传递列表的克隆进行迭代。
listForIteration = list.clone();
listForIteration = list.clone();
//Do operation..
//做操作..
回答by Mojtabye
just use java.util.concurrent.CopyOnWriteArrayList
只是使用 java.util.concurrent.CopyOnWriteArrayList
List<String> empList = new CopyOnWriteArrayList<>();
empList.add("Mojtaba");
empList.add("Mojtabye");
empList.add("Yeganeh");
for (String item : empList) {
System.out.println(item);
empList.add("test");
}
回答by Martin
Or use a ListIterator which allows iterating and modifying the same list
或者使用允许迭代和修改相同列表的 ListIterator
http://docs.oracle.com/javase/6/docs/api/java/util/ListIterator.html
http://docs.oracle.com/javase/6/docs/api/java/util/ListIterator.html
回答by 18bytes
Are you accessing jsonArr from another thread? i.e. Iterating over jsonArr when you are modifying it at the same time.
你是从另一个线程访问 jsonArr 吗?即在同时修改 jsonArr 时迭代它。
ConcurrentModificationException is thrown when you modify a collection at the same time while iterating it.
当您在迭代集合的同时修改集合时,会抛出 ConcurrentModificationException。