Hallo!
Ich bastle gerade an einer einfache Spieleengine, bekomme jedoch bei einem Testspiel in scheinbar unregelmäßigen Abstände eine Concurrent Modification Exception geworfen in der Spielschleife.
Meine Spielschleife sieht so aus:
Es passiert oft, dass Objekte wie Projektile sich aus der Spielschleife löschen, wenn sie z.B. auf ein Ziel getroffen haben. Dies Funktioniert in der doLogic Methode. Es wäre nun klar, wenn eine solche Exception geworfen wird, da die Liste ja während der Iteration geändert wird. Dies habe ich in meiner GameList (eine eigene Klasse) eigendlich berücksichtigt, die zu löschenden oder hinzuzufügenden Objekte werden vorher zwischengespeichert und vor der Zurückgabe des Iterators wird die eigentliche Liste dann abgeglichen:
Dies scheint auch zu funktionieren, ab und zu werden jedoch dennoch die Exceptions geworfen und einen wirklichen Grund konnte ich bisher noch nicht finden. Interessant ist auch, dass sie scheinbar immer aus anderen Threads geworfen werden, ich kann mir allerdings nicht erklären wo diese Threads herkommen:
In meinem Programm sind außer der Spielschleife eigendlich keine anderen Threads vorhanden.
mfg
Ich bastle gerade an einer einfache Spieleengine, bekomme jedoch bei einem Testspiel in scheinbar unregelmäßigen Abstände eine Concurrent Modification Exception geworfen in der Spielschleife.
Meine Spielschleife sieht so aus:
Java:
public void run() {
while (gameRunning) {
calculateDelta();
Graphics2D g = buffer.createGraphics();
g.clearRect(0, 0, getWidth(), getHeight());
g.drawString("FPS " + fps, 0, 20);
for (GameObject o : gameList) {
if (o instanceof Logicable)
((Logicable) o).doLogic(delta);
if (o instanceof Movable)
((Movable) o).move(delta);
o.draw(g);
}
g.dispose();
g = null;
getGraphics().drawImage(buffer, 0, 0, null);
try {
Thread.sleep(sleepTime);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
Es passiert oft, dass Objekte wie Projektile sich aus der Spielschleife löschen, wenn sie z.B. auf ein Ziel getroffen haben. Dies Funktioniert in der doLogic Methode. Es wäre nun klar, wenn eine solche Exception geworfen wird, da die Liste ja während der Iteration geändert wird. Dies habe ich in meiner GameList (eine eigene Klasse) eigendlich berücksichtigt, die zu löschenden oder hinzuzufügenden Objekte werden vorher zwischengespeichert und vor der Zurückgabe des Iterators wird die eigentliche Liste dann abgeglichen:
Java:
public class GameList implements Iterable<GameObject> {
private ArrayList<GameObject> addList = new ArrayList<GameObject>();
private ArrayList<GameObject> removeList = new ArrayList<GameObject>();
private ArrayList<GameObject> gameList = new ArrayList<GameObject>();
public boolean add(GameObject go) {
return addList.add(go);
}
public boolean remove(GameObject go) {
return removeList.add(go);
}
@Override
public Iterator<GameObject> iterator() {
gameList.removeAll(removeList);
removeList.clear();
gameList.addAll(addList);
addList.clear();
return gameList.iterator();
}
}
Dies scheint auch zu funktionieren, ab und zu werden jedoch dennoch die Exceptions geworfen und einen wirklichen Grund konnte ich bisher noch nicht finden. Interessant ist auch, dass sie scheinbar immer aus anderen Threads geworfen werden, ich kann mir allerdings nicht erklären wo diese Threads herkommen:
Java:
Exception in thread "Thread-3" java.util.ConcurrentModificationException
at java.util.AbstractList$Itr.checkForComodification(AbstractList.java:372)
at java.util.AbstractList$Itr.next(AbstractList.java:343)
at armEngine.Game.run(Game.java:60)
at java.lang.Thread.run(Thread.java:619)
Exception in thread "Thread-5" java.util.ConcurrentModificationException
...
Exception in thread "Thread-6" java.util.ConcurrentModificationException
...
Exception in thread "Thread-7" java.util.ConcurrentModificationException
...
In meinem Programm sind außer der Spielschleife eigendlich keine anderen Threads vorhanden.
mfg