C++ 如何擦除C++;地图?

C++ 如何擦除C++;地图?,c++,stl,C++,Stl,在C++std::map中,有没有一种简单的方法可以找到n个元素?特别是我正在寻找一种算法来从映射中删除最后的k元素。将迭代器检索到n元素并调用std::map::erase,这样做是有意义的。要求是不受复杂性的影响-这应该可以擦除O(N)中的元素范围 复制数据不应该只是为了删除元素。例如,一种解决方案是将数据复制到std::vector,然后在std::vector上执行std::nth_元素,然后std::map::find查找迭代器,以找出从何处进行擦除 另一种解决方案是迭代std::ma

C++
std::map
中,有没有一种简单的方法可以找到
n个元素?特别是我正在寻找一种算法来从
映射
中删除最后的
k
元素。将迭代器检索到
n元素
并调用
std::map::erase
,这样做是有意义的。要求是不受复杂性的影响-这应该可以擦除
O(N)
中的元素范围

复制数据不应该只是为了删除元素。例如,一种解决方案是将数据复制到
std::vector
,然后在
std::vector
上执行
std::nth_元素
,然后
std::map::find
查找迭代器,以找出从何处进行擦除


另一种解决方案是迭代
std::map
,在要删除的元素数量上维护一个计数器变量。这将给出
O(n)
。是否可以用STL算法替换
for
循环的

编辑:编辑原始帖子后,答案不适用。

地图不提供比索引更好的对元素的线性访问,如
向量
deque
。您可以使用
std::advance
,但所需时间与
k
成正比。如果
k
很小,它通常会足够快-它基本上包括遵循
k
指针。下面是一个例子:

template<typename Map>
void erase_last_elements(Map & map, ptrdiff_t k)
{
    assert(k >= 0);
    assert(map.size() >= (size_t)k);
    typename Map::iterator i = map.end();
    std::advance(i, -k);
    map.erase(i, map.end());
}

否则,您必须维护一个单独的索引,或者使用不同的容器。如果您不插入和删除太多元素,像排序的
向量
这样的东西可能是合适的。

有什么理由
std::map
不提供访问第n个元素的
O(log(n))
解决方案吗?删除“end()-1”应该更有效对于k次。这听起来是一个合理的解决方案,Stefan。@Leonid-他们不能快速访问第n个元素,因为他们必须维护一个单独的索引,这需要更多内存,或者减慢插入或删除的速度。@Stefan-为什么你认为这样做会更快?渐进地,复杂性是相同的,如果在一次擦除调用中删除所有树,则可能需要更少的树重新平衡。这正是我不想做的。
template<typename Map>
void erase_last_elements(Map & map, ptrdiff_t k)
{
    assert(k >= 0);
    assert(map.size() >= (size_t)k);
    typename Map::iterator i = boost::prior(map.end(), k);
    map.erase(i, map.end());
}