【问题标题】:Iterator to last element of std::vector using end()--使用 end() 迭代到 std::vector 的最后一个元素--
【发布时间】:2016-08-29 06:37:28
【问题描述】:

我有一个std::vector,我想要iterator 到向量中的最后一个元素;我将存储此迭代器以供以后使用。

注意:我想要一个迭代器引用,而不是 std::vector::back。因为我希望以后能够从std::vector::begin 计算这个对象的索引。

以下是我将迭代器获取到最后一个元素的逻辑:

std::vector<int> container;
std::vector<int>::iterator it = container.end()--;

由于std::vector::end 的时间复杂度为 O(1),有没有更好的方法来做到这一点?

【问题讨论】:

  • 我看不出有什么问题。那么问题是什么?
  • 您需要--container.end() 而不是container.end()--。此外,您需要先确保容器不是空的,否则您将有未定义的行为。
  • 啊哈,我看到通过 std::vector&lt;int&gt;::iterator it = container.end()-- 我会得到 end 迭代器然后递减迭代器
  • 除了计算最后一个元素的索引之外,你还打算用迭代器做什么?如果不出意外,您可以只存储索引。无论哪种方式,迭代器或索引在您实际使用它们时可能已经无效。
  • 如果您以一种使索引无效的方式弄乱了向量的内容,那么这肯定也会使迭代器无效。

标签: c++ c++11 vector stl


【解决方案1】:

你有 rbegin 可以满足你的需要

cplusplus reference

auto last = container.rbegin();

【讨论】:

  • 但是rbegin 没有返回一个迭代器,它返回一个reverse_iterator。
  • @MarkRansom 这是一种迭代器,而不是std::vector&lt;int&gt;::iterator
  • 另一种解决方案就是保存一个整数索引.size(),而不是一个迭代器。
  • @dau_sama 不应该是size-1吗?否则索引将指向最后一个元素。
【解决方案2】:

你这样做的方式会给你错误的迭代器,因为 post increment 直到 赋值之后才会改变值。

总是这样:

auto it = std::prev(container.end());

记得先检查容器不是空的,所以你的迭代器存在于一个有效的范围内。

【讨论】:

    【解决方案3】:

    我认为你的意思是:

    std::vector<int>::iterator it = --container.end();
    std::vector<int>::iterator it = container.end() - 1;
    std::vector<int>::iterator it = std::prev(container.end());
    

    您无意中只是返回了end()。但是所有这些的问题是当向量为空时会发生什么,否则它们都会在恒定时间内做正确的事情。尽管如果向量为空,则无论如何都没有最后一个元素。

    在存储迭代器时也要小心——它们可能会失效。

    请注意,如果vector&lt;T&gt;::iterator 只是T*(这将是有效的),则上面的第一种形式是错误的。后两者不管用,所以更可取。

    【讨论】:

    • 如果迭代器是指针,第一个无效。其他两个都很好。
    • 而第二个仅限于随机访问容器。
    • @MSalters 问题是关于std::vector
    • @T.C.为什么第一个无效?递减指针是一种常见的操作。
    • @quark 右值是临时值,修改它们没有意义;这就是不允许修改运算符++-- 的原因。见What exactly is a R-Value in C++?。但是,如果临时是类类型,则不会直接应用运算符,而是将其转换为 operator-- 调用,这在右值上是允许的 - 请参阅Why myClassObj++++ doesn't incur a compile error : '++' needs l-value
    猜你喜欢
    • 2011-02-10
    • 2015-09-27
    • 2019-12-07
    • 1970-01-01
    • 2015-04-20
    • 2017-01-03
    • 1970-01-01
    • 1970-01-01
    • 2016-02-12
    相关资源
    最近更新 更多