Unordered_map迭代器失效



我有这个迭代器循环,

typedef  boost::unordered_map<std::pair<int, int>, NavigationNode> NodesMap;
NodesMap nodes;
for (NodesMap::iterator it= nodes.begin(); it != nodes.end() ; ++it)
{
  if(it->second.type == NavigationNodeType_Walkable)
  {
    ConnectNode(&it->second);
  }
}

ConnectNode函数似乎使迭代器无效。它在导航节点内推送新元素,并修改导航节点的现有成员。

我有两个问题

  • 将它传递为指针>秒不好吗?
  • 循环访问此容器的最佳方法是什么?

谢谢。

编辑:

像这样访问容器的元素吗

   nodes[intpair(x, y)]

在连接节点函数中会导致此问题吗?

编辑2是的,确实如此。

为什么会这样?我该如何解决呢?

  • 将它传递>秒作为指针不好吗?

    这取决于获取指针的函数本身的作用。孤立地看,传递指针本身并没有错。

  • 循环访问此容器的最佳方法是什么?

    您使用的方式很好。使用 begin()end() 进行迭代是非常标准的。

所以我认为问题一定出在ConnectNode,很可能你没有迭代器失效问题,而是别的东西。

"像这样访问容器的元素吗"

nodes[intpair(x, y)]

这将向地图添加一个新条目,这是一个不存在键intpair(x,y)条目,所以是的,这可能会搞砸迭代。您可以通过在使用 [] 运算符访问之前检查该键的元素是否存在来避免这种情况。

根据您的

更新,ConnectNode可以修改您正在迭代的地图。

nodes[intpair(x, y)]

如果映射中尚不存在该键,则将插入一个新元素。这可能会导致映射被重新散列,从而使所有迭代器无效。

为避免修改地图,您可以使用 find()at() . find()将通过其返回值指示键是否存在,如果键不存在,at()将抛出。

如果你确实需要在ConnectNode期间向地图添加新元素,那么事情就更棘手了。您也许可以将它们放在一个单独的容器中,然后在循环后将它们添加到nodes中。

最新更新