英文:
Why does this gives me an error (Multi Thread or ArrayList)?
问题
ArrayList<Nemico> nemici = o_orda.getNemici();
for (Nemico nemico : nemici) {
if (Collisioni.ControllaCollisioni(o_navicella, nemico)) {
nemici.remove(nemico);
this.o_navicella.vita -= 10;
break;
}
for (Proiettile pro : proiettili) {
System.out.println("s1");
if (Collisioni.CollsioniProiettile(pro, nemico)) {
System.out.println("s2");
nemici.remove(nemico);
System.out.println("s3");
proiettili.remove(pro);
System.out.println("s4");
break;
}
System.out.println("s5");
}
if (ControllaSconfitta()) {
this.giocON = false;
Disegna();
}
}
This is the code, I'm sure it will help you.
This code is in a function that checks and updates everything every n milliseconds.
Thanks for the help
Exception in thread "Thread-7" java.util.ConcurrentModificationException
at java.util.ArrayList$Itr.checkForComodification(ArrayList.java:901)
at java.util.ArrayList$Itr.next(ArrayList.java:851)
at java.lang.Thread.run(Thread.java:745)
and it freezes the game when the collision happens.
<details>
<summary>英文:</summary>
I have two threads which are running and I need to control if the bullet is touching the enemy but it gives me this problem where I printed "s4". Any idea what happened there? I'm quite a beginner. I'm using Java.
ArrayList<Nemico> nemici= o_orda.getNemici();
for (Nemico nemico : nemici) {
if(Collisioni.ControllaCollisioni(o_navicella, nemico)){
nemici.remove(nemico);
this.o_navicella.vita-=10;
break;
}
for (Proiettile pro : proiettili){
System.out.println("s1");
if(Collisioni.CollsioniProiettile(pro, nemico)){
System.out.println("s2");
nemici.remove(nemico);
System.out.println("s3");
proiettili.remove(pro);
System.out.println("s4");
break;
}
System.out.println("s5");
}
if(ControllaSconfitta()){
this.giocON=false;
Disegna();
}
}
This is the code, I'm sure it will help you.
This code is in a function that checks and update everything every n millisecond.
Thanks for the help
Exception in thread "Thread-7" java.util.ConcurrentModificationException
at java.util.ArrayList$Itr.checkForComodification(ArrayList.java:901)
at java.util.ArrayList$Itr.next(ArrayList.java:851)
at java.lang.Thread.run(Thread.java:745)
and it freeze the game when the collsion happens.
</details>
# 答案1
**得分**: 1
_以下代码已经更新以使用Iterator.remove(),而不是ArrayList.remove()。感谢@PeterRader澄清了它们的使用方法。_
---
如果您在迭代ArrayList时打算对其进行修改,不应直接使用for-each循环进行迭代。有两种替代方法,一种是使用迭代器避免直接迭代ArrayList本身,另一种是使用Java 8的removeIf()函数。
我将给出一个简单(经过测试的)使用迭代器的示例,然后尝试修改您的代码以执行相同的操作:
**迭代器示例**
```java
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
public class IteratorExample {
public static void main(String[] args) {
ArrayList<Integer> arrList = new ArrayList<Integer>(Arrays.asList(1, 2, 3));
// 获取一个迭代器以迭代arrList中的整数
Iterator<Integer> iterator = arrList.iterator();
// 当迭代器有下一个元素时,使用.next()访问此元素并将其打印出来。
while (iterator.hasNext()) {
System.out.println(iterator.next());
}
}
}
修改您的代码以使用迭代器
对于此版本中可能存在的拼写错误或语法错误,我深感抱歉 - 我无法对其进行测试,但鉴于这只是一个小片段的代码,错误应该不会太多,希望您可以使用上述示例进行修复。 不要忘记也导入java.util.Iterator!
ArrayList<Nemico> nemici = o_orda.getNemici();
Iterator<Nemico> nemiciIterator = nemici.iterator();
while (nemiciIterator.hasNext()) {
nemico = nemiciIterator.next();
if (Collisioni.ControllaCollisioni(o_navicella, nemico)) {
nemiciIterator.remove();
this.o_navicella.vita -= 10;
break;
}
Iterator<Proiettile> proIterator = proiettili.iterator();
while (proIterator.hasNext()) {
pro = proIterator.next();
if (Collisioni.CollsioniProiettile(pro, nemico)) {
nemiciIterator.remove();
proIterator.remove();
break;
}
}
if (ControllaSconfitta()) {
this.giocON = false;
Disegna();
}
}
...
资源
这是一个相关的资源。它还包括使用removeIf()的示例!https://www.baeldung.com/java-concurrentmodificationexception。
英文:
The below code has been updated to use Iterator.remove() instead of ArrayList.remove(). Thank you to @PeterRader for clarifying how these should be used.
If you are intending to modify an ArrayList while iterating over it, you should not use a for-each loop to iterate over it directly. There are two alternative approaches, using an iterator to avoid iterating over the ArrayList itself, or using Java 8's removeIf() function.
I will give a simple (and tested) example of using an iterator, and then attempt to modify your code to do the same thing:
Iterator Example
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Iterator;
public class IteratorExample{
public static void main(String []args){
ArrayList<Integer> arrList = new ArrayList<Integer>(Arrays.asList(1,2,3));
// Get an Iterator to iterate over the Integers in arrList
Iterator<Integer> iterator = arrList.iterator();
// While iterator hasNext element, access this element with .next() and print it.
while(iterator.hasNext()) {
System.out.println(iterator.next());
}
}
}
Modifying your code to use an iterator
Apologies for any spelling mistakes or syntax errors in this version - I have been unable to test it, but given it's only a small piece of code there shouldn't be many and hopefully you will be able to remedy them using the example above. Don't forget to import java.util.Iterator too!
ArrayList<Nemico> nemici= o_orda.getNemici();
Iterator<Nemico> nemiciIterator = nemici.iterator();
while (nemiciIterator.hasNext()) {
nemico = nemiciIterator.next();
if(Collisioni.ControllaCollisioni(o_navicella, nemico)){
nemiciIterator.remove(nemico);
this.o_navicella.vita-=10;
break;
}
Iterator<Proiettile> proIterator = proiettili.iterator();
while (proIterator.hasNext()) {
pro = proIterator.next();
if(Collisioni.CollsioniProiettile(pro, nemico)){
nemiciIterator.remove(nemico);
proIterator.remove(pro);
break;
}
}
if(ControllaSconfitta()){
this.giocON=false;
Disegna();
}
}
...
Resources
Here is a relevant resource. This also includes an example of using removeIf()! https://www.baeldung.com/java-concurrentmodificationexception.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论