std::reverse_iterator通过包装正向迭代器并调整其位置实现反向遍历,核心是解引用时执行*(current - 1),rbegin()指向end()、rend()指向begin()以维持左闭右开区间语义,要求底层迭代器为双向迭代器且支持--和-运算。

std::reverse_iterator 的核心是 operator-> 和 operator* 怎么反向解引用?
它不自己存数据,而是“包装”一个正向迭代器(比如 std::vector<int>::iterator</int>),所有操作都靠调整这个底层迭代器的位置来实现。关键在于:反向迭代器的 current 成员指向的是“逻辑上后一个位置”。比如,rend() 对应 begin(),rbegin() 对应 end()。
所以 operator* 实际执行的是 *(current - 1) —— 这就是偏移量处理的核心:每次解引用都要往前退一位。
-
++rit等价于--rit.current(底层迭代器往左走) -
--rit等价于++rit.current(底层迭代器往右走) -
rit[0]调用的是*(rit.current - 1),rit[1]是*(rit.current - 2)
为什么 rbegin() 指向 end(),而 rend() 指向 begin()?
这是为了保持和正向迭代器一致的“左闭右开”区间语义:[rbegin(), rend()) 应该覆盖和 [begin(), end()) 相同的元素,只是顺序相反。
如果 rbegin() 指向最后一个元素本身,那 rend() 就得指向 begin() - 1 —— 这在很多容器(如 std::vector)里是非法的(越界)。用 end() 和 begin() 作锚点,能保证所有标准容器都安全支持 reverse_iterator。
立即学习“C++免费学习笔记(深入)”;
- 对
std::vector:若v = {1,2,3},则v.rbegin().current == v.end(),即指向&v[3](合法哨兵) - 对
std::list:end()是有效节点指针(sentinel node),current - 1可安全访问尾节点 - 注意:
current必须支持--和-运算,所以 reverse_iterator 要求底层迭代器至少是 BidirectionalIterator
自定义 reverse_iterator 时容易踩的偏移边界坑
手写 reverse wrapper 时,最常错的是在 operator[] 或比较操作中漏掉 -1 偏移,或在构造时搞反初始值。
例如:把 rbegin() 错写成传入 last_element_iter 而不是 end(),会导致第一次 *rit 解引用到未定义内存;或者在 operator== 中直接比 current,而忘了两个 reverse_iterator 相等,当且仅当它们的 current 相等 —— 这个是对的,但前提是构造正确。
- 构造
reverse_iterator(it)时,current应设为it,不是it - 1 -
operator!=可直接用current != other.current,但前提是所有 reverse_iterator 都遵守同一套构造约定 - 对随机访问迭代器,
rit += n应转为current -= n;别写成current += n
std::reverse_iterator 在 vector 上为啥不能用?
因为 std::vector<bool></bool> 是特化,它的 iterator 不是真正的随机访问迭代器,而是一个代理类(proxy reference),operator* 返回的是临时 std::vector<bool>::reference</bool>,不能取地址 —— 而 std::reverse_iterator 的 operator-> 要求能返回有效的指针(或模拟指针行为的对象)。
这导致 vector<bool>::reverse_iterator</bool> 的 operator-> 无法合规实现,大多数标准库干脆禁用或留空,编译时报错类似:no match for 'operator->'。
- 替代方案:用
std::vector<char></char>或std::deque<bool></bool>(其迭代器更接近常规) - 或者绕过 reverse_iterator,手动用下标倒序遍历:
for (int i = v.size(); i-- > 0; ) { ... v[i] ... } - 这不是 reverse_iterator 的 bug,是
vector<bool></bool>自身设计妥协带来的连锁限制
偏移量逻辑本身很干净,但一旦底层迭代器行为不标准(比如 proxy reference、无 operator-、不可取址),整个 reverse_iterator 就会卡在第一步。










