【问题标题】:How to iterate first ten items from the container如何从容器中迭代前十个项目
【发布时间】:2018-10-12 09:37:22
【问题描述】:

我只想打印前 10 个插入的项目,而将其余的留在后面。我必须使用什么代码(而不是使用 myset.end() )仅打印前 10 个整数而不是打印每个整数。

int main ()
{
std::set<int> myset;
std::set<int>::iterator it;

// set some initial values:
for (int i=1; i<=20; ++i) 
    myset.insert(i*10);    

std::cout << "myset contains:";
for (it=myset.begin(); it!=myset.end(); ++it)
std::cout << *it << ' ';
std::cout << "\n\n";

return 0;
}

【问题讨论】:

  • std::set的迭代器不是ransom-access,所以最简单的方法是设置一个计数器,当它达到10时中断。
  • 对于其他一些容器,比如std:vector,可以使用begin() + 10作为10个元素后停止的结束条件。

标签: c++ stl iterator containers


【解决方案1】:

您可以使用std::next 如下:

const auto begin = myset.begin();
const auto end = myset.size() < 10 ? myset.end() : std::next(begin, 10);
for (auto it = begin; it != end; ++it) {
    std::cout << *it << ' ';
}

【讨论】:

  • 为什么是const auto begin 而不仅仅是for (auto it = myset.begin(), ...)
  • 为了避免重复 myset.begin() 也用作 std::next 中的参数。
  • 另外,由于std::next 会消耗input_iterator,因此似乎有一点通用性损失?但问题是关于容器的,所以它仍然适合。
  • 如果你 100% 确定 myset 至少有 10 个元素,我会简单地写 for (auto it=myset.begin(), end=std::next(it,10); it!=end; ++it);它更简洁。可能前面有assert(myset.size() &gt;= 10);
  • 另外,我喜欢这个解决方案,但是,我会注意到它可能效率低下,因为它有效地迭代了集合中的元素两次(而其他带有计数器的解决方案则没有)。跨度>
【解决方案2】:

您可以只保留一个count 变量并在它达到10 或达到myset.end() 时立即中断循环。

int main ()
{
    std::set<int> myset;
    std::set<int>::iterator it;

    // set some initial values:
    for (int i=1; i<=20; ++i) 
        myset.insert(i*10);    

    int count = 0;
    std::cout << "myset contains:";
    for (it=myset.begin(); count < 10 && it!=myset.end(); ++it, ++count)
        std::cout << *it << ' ';

    std::cout << "\n\n";

    return 0;
}

【讨论】:

    【解决方案3】:

    我会这样做:

    int nCount = 0;
    for (it=myset.begin(); nCount<10 && it!=myset.end(); ++nCount, ++it)
    {
        std::cout << *it << ' ';        
    }
    

    希望这会有所帮助。

    【讨论】:

    • 在不依赖延迟增量时使用后增量在 C++ 中是个坏主意;这意味着创建不必要的副本,而不是对除原始类型之外的所有类型执行纯粹的就地增量(并且迭代器不是原始类型)。设为++it,而不是it++
    • 改了,好像有人已经有了同样的答案。谢谢。
    • @KillzoneKid:要么你误读/误用了注释,要么在我评论过的这个答案的版本和历史上没有保留的当前版本之间进行了编辑。该注释中对++ 和迭代器的关注与在r 值上使用它有关,而不是与++ 和一般的迭代器有关。 ++it 是将 any 迭代器向前推进一步的惯用方式; allowing increment is a contractual requirement of all iterator categoriesit 是一个左值,递增是完全没问题的。
    • 鉴于std::next 通常会以std::advance 的形式实现,它被定义为对不满足RandomAccessIterator 要求的迭代器使用增量,如果增量将是荒谬的不保证可以工作,但std::next 可以。
    • @ShadowRanger 我指的是迭代器的 ++ 与 std::next 的一般用途。感谢您阐明 r 值细节。
    猜你喜欢
    • 2022-11-20
    • 2019-12-01
    • 2018-10-18
    • 1970-01-01
    • 1970-01-01
    • 2020-03-21
    • 1970-01-01
    • 2020-07-27
    • 2018-07-24
    相关资源
    最近更新 更多