如何获得保证的无效迭代器(用于向量)?

Posted

技术标签:

【中文标题】如何获得保证的无效迭代器(用于向量)?【英文标题】:How to get a guaranteed invalid iterator (for vector)? 【发布时间】:2018-04-25 18:04:39 【问题描述】:

我有一个容器类,它本质上是(仅显示相关部分)

class Foo 
    typedef std::map<int, std::vector<int>> data_t;
    data_t data;
    struct iterator 
        data_t::iterator major_it;
        data_t::mapped_type::iterator minor_it;
        // ...
    ;
    iterator begin();
    iterator end() 
        return  data.end(), /* XXX */ ;
    
;

如您所见,我想为这个容器实现迭代器。迭代器应遍历 map 中的每个节点,而迭代器应遍历节点引用的向量中的每个元素。我在实现迭代器时没有问题,但在为容器实现 end() 时遇到了一些麻烦。

迭代器由两级迭代器组成,对于过去结束的迭代器,major_it 必须是 data_t.end(),但我不会有任何东西要初始化 minor_it

同样,begin() 也会在地图为空时被破坏。

有什么想法吗?

【问题讨论】:

【参考方案1】:

std::vector::iterator在值初始化时总是无效的:

std::vector<…>::iterator invalid_iter_value = ;

顺便说一句,默认初始化(即未初始化)时它是不可用的,这对你来说可能已经足够了。如果major_it 已经在末尾,那么就不要访问minor_it

std::vector<…>::iterator unusable_iter_value;

但是,请注意,复制默认初始化的对象也是非法的,因此值初始化是一个好主意,除非您正在自定义复制构造函数和运算符。

【讨论】:

也许我只是偏执。 begin()中是否需要一个分支来过滤掉map为空的情况? @YiFei Make it UB :P @Rakete1111,不知道对未来的访客是否有好处,但我赞成:P。 补充:将一个值初始化的迭代器与另一个值初始化的迭代器进行比较是很好的定义,而默认初始化的迭代器不能与任何东西进行比较。

以上是关于如何获得保证的无效迭代器(用于向量)?的主要内容,如果未能解决你的问题,请参考以下文章

C++向量调试实现

如何识别向量迭代器是不是已到达向量末尾?

对于 C++ Random Access Iterator(向量迭代器),迭代器之间的差异是如何计算的?

如何仅使用 C++ 中的迭代器正确迭代 3D 向量? [关闭]

如何通过迭代器访问向量中的嵌套对?

如何在迭代器中正确引用第一个向量容器?