2

在遍历 a std::maporstd::vector或其中包含的任何容器iterator时,会检查.variable.end()而不是container<>::end. 例如,

map<int, int> var;
for(map<int, int>::iterator it = var.begin(); it != var.end(); it++)
...                                           ^^^^^^^^^^^^^^^

上面突出显示的部分不能是这样的:

it != map<int,int>::end

这类似于 static member string::npos.end()提供每个变量基础而不是每种类型的容器基础的设计决策背后的原因可能是什么?(即map<int,int>::endmap<int,double>::end会有所不同;但对于每个map<int,int>变量,::end将是相似的。)

4

3 回答 3

7

这样,一些基于数组的容器可以简单地将迭代器实现为指向元素的指针。每个数组的最后一个元素指针都不同。

于 2012-01-09T06:21:20.680 回答
5

考虑以下两个数组:

int a1[] = {2, 3, 4};
int a2[] = {5, 6, 7};

两个数组的最后一个元素不同:

int *p1 = a1 + 3; // for a1
int *p2 = a2 + 3; // for a2

您不能将一个指针用于另一个指针。没有通用常数来表示数组的结尾。以下是错误的:

for (int *p = a1; p != a2; p++)

同种容器的迭代器不一样的解释end()类似。

于 2012-01-09T06:29:38.513 回答
4

迭代器用于迭代、向前和向后移动。它们需要提供递增和递减(双向迭代器)操作。当您递减 end() 迭代器时,您将到达容器中的最后一项。这允许向后迭代。

至于你的建议。实现这一点意味着每个迭代器都携带结束迭代器,并且当它等于它正在存储的真实结束迭代器时,它与静态结束迭代器进行比较。实际上,将所有静态结束迭代器设为不同类型是没有意义的,因为“迭代器”无论如何都不能用于除此之外的任何东西。

这样的设计实施起来更麻烦,使用起来也更浪费。如果每个迭代器都必须知道其容器的末尾,那么要指定一个任意范围,您必须在混合的末尾添加两个可能未使用的迭代器。

于 2012-01-09T07:42:12.247 回答