帮助C ++ List擦除功能

时间:2008-12-17 02:10:06

标签: c++ iterator

我正在尝试进行简单的擦除并不断出错。

以下是我擦除的代码片段:

std::list<Mine*>::iterator iterMines = mines.begin();
for(int i = oldSizeOfMines; i >0 ; i--, iterMines++)
{
    if(player->distanceFrom(*iterMines) < radiusOfOnScreen)
    {
        onScreen.push_back(*iterMines);
        iterMines = onScreen.erase(iterMines);
        iterMines--;
    }
}

我不断收到编译器消息:

1>c:\users\owner\desktop\bosconian\code\bosconian\environment.cpp(158) : error C2664: 'std::list<_Ty>::_Iterator<_Secure_validation> std::list<_Ty>::erase(std::list<_Ty>::_Iterator<_Secure_validation>)' : cannot convert parameter 1 from 'std::list<_Ty>::_Iterator<_Secure_validation>' to 'std::list<_Ty>::_Iterator<_Secure_validation>'
1>        with
1>        [
1>            _Ty=SpaceObject *,
1>            _Secure_validation=true
1>        ]
1>        and
1>        [
1>            _Ty=Mine *,
1>            _Secure_validation=true
1>        ]
1>        and
1>        [
1>            _Ty=SpaceObject *,
1>            _Secure_validation=true
1>        ]
1>        No user-defined-conversion operator available that can perform this conversion, or the operator cannot be called

我很困惑因为我相信我正在给它正确的迭代器。

Mine是SpaceObject的子类(是第二代子类)

这与它有什么关系吗?我该如何解决?

3 个答案:

答案 0 :(得分:4)

问题是你试图在onScreen列表中使用mines的迭代器作为迭代器。这不行。

你的意思是调用mines.erase(iterMines)而不是onScreen.erase(iterMines)吗?

答案 1 :(得分:2)

std::list<Mine*>::iterator iterMines = mines.begin();
for(int i = oldSizeOfMines; i >0 ; i--, iterMines++)
{
        if(player->distanceFrom(*iterMines) < radiusOfOnScreen)
        {
                onScreen.push_back(*iterMines);
                iterMines = onScreen.erase(iterMines);
                iterMines--;
        }
}

一个真正的问题,一个可能的解决方案:

erase将在删除元素后为您提供下一个迭代器。因此,如果你刚开始,并且擦除,你将获得新的开始。如果然后递减迭代器,则在开始之前递减。这是无效的。最好将iterMines++分解为循环体:

std::list<Mine*>::iterator iterMines = mines.begin();
for(int i = oldSizeOfMines; i >0 ; i--)
{
        if(player->distanceFrom(*iterMines) < radiusOfOnScreen)
        {
                onScreen.push_back(*iterMines);
                iterMines = mines.erase(iterMines); // change to mines!!
        } else { 
            ++iterMines; // better to use ++it instead of it++
        }
}

更好地使用预增量,因为在创建自身副本时,您永远不知道迭代器在场景后面的作用。 ++it将返回新的迭代器,而it++将在增量之前返回迭代器的副本。我已经评论了可能解决方案的部分:)

答案 2 :(得分:0)

更简单的方法 List.erase(p)的用法