问题描述
我有一个名为 Action
的类,它本质上是一个包装 Move
对象的双端队列.
I have a class called Action
, which is essentially a wrapper around a deque of Move
objects.
因为我需要向前和向后遍历 Moves
的双端队列,所以我有一个向前迭代器和一个 reverse_iterator 作为类的成员变量.这样做的原因是因为我需要知道我什么时候已经过了结束".双端队列,无论是我前进还是后退.
Because I need to traverse the deque of Moves
both forward and backwards, I have a forward iterator and a reverse_iterator as member variables of the class. The reason for this is becuase I need to know when I have gone one past the "end" of the deque, both when I am going forwards or backwards.
类如下所示:
class Action
{
public:
SetMoves(std::deque<Move> & dmoves) { _moves = dmoves; }
void Advance();
bool Finished()
{
if( bForward )
return (currentfwd==_moves.end());
else
return (currentbck==_moves.rend());
}
private:
std::deque<Move> _moves;
std::deque<Move>::const_iterator currentfwd;
std::deque<Move>::const_reverse_iterator currentbck;
bool bForward;
};
Advance
函数如下:
void Action::Advance
{
if( bForward)
currentfwd++;
else
currentbck++;
}
我的问题是,我希望能够检索到当前 Move
对象的迭代器,而无需查询我是前进还是后退.这意味着一个函数返回一种类型的迭代器,但我有两种类型.
My problem is, I want to be able to retrieve an iterator to the current Move
object, without needing to query whether I am going forwards or backwards. This means one function returning one type of iterator, but I have two types.
我应该忘记返回一个迭代器,而是返回一个对 Move
对象的 const 引用吗?
Should I forget returning an iterator, and return a const reference to a Move
object instead?
推荐答案
这正是促使STL设计开始的那种问题.有以下真正原因:
This is exactly the sort of problem that prompted the design of STL to start with. There are real reasons for:
- 不将迭代器与容器一起存储
- 使用接受任意迭代器的算法
- 让算法评估整个范围而不是单个项目一次
- Not storing iterators along with containers
- Using algorithms that accept arbitrary iterators
- Having algorithms evaluate an entire range instead of a single item at a time
我怀疑您现在看到的或多或少只是真正问题的冰山一角.我的建议是退后一步,不要问如何处理目前的设计细节,而是问一个更笼统的问题,关于你想要完成什么,以及如何最好地完成它最终结果.
I suspect what you're seeing right now is more or less the tip of the iceberg of the real problems. My advice would be to take a step back, and instead of asking about how to deal with the details of the design as it currently stands, ask a somewhat more general question about what you're trying to accomplish, and how best to accomplish that end result.
对于那些主要关心标题中问题的人来说,答案是非常合格的是".特别是,reverse_iterator 有一个 base()
成员来执行此操作.资格虽然有些问题.
For those who care primarily about the question in the title, the answer is a heavily qualified "yes". In particular, a reverse_iterator has a base()
member to do that. The qualifications are somewhat problematic though.
演示问题,考虑如下代码:
The demonstrate the problem, consider code like this:
#include <iostream>
#include <vector>
#include <iterator>
int main() {
int i[] = { 1, 2, 3, 4};
std::vector<int> numbers(i, i+4);
std::cout << *numbers.rbegin() << "
";
std::cout << *numbers.rbegin().base() << "
";
std::cout << *(numbers.rbegin()+1).base() << "
";
std::cout << *numbers.rend() << "
";
std::cout << *numbers.rend().base() << "
";
std::cout << *(numbers.rend()+1).base() << "
";
}
在这个特定的时刻在我的特定机器上运行它会产生以下输出:
Running this at this particular moment on my particular machine produces the following output:
4
0
4
-1879048016
1
-1879048016
总结:使用 rbegin()
我们必须在转换为前向迭代器之前添加一个以获得有效的迭代器 - 但使用 rend()
我们必须不在转换之前添加一个以获得有效的迭代器.
Summary: with rbegin()
we must add one before converting to a forward iterator to get an iterator that's valid -- but with rend()
we must not add one before converting to get a valid iterator.
只要您使用 X.rbegin()
和 X.rend()
作为通用算法的参数,就可以了——但经验表明转换为前向迭代器通常会导致问题.
As long as you're using X.rbegin()
and X.rend()
as the parameters to a generic algorithm, that's fine--but experience indicates that converting to forward iterators often leads to problems.
然而,最后,对于问题的主体(而不是标题),答案与上面给出的差不多:问题源于试图创建一个将集合与几个迭代器组合在一起的对象进入那个集合.解决这个问题,使用正向和反向迭代器的整个业务就变得没有意义了.
In the end, however, for the body of the question (as opposed to the title), the answer is pretty much as given above: the problem stems from trying to create an object that combines the collection with a couple of iterators into that collection. Fix that problem, and the whole business with forward and reverse iterators becomes moot.
这篇关于我可以将反向迭代器转换为正向迭代器吗?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持编程学习网!