哪个更好 std::prev(itr) 或 --itr?
Posted
技术标签:
【中文标题】哪个更好 std::prev(itr) 或 --itr?【英文标题】:Which one is better std::prev(itr) or --itr? 【发布时间】:2018-04-10 14:26:21 【问题描述】:我正在迭代一个双向数据结构。我可以使用 (++
, --
) 或 (std::prev
,std::next
,std::advance
) 来实现。以后使用比其他有优势吗?
【问题讨论】:
请更具体一点:容器/迭代器到底是什么? @Sumit Jha 有时它们不可互换。例如比较 auto next = std::next( first );并且自动下一个 = ++first; 主要是它们不等价。但这就是说std::prev
会对自然不允许朝那个方向迭代的容器做坏事,--itr
在这样的容器上不会编译。所以我会使用后者。
@Bathsheba std::prev
不会在底层使用operator--
,因此如果迭代器不是双向的,也无法编译?
【参考方案1】:
他们做的事情略有不同。所以总的来说两者都不是更好。
特别是std::prev
不会修改itr
。因此,最好在 itr
不应该或不能修改时(参见 S.M. 的答案,例如后者)。 --itr
和 std::advance
一定要修改 itr
,所以在必须修改 itr
时更好。
std::prev
和 std::advance
优于 --itr
的一个优点是它们的参数 n
在您需要推进多个步骤时可以避免编写循环。如果迭代器是随机访问,它们比循环更有效。
【讨论】:
如果迭代器是随机访问的,我们也可以做i + n
和i += n
...
@Aconcagua 和使用std::prev / std::advance
优于-
/ -=
的(可能是不利的)优势在于它适用于任何类型的双向迭代器;不仅仅是随机访问。
@Aconcagua 我忘了在我最后的评论中添加,确实,使用--
循环也适用于非随机访问迭代器。
好吧,除了你回答的最后一句话之外,我不同意你的观点......虽然技术上没有错,但使用 RA 迭代器我不会循环,而是使用 +/-(=) n而是运营商。 std::advance
的主要好处是不必使用 NRA 迭代器显式编写循环...“一致性”也可以作为在 RA 迭代器上使用它的参数。
@Aconcagua 我经常希望我的算法与 NRA 迭代器一起使用,但我也希望提高使用 RA 迭代器的效率。 std::prev
和 std::advance
实现了这两个目标。 +/-(=) 运算符不能同时实现两者。【参考方案2】:
我认为优势在cppreference.com 中得到了很好的描述。例如std::prev
具有如下所述的优势:
虽然表达式
--c.end()
经常编译,但不能保证 这样做:c.end()
是一个右值表达式,并且没有迭代器 要求保证右值的减少 去工作。特别是,当迭代器被实现为指针时,--c.end()
不能编译,而std::prev(c.end())
可以。
【讨论】:
以上是关于哪个更好 std::prev(itr) 或 --itr?的主要内容,如果未能解决你的问题,请参考以下文章