Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/128.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 集合中的迭代器是如何工作的_C++ - Fatal编程技术网

C++ 集合中的迭代器是如何工作的

C++ 集合中的迭代器是如何工作的,c++,C++,我想知道c++的STL中的迭代器是如何设置的。我猜这个集合是用二叉搜索树实现的,这意味着迭代器按顺序遍历这棵树。但我的问题是,他们什么时候开始遍历 当我们喜欢的时候 it=s.begin() 并在内部以堆栈的形式存储遍历的指针,并在迭代器中的每个增量上仅引用此数据结构 或者迭代器中的增量在树上执行新的顺序遍历 我是说当我们喜欢 set<int> s; set<int>::iterator it; //and then use it like:

我想知道c++的STL中的迭代器是如何设置的。我猜这个集合是用二叉搜索树实现的,这意味着迭代器按顺序遍历这棵树。但我的问题是,他们什么时候开始遍历 当我们喜欢的时候 it=s.begin() 并在内部以堆栈的形式存储遍历的指针,并在迭代器中的每个增量上仅引用此数据结构 或者迭代器中的增量在树上执行新的顺序遍历

我是说当我们喜欢

     set<int>  s;
     set<int>::iterator it;

 //and then use it like:

      for(it = s.begin(); it!=s.end(); )
      {
           dosth();
           ++it;     // does this do a inorder traversal of the tree again to find the next 
                     // node or it gets the next node in the tree by reading the internal
                    // data structure(of inorder traversal) which is created when we do   s.begin().
      } 
set;
set::迭代器;
//然后像这样使用它:
for(it=s.begin();it!=s.end();)
{
dosth();
++it;//是否再次按顺序遍历树以查找下一个
//节点或通过读取内部
//在执行s.begin()时创建的(按顺序遍历的)数据结构。
} 

它取决于实现。但是,只有当迭代器引用从集合中删除的元素时,std::set迭代器才会失效。因此,您可以将
std::set
迭代器视为树中的节点在树的一个遍历方向上移动它,然后--在另一个遍历方向上移动它


请注意,迭代器是由其他函数返回的,这些函数是
begin
,因此它们的有效性不仅限于开始/结束迭代。

这是一个有趣的问题。正如Nicol指出的,它依赖于实现,在实现自己的集合时,您必须决定是喜欢更小的迭代器还是更快的遍历(您可以将更多数据放入迭代器以加快遍历速度)

在我的平台上(64位)
std::set::iterator
的大小为8字节,这表明它只保留指向实际节点的指针。如果集合是使用某种树实现的,那么迭代器的递增肯定不是O(1)操作,需要遍历多达log(N)个额外节点(如果谈论平衡树)。我还检查了不同节点的
++it
操作的速度,它不是常数,表示额外的遍历。对于通用集合容器来说,这是完全合适的,因为它满足了树遍历复杂性的期望,并且人们通常认为迭代器尽可能小。如果实现标准的递归树遍历,则完全相同,只需隐藏堆栈上的额外节点访问


请看一看,以获得有关实现您自己的树迭代器的更多详细信息。

谢谢您的回答…但让我用另一种方式提出我的问题..如果您被要求这样做,您将如何在std::set上实现迭代器的增量操作..假设在内部使用二叉搜索树而不是链表来实现节点每次增量操作时,您都会对该树进行索引遍历++它..或者您将初始保存该顺序,并在每次执行时引用该顺序++it@raja:无法使用简单的链接列表实现
std::set
。在集合中查找元素必须是O(logn),但在链表中查找元素是O(N)。它一定是一棵树。如果树节点保留指向其父节点的指针,
it++
始终可以在不进行完整树遍历的情况下找到下一个最高值。如果您在64位机器上工作,则地址为8字节。迭代器很可能被实现为一个类,其唯一的数据成员是指针——这正是GNU实现的工作原理。David,你完全正确,我忘了我现在在64位机器上。谢谢,我已经编辑了我的帖子。