【问题标题】:Is there a way to intersect/diff a std::map and a std::set?有没有办法使 std::map 和 std::set 相交/区分?
【发布时间】:2012-04-22 20:35:06
【问题描述】:

我想知道是否有办法使用标准算法(如std::set_intersect)将定义为std::set<MyData*>std::map<MyData*, MyValue> 的两个结构相交或产生差异

问题是我需要计算地图的集合和键集之间的差异,但我想避免重新分配它(因为它是每秒对大型数据结构执行多次的事情)。有没有办法获得std::map 的“关键视图”?毕竟我正在寻找的是在进行设置操作时只考虑键,所以从实现的角度来看它应该是可能的,但我找不到任何东西。

【问题讨论】:

  • 看看 boost 迭代器库中的 filter_iterator。
  • 对不起,不是 filter_iterator -- transform_iterator。请参阅匿名者的回答。

标签: c++ stl map set


【解决方案1】:

您可以使用 boost 中的 transform_iterator 来调整 std::map 迭代器并仅返回键:

#include <algorithm>
#include <iostream>
#include <map>
#include <iterator>
#include <string>
#include <set>
#include <vector>

#include <boost/iterator/transform_iterator.hpp>

typedef std::map<std::string, int> map_t;
typedef std::set<std::string> set_t;

const map_t::key_type & getKey(const map_t::value_type & pair)
{
    return pair.first;
}

typedef const map_t::key_type & (*getKey_t)(const map_t::value_type &);

typedef boost::transform_iterator<getKey_t, map_t::iterator> key_iterator_t;

int main()
{
    map_t map;
    map["a"]=1; map["b"]=2;
    set_t set;
    set.insert("a"); set.insert("c");

    std::vector<std::string> v;

    std::set_intersection(set.begin(), set.end(),
        key_iterator_t(map.begin(), getKey),
        key_iterator_t(map.end(), getKey),
        std::back_inserter(v));
    std::copy(v.begin(), v.end(),
        std::ostream_iterator<std::string>(std::cout," , "));
}

【讨论】:

    【解决方案2】:

    set_intersection 处理有序集合。您可以编写一个自定义迭代器来包装标准映射迭代器并返回键。然后您可以将其与set_intersect 一起使用

    【讨论】:

      猜你喜欢
      • 2014-03-15
      • 2012-01-25
      • 2023-04-09
      • 1970-01-01
      • 2019-04-01
      • 2021-06-14
      • 1970-01-01
      • 2016-09-10
      • 1970-01-01
      相关资源
      最近更新 更多