C ++迭代一组

时间:2011-03-03 20:18:00

标签: c++ iterator set std

我最近更改了一些代码以使用集合而不是向量:

std::set<b2Body *>toDestroy;
//std::vector<b2Body *>toDestroy;

但现在我不确定如何迭代该集来查找对象。这就是我所拥有的:

std::vector<b2Body *>::iterator pos2;
    for(pos2 = toDestroy.begin(); pos2 != toDestroy.end(); ++pos2) {
        b2Body *body = *pos2;     
        if (body->GetUserData() != NULL) {
            CCSprite *sprite = (CCSprite *) body->GetUserData();
            [self removeChild:sprite cleanup:YES];
        }
        _world->DestroyBody(body);
    }

现在toDestroy是一个集合的等价物是什么?来自Objective-C所以我只是学习C ++中的最佳实践。

编辑:添加我收到的错误消息:

error: no match for 'operator=' in 'pos2 = toDestroy. std::set<_Key, _Compare, _Alloc>::begin [with _Key = b2Body*, _Compare = std::less<b2Body*>, _Alloc = std::allocator<b2Body*>]()'

5 个答案:

答案 0 :(得分:5)

您需要将迭代器声明为set迭代器:

更改

std::vector<b2Body *>::iterator pos2;

std::set<b2Body *>::iterator pos2;

答案 1 :(得分:1)

使用C ++ 11,您只需编写:

    for(auto pos2:toDestroy)

答案 2 :(得分:0)

通过集合的迭代将在向量存在时起作用,因此无需更改代码。

我会注意DestroyBody中发生的事情(调用是从向量中移除元素还是设置,使迭代器无效?)

vector,set或list的用法取决于用法:

  • 如果预先知道b2Body对象的数量,我会使用向量,因此可以预先保留容量,并且不经常发生新的插入删除,或者如果你需要随机访问向量的元素(没有迭代器)
  • 如果事先不知道元素数量和/或经常插入和删除,我会使用该列表
  • 如果我需要遍历一个有序的元素列表,或者如果我需要应用程序来查找某些数据是否已经处理并且在集合中(方法中的方法发现很快),我会使用该集合)

我认为这里最合适的容器是列表(仍然不需要更改迭代代码)

答案 3 :(得分:0)

很多时候值得为类型化的模板化容器类型(特别是在类中使用时)。

typedef std::set<b2Body *>   BodyCont;
//typedef std::vector<b2Body *>   BodyCont;
BodyCont                toDestroy;

然后你的其他代码就不需要修改了:

BodyCont::iterator pos2;

如果您可以将typedef设为私有,那么您就知道实现细节不会逃避该类。如果你需要公开typedef,那么你知道你正在泄漏实现细节,需要了解为什么以及你是否可以收紧你的设计。

答案 4 :(得分:0)

从C ++ 11开始,在遍历容器时,应该使用“auto”来声明迭代器。 在您的情况下,“for”行可以这样写: for(auto pos2 = toDestroy.begin(); pos2!= toDestroy.end(); ++ pos2)