std :: forward_list - 用存储的迭代器擦除

时间:2013-09-20 04:05:31

标签: c++ c++11 linked-list intrusive-containers forward-list

我试图保留特定(基类)实例的全局列表,以便我可以随时通过遍历此全局列表来跟踪它们。

我认为解决这个问题的最恰当的方法是使用侵入性列表。我听说过可以通过挖掘Linux内核来遇到这些生物,例如。

在我进入的情况下,我并不需要这样的性能保证,使用侵入式列表会让事情变得复杂一些。

到目前为止,我已经实现了这个知道其所有实例的类概念。

class A {
    static std::forward_list<A*> globallist;
    std::forward_list<A*>::iterator listhandle;
public:
    A() {
        globallist.push_front(this);
        listhandle = globallist.begin();
    }
    virtual ~A() {
        globallist.erase_after(...);  // problem
    }
};

问题在于没有forward_list::erase(),并且看起来好像保存globallist.before_begin()并不会对我有好处。我永远不应该取消引用before_begin()的迭代器。它真的会保持这个位置吗?如果我保存before_begin的迭代器,然后push_front()一个新项,那么迭代器可能仍然无法被解除引用,但是它可以用于发送到{{1} }?

1 个答案:

答案 0 :(得分:3)

forward_list是一个单独链接列表。要删除中间的节点,必须以某种方式指向前一个节点。例如,你可以这样做:

class A {
    static std::forward_list<A*> globallist;
    std::forward_list<A*>::iterator prev_node;
public:
    A() {
        A* old_head = globallist.front();
        globallist.push_front(this);
        prev_node = globallist.before_begin();
        old_head->prev_node = globallist.begin();
    }
};

将第一个元素推入空列表以及删除逻辑的情况留给读者练习(删除时,将prev_node复制到下一个节点的prev_node )。

或者,只需使用std::list并避免所有这些麻烦。