STD 设置在内存中

问题描述

从我读过的内容来看,该集合是使用树实现的(我希望使用二叉搜索树)。据我所知,树的元素不是以连续方式存储的,因为它们是使用 new 创建的。 这是迭代一组的方法

for (auto it = myset.begin() ; it != myset.end() ; it++)
//or
for (auto it : myset)

在第一种方法中,如果树中的元素不是以连续方式存储,“it++”将如何工作?

解决方法

For 循环与容器没有直接关系,它只是允许您在满足条件时多次执行某些代码块。

For 循环的常见应用是按顺序调整某个数字,并使用它以该数字作为索引(从头开始偏移)访问连续数组中的某个元素。

正如您所提到的,它不适用于未连续对齐的数据,但“For”循环不仅限于更新索引。迭代器是一种封装了容器遍历逻辑的对象模式。容器提供了获取迭代器的方法,然后迭代器提供了在某个方向移动容器内容的方法。

有了它,你可以使用“for”循环(它不仅限于更新索引!)和迭代器来遍历集合元素

for (auto iterator = my_set.begin(); iterator != my_set.end(); iterator++)
// do something with element through iterator

C++11 的“基于范围的 for”特性只允许你为相同的逻辑提供一个紧凑的形式:

for (auto iterator : my_set)
// do something with element through iterator

内部设置的前向迭代器只是按照特定的顺序遍历树节点,处理下一个节点选择的所有逻辑,在二叉搜索树中从左到右移动。

你可以想象 set::begin() 返回一个迭代器,它内部存储了 set 中第一个节点的地址(前向迭代器的最左边的叶子)。 Iterator::operator++ 的实现方式是更新迭代器以按排序顺序引用下一个节点。

从迭代器的角度来看下一项选择的非正式逻辑: 如果我的节点留下了孩子 - 它小于我的元素,所以我不需要访问它。右节点比我的元素大,所以它是下一个元素。 如果我的节点没有右孩子 - 我需要向上移动以找到下一个元素。我需要知道我是从左上还是从右上。如果我从左子树向上移动 - 那么父节点的值是下一个有序值。如果我从右子树移动 - 我已经访问了这个节点,我需要递归地继续我的提升,同时我会发现我从左子树接近节点。如果没有找到这样的节点 - 这意味着我刚刚指向了最后一个元素,所以现在我应该使内部引用无效以突出显示迭代器到达容器的末尾。