奇怪的射击虫 我正在用C++和SFML做游戏。我有一个奇怪的错误,每当我在屏幕上有1个敌人和3个镜头,一颗子弹与敌人相撞,游戏就会崩溃。我得到的错误是: Expression: vector subscript out of range

奇怪的射击虫 我正在用C++和SFML做游戏。我有一个奇怪的错误,每当我在屏幕上有1个敌人和3个镜头,一颗子弹与敌人相撞,游戏就会崩溃。我得到的错误是: Expression: vector subscript out of range,c++,vector,sfml,C++,Vector,Sfml,这是我检查射击和敌人之间碰撞的方式: for (int i = 0; i < enemies.size(); i++) { for (int s = 0; s < shots.size(); s++) { if (Collision::PixelPerfectTest(enemies[i].getSprite(), shots[s].getSprite())) { enemies[i].setHealth(enemies[i].getH

这是我检查射击和敌人之间碰撞的方式:

for (int i = 0; i < enemies.size(); i++)
{
    for (int s = 0; s < shots.size(); s++) {
        if (Collision::PixelPerfectTest(enemies[i].getSprite(), shots[s].getSprite())) {
            enemies[i].setHealth(enemies[i].getHealth() - player.getDamage());
            if (enemies[i].getHealth() <= 0) {
                enemies.erase(enemies.begin() + i);
            }
            shots.erase(shots.begin() + s);
        }
    }
}
for(int i=0;iif(敌人[i].getHealth()您不能像现在这样在向量上进行迭代的同时从向量中删除内容,因为这样会产生不再在向量范围内的i值(在调用erase将其大小减小后),这基本上会导致尝试索引不再存在的数组值。
如果需要这种行为,最好使用迭代器:

auto eit = enemies.begin();
for (; eit != enemies.end(); )
{
    if((*eit).isDead())
    {
         eit = enemies.erase(eit);
    }
    else
    {
         eit++;
    }
}

您也可以对快照数组执行同样的操作。

@moka的回答解释了代码的核心问题,他/她的代码使用迭代器将解决您的问题。但是,还有另一种方法可以解决此问题:将代码拆分为“计算过程”和“数组修改过程”。代码如下所示:

for (int i = 0; i < enemies.size(); i++)
{
    for (int s = 0; s < shots.size(); s++) {
        if (!enemies[i].alive || !shots[s].active) {
            continue;
        }
        if (Collision::PixelPerfectTest(enemies[i].sprite(), shots[s].sprite())) {
            shots[s].active = false;
            enemies[i].setHealth(enemies[i].getHealth() - player.getDamage());
            if (enemies[i].getHealth() <= 0) {
                enemies[i].alive = false;
            }
        }
    }
}

enemies.erase(std::remove_if(enemies.begin(), enemies.end(),
    [](Enemy const &e) { return !e.alive; }), enemies.end());

shots.erase(std::remove_if(shots.begin(), shots.end(),
    [](Shot const &s) { return !s.active; }), shots.end());
for(int i=0;i如果(敌人[i].getHealth()谢谢,但现在我遇到了另一个问题。请参阅我编辑的帖子
auto eit = enemies.begin();
for (; eit != enemies.end(); )
{
    if((*eit).isDead())
    {
         eit = enemies.erase(eit);
    }
    else
    {
         eit++;
    }
}
for (int i = 0; i < enemies.size(); i++)
{
    for (int s = 0; s < shots.size(); s++) {
        if (!enemies[i].alive || !shots[s].active) {
            continue;
        }
        if (Collision::PixelPerfectTest(enemies[i].sprite(), shots[s].sprite())) {
            shots[s].active = false;
            enemies[i].setHealth(enemies[i].getHealth() - player.getDamage());
            if (enemies[i].getHealth() <= 0) {
                enemies[i].alive = false;
            }
        }
    }
}

enemies.erase(std::remove_if(enemies.begin(), enemies.end(),
    [](Enemy const &e) { return !e.alive; }), enemies.end());

shots.erase(std::remove_if(shots.begin(), shots.end(),
    [](Shot const &s) { return !s.active; }), shots.end());