矢量迭代器不兼容:运行时错误

Vector iterators incompatible: runtime error

本文关键字:运行时错误 不兼容 迭代器      更新时间:2023-10-16

我当前遇到了一个包含对象向量的类的析构函数问题。应用程序运行良好,但是在释放堆时会抛出一个错误。

这是我的析构函数的代码:

    ~StaticNetwork(void) { // clear memory
    for(vector<Node*>::iterator iter = nodes.begin(); iter != nodes.end(); )
        nodes.erase(iter++);
}

节点被添加到网络中,如下所示:

    if((temp = is_already_added(regex_d[1])) >= 0) // check if the src node has already been added
            {
                if((temp1 = is_already_added(regex_d[2])) >= 0) // check if the next_hop has already been added
                {
                    nodes[temp]->add_n_vchannels(regex_d[5]);
                    nodes[temp]->add_next_hop(nodes[temp1]);
                }
                else // the next_hop has not been added 
                {
                    Node *anext_hop = new Node(regex_d[2]);
                    nodes[temp]->add_next_hop(anext_hop);
                    nodes[temp]->add_n_vchannels(regex_d[5]);
                    nodes.push_back(anext_hop); //  add next hop        
                    param.n_of_nodes++;
                }       
            }

网络由指向实际节点的指针组成。

任何帮助/建议/参考/(建设性的)批评都将不胜感激。

您对容器的迭代是错误的。如果node是类的成员,那么忽略它,因为向量的析构函数会处理它。如果它不是成员,并且你真的想删除所有元素,最简单的事情就是调用node.clear()(注意,两者都相当于你的代码,但如果应该由你的类管理,它们会泄漏指向内存)

如果指针由类管理,请考虑使用智能指针或特定的指针容器。否则,释放所有内存的最简单循环是:

for ( std::vector<Node*>::iterator it = nodes.begin(); it != nodes.end(); ++it )
   delete *it;

请注意,我没有修改容器本身,只是修改了包含的元素。

您不需要手动删除向量的元素,它将由向量本身完成。析构函数就是这样工作的:它们调用被删除对象的成员对象的析构函数,所以你不必担心

擦除无法按预期工作:它从容器中删除元素,即指针和而不是指向对象。所以你在这里泄露记忆。

此外,擦除会使被擦除元素后面的迭代器失效,因此当指针超过它时,测试iter != nodes.end();会导致错误。

不管怎样,你可以按照David Rodríguez-dribeas所示编写代码。