[sfml] usuwanie obietku z vectora [rozwiązany]
Ostatnio zmodyfikowano 2013-01-14 17:18
bari Temat założony przez niniejszego użytkownika |
[sfml] usuwanie obietku z vectora [rozwiązany] » 2013-01-14 15:05:11 Witam. Mam problem, z którym borykam się od wczoraj. W SFML w pętli while(Okno.isOpen()) rysuje obiekty, które chciałbym skasować przy pewnych założeniach. Mam obiekt "aktualnyLevel" klasy Plansza. Zawiera on w sobie vector elementów typu Pocisk. Chciałbym, by elementy te zostały skasowane z pamięci kiedy wylecą poza obramowanie ekranu: for( vector < Pocisk *>::iterator pocisk = aktualnyLevel->getGracz()->rakiety.begin(); pocisk != aktualnyLevel->getGracz()->rakiety.end(); ) { int x =( * pocisk )->getX(); int y =( * pocisk )->getY(); if(( x < 0 || x > desktop.width ) ||( y < 0 || y > desktop.height ) ) { delete * pocisk; aktualnyLevel->getGracz()->rakiety.erase( pocisk ); } else { ( * pocisk )->ruch( & event ); Okno.draw(( * pocisk )->getSprite() ); } pocisk++; }
problem w tym, że aplikacja się wysypuje z komunikatem "vector iterators incompatible". Nie rozumiem, gdzie może wystąpić niekompatybilność, skoro cały czas operuje na tym samym iteratorze. Dodam, że jeśli okomentuję zawartość if'a, wówczas wszystko działa jak należy, z tym, że obiekty pozostają w pamięci, co z oczywistych względów jest nie do zaakceptowania. Pozdrawiam i z góry dziękuję za pomoc |
|
DejaVu |
» 2013-01-14 16:34:21 Nie można kontynuować iteracji w std::vector po usunięciu elementu. Używaj albo indeksów, albo rozpoczynaj iterację od początku (ale to raczej chybiony pomysł). |
|
ison |
» 2013-01-14 16:38:10 Nie można kontynuować iteracji w std::vector po usunięciu elementu |
Można, erase zwraca iterator kolejnego elementu po usunięciu. @bari, pod pocisk podstaw to co zwróci erase, a pocisk++; wrzuć do else. |
|
DejaVu |
» 2013-01-14 16:47:16 Hę? std::vector? Przecież może dojść do realokacji całej tablicy i wszystkie iteratory szlag trafi...
/edit: Racja :P Myślałem, że erase w std::vector zwraca void-a :P A tu niespodzianka :) |
|
bari Temat założony przez niniejszego użytkownika |
» 2013-01-14 17:18:48 rozwiązane
pocisk = aktualnyLevel->getGracz()->rakiety.erase(pocisk); zamiast aktualnyLevel->getGracz()->rakiety.erase(pocisk);
tak oczywisty błąd, a tyle szukania, no ale tak bywa, że większość czasu w debuggerze spędza się w poszukiwaniu średnika ;)
ps. ison widzę, że też to zauważył, dzięki ;)
|
|
« 1 » |