这让我很困惑,我正在实现一个自定义迭代器,我在这里读到:http://en.cppreference.com/w/cpp/concept/InputIterator, *iter++
的行为应该首先使用解引用运算符,然后将返回值(复制)增加1。
我已经在我的自定义迭代器中覆盖了operator*
和operator++(int v)
,问题是当我执行*iter++
时,operator++(int v)
在operator*
之前被调用,这是正确的行为,但不是我想做的(我猜?)。
如果你读了这个链接,你会看到,在表的最后一行,它说如果你执行*iter++
,你的实现应该首先取消引用,然后增加结果,这不是默认的行为。
我真的不知道该做什么,有什么主意吗?
理解答案后,标题误导,对不起!
谢谢,
Johan
从您提供的链接来看,*i++
相当于:
value_type x = *i; // (1)
++i; // (2)
return x; // (3)
即
- 取消对
i
的引用并将其存储在x
- 递增迭代器
- 返回在对迭代器加1之前对解引用得到的值
x
。
可以在接受输入迭代器的模板代码中使用,如下所示:
template <typename InputIterator, typename T>
InputIterator drop_until (InputIterator i, T const & x)
{
while (*i++ != x);
return i;
}
此行为的实现通常看起来像
struct my_iterator
{
// ...
value_type operator * ()
{
// return the value that this operator is pointing to
}
my_iterator operator ++ (int)
{
my_iterator copy = *this;
// increment *this iterator
return copy;
}
// ...
};
这是有效的,因为调用operator++(int)
的i++
返回前一个迭代器的值,然后该值被解引用,而i
本身被加1。
要增加解引用值,您应该手动指定操作符优先级:
(*i)++;
由于这是c++标准中定义运算符优先级的方式,因此您无法为表达式*i++
实现此行为,否则我猜i
将不再是迭代器。
如果你读了链接,你会看到,在表的最后一行,据说如果你执行*iter++,你的实现应该首先取消引用,然后增加结果
操作顺序与结果无关。该网站并没有说操作符必须按这个顺序调用,只是说副作用必须是相等的。站点上的示例进行了简化。下面的操作具有相同的副作用,但其操作顺序与调用*iter++
时这两个操作符的实际实现相同:
const It it_copy = i; // copying the iterator is part of post increment
++i; // increment is called first
value_type value = *it_copy; // dereference second
return value;
结果是一样的。
如果你调用*iter++
,你不能得到表中显示的顺序,但你也不需要。