2013-02-22 155 views
0

为我的投资组合工作一个小行星游戏。使用以下代码块与错误进行游戏。错误仅仅是迭代器不可忽略,但是我已经缩小了错误的范围。我将谈论后,我已经向你展示的代码:迭代器错误内的向量迭代器

void Game::Update() 
{ 
if (elapsedTime > REFRESH_RATE) 
{ 
    player->Update(elapsedTime); 

    std::vector<Asteroid*>::iterator iterator= bigAsteroids.begin(); 
    std::vector<Bullet*>::iterator iter = bullets.begin(); 

    // *********************** // 
    while (iterator!= bigAsteroids.end()) 
    { 
     if (*iterator != nullptr) // Checks to see if player is colliding with an asteroid and updates the asteroid 
     { 
      player->CheckCollisionsAsteroid(*iterator); 

      // *********************** // Checks to see if bullet is colliding with asteroid 
      while (iter != bullets.end()) 
      { 
       if (*iter != nullptr) 
       { 
        if ((*iter)->CheckCollisionsAsteroid(**iterator)) 
        { 
         size_t i = iterator - bigAsteroids.begin(); 
         iter = bullets.erase(iter); 
         iterator = bigAsteroids.erase(iterator); 
         printf("\nAsteroid destroyed at position %i", i); 
        } 
        else 
        { 
         ++iter; 
        } 
       } 
      } 
      iter = bullets.begin(); // Reset the bullet iterator else we'd only get to check 1 asteroid 

      // *********************** // 
      if (*iterator != nullptr && iterator != bigAsteroids.end()) { (*iterator)->Update(elapsedTime); } 
     } 
     if (*iterator != nullptr && (iterator!= bigAsteroids.end())) 
     {++iterator;} 
    } 
    // *********************** // 
    Clock.Reset(); 
} 
} 

如果这一切看起来有点乱,这里有一个简要说明:

随着迭代器通过每个小行星的,我检查玩家是否与每个小行星碰撞。 目前这无能为力

然后我遍历我的子弹矢量,检查每个子弹对当前的小行星。如果发生碰撞,我会摧毁子弹和小行星,并打印被毁坏的小行星在矢量中的位置。

一旦我完成了这一点,我重置子弹iter为下一个小行星。

我目前的主要问题是通过(*迭代器)< - 小行星对更新的调用。

这个问题只会在我删除小行星向量中的最后一个对象时出现。我知道擦除返回一个迭代器到下一个对象 - 如果下一个对象不存在,将抛出一个错误(因为迭代器然后指向一个nullptr,是否正确?)。我正在检查nullptr无济于事。

有没有人有任何建议或帮助,他们可以提供?将不胜感激,一直在挠我的头几个小时!

+0

这将有助于代码的可读性显著如果你命名了迭代它们是指,如后什么'itAsteroid'和'itBullet'。 – Angew 2013-02-22 11:38:45

+0

@Angew我得到了很多哈哈,我现在不断重写代码,所以在'iter'或'iterator'上键入bulletIter或asteroidIter:P最终版本将实现这些,谢谢。 和BoB嗯..我会尽快给你回复,谢谢你的帮助 – DerryHolt 2013-02-22 11:44:28

回答

1

问题是,当你销毁最后一颗小行星时,iterator将被设置为bigAsteroids.end()(通过分配给erase()的结果)。然后内部while循环终止后,您解除引用iterator。过去的最终迭代器不能被解除引用。

你必须切换检查的顺序:

if (iterator != bigAsteroids.end() && *iterator != nullptr) 
+0

它不是最后一颗小行星。它可能是我拍摄的第一颗小行星。如果它是向量中最后一个小行星(如最后一个小行星),则错误会抛出。我不认为我目前已经设法让一个小行星射击!哈哈 – DerryHolt 2013-02-22 11:45:47

+0

他的意思是:当你调用'bigAsteroids.erase(iterator)'时,'iterator'设置为'bigAsteroids.end()'。 '* iterator!= nullptr'将会失败,并且'iterator!= bigAsteroids.end()'将返回'false',所以切换条件的顺序,并且你应该很好 – marsze 2013-02-22 11:48:05

+0

Ohhhhhhhh。我懂了。 我确实改变了它: 'if(itAsteroid!= bigAsteroids.end()){(* itAsteroid) - > Update(elapsedTime); }' 而这仍然导致错误。 但是,我再改线下: \t \t \t'如果(itAsteroid = bigAsteroids.end()&& * itAsteroid!= nullptr){++ itAsteroid;}' 它的确如你所说。我和你们做了什么:P谢谢你们两位! – DerryHolt 2013-02-22 11:53:34