【问题标题】:Remove element from std::map based on the time of insertion根据插入时间从 std::map 中删除元素
【发布时间】:2012-04-01 02:27:36
【问题描述】:

我需要根据插入时间(或其他更有效的方法)从 std::map 中删除元素。

地图可能包含数千个元素,如果我存储时间并迭代地图以检查每个元素的时间,最终可能会非常耗时。

有没有人知道如何在 std::map 变老时擦除元素?

【问题讨论】:

  • 你可能想看看 boost 多索引容器
  • 旧的?你需要一个明确的标准来执行一个动作,除非你定义一个,否则 Q 几乎是没有方向的。
  • @PlasmaHH 是的,boost 本来不会但不可能在这个项目中使用
  • @Alborz:我经常听到这种说法,我想知道是否有人在使用 boost...
  • "或其他比这更有效的方法" - 那么,根据插入时间与否?如果不是,我建议将其作为地图中的第一个元素,这将比搜索地图更有效;)

标签: c++ map std stdmap


【解决方案1】:

std::map<> 类型不知道何时插入元素。它仅用于保存键/值对映射。它也没有插入顺序的概念,因此它甚至不能提供相对类型的插入。

要执行您想要的操作,您需要在元素和插入时间之间添加关联。如果您想要的只是相对顺序,那么您可以使用与地图配对的std::queue。每次插入地图时,您也会插入std::queue。队列前面的元素比后面的元素更老,您可以将其用于相对年龄

【讨论】:

    【解决方案2】:

    非常接近LRU Cache

    Boost.MultiIndex 库显示了 MRU Cache(最近使用)的示例,因此将其适应 LRU 应该很简单。

    基本上这个想法是并行维护两个数据结构:

    • map 中的项目
    • deque 引用到地图中

    基本代码:

    static double const EXPIRY = 3600; // seconds
    
    std::map<Key, Value> map;
    std::deque<std::pair<std::map<Key, Value>::iterator, time_t>> deque;
    
    bool insert(Key const& k, Value const& v) {
      std::pair<std::map<Key, Value>::iterator, bool> result =
        map.insert(std::make_pair(k, v));
    
      if (result.second) {
        deque.push_back(std::make_pair(result.first, time()));
      }
    
      return result.second;
    }
    
    // to be launched periodically
    void clean() {
      while (not deque.empty() and difftime(time(), deque.front().second) > EXPIRY) {
        map.erase(deque.front().first);
        deque.pop_front();
      }
    }
    

    当然,如果目的是获得多线程代码,这些结构需要同步。

    【讨论】:

    • 不应该是&gt; EXPIRY 吗?
    • @klaus:在我看来是这样。这只是错误的...... 7 年 oO
    • 哈哈!顺便说一句,谢谢你的回答,它对我帮助很大(:
    【解决方案3】:

    您可以使用队列,并在对象插入地图时插入指向对象的指针。队列中的下一项将是最旧的一项。或者,如果您还需要插入时间,您可以将一对存储在队列中。

    【讨论】:

    猜你喜欢
    • 2013-05-25
    • 1970-01-01
    • 1970-01-01
    • 2022-01-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-02-21
    相关资源
    最近更新 更多