【问题标题】:how to get matching key using the value in a map C++如何使用映射 C++ 中的值获取匹配键
【发布时间】:2012-09-26 09:16:55
【问题描述】:

我有一个结构体作为值类型的映射

map<int id, struct_t*> table

struct_t
{
int prev;
int wt;
string name;
}

只使用prev,我需要找到对应的id。提前非常感谢!

编辑:

int key=0;
for(auto it = table.begin(); it != table.end(); ++it)
{
     if(table[(*it).first].prev == ?)
}

这就是我的地图数据的样子:

id    prev abundance  thing
1573  -1      0       book
1864  1573    39      beds
2075  1864    41      tray
1760  2075    46      cups

对于每个 id,我需要找到 NEXT 匹配的 id。因此,对于上一列中的 1573,我需要找到一个匹配的“id”,即 1864。此外,std::next 不起作用,因为数据集不一定在下一个元素中具有匹配的 id。希望这会有所帮助!

请帮帮我!!!我的老板已经对我花这么多时间学习 C++ 感到失望(已经 3 周了!)

【问题讨论】:

  • map 的密钥是什么?
  • 你的意思是数据类型吗?它是 int id
  • 地图是用来搜索它们的键,而不是值。也许你应该调整你的设计或使用另一种容器。
  • 精通C++需要3个多星期...

标签: c++ stl map struct


【解决方案1】:

如果您有现代编译器(支持 lambda),您可以执行以下操作:

const int prevToFind = 10;
auto findResult = std::find_if(std::begin(table), std::end(table), [&](const std::pair<int, struct_t*> &pair)
{
    return pair.second->prev == prevToFind;
});

int foundKey = 0; // You might want to initialise this to a value you know is invalid in your map
struct_t *foundValue = nullptr
if (findResult != std::end(table))
{
    foundKey = findResult->first;
    foundValue = findResult->second;

    // Now do something with the key or value!
}

如果您有较旧的编译器,请告诉我,我可以更新示例以改用谓词类。

【讨论】:

  • 我不太明白这个..我不需要结构,我需要一个 int 的键。
  • 你想要钥匙吗?听起来你的地图是倒退的......这是对上面代码的简单更改(只需使用 findResult->first)。
  • 成功了!!非常感谢!!如果我知道你的地址,我会送你巧克力!
  • 哈哈没关系,点我的答案旁边的勾,把它标记为正确答案。 :-)
  • 使用 std::find_if 和 lamda 的绝妙解决方案 :-)。
【解决方案2】:

简单的循环就可以做到:

#include <map>
#include <string>
#include <iostream>

int main()
{
   std::map<int, std::string> m = {
      std::make_pair(0, "zero"), std::make_pair(1, "one"), std::make_pair(2, "two")
   };

   int key = 0;
   for (auto &i : m) {
      if (i.second == "two") {
         key = i.first;
         break; // to stop searching
      }
   }

   std::cout << key << std::endl;
}

当然,您需要设置自己的 if 语句来进行搜索。 请注意,提升双向地图可能是一种解决方案 (boost::bimap)

【讨论】:

  • 所以,我添加了我前进的方向,但我不知道我应该在 if 语句中比较什么!
  • 试试if (i.second-&gt;prev == the_id_youre_looking_for)
  • 这对我来说看起来比接受的答案要简单得多。我不明白为什么这没有任何赞成票......
【解决方案3】:

循环遍历地图当然可以,但您可能需要考虑使用第二张地图作为索引:

map<int,int> table_idx;

每当您向table 添加新条目时,您还需要更新table_idx,存储与每个prev 对应的idtable_idx 将允许您在 log(N) 时间内反向查找 id

int prev_for_id = table_idx[id];

【讨论】:

  • 循环遍历地图是什么意思?
  • 我指的是上面一些答案中采用的方法:遍历地图中的每个条目,直到找到 prev 字段等于您正在寻找的 id 的值。
【解决方案4】:

我感觉你是一个初学者,所以如果你能告诉我们你想做什么会很好,因为你可能试图解决一个错误的问题。
如前所述,地图旨在通过键而不是值进行搜索。
话虽如此,如果您坚持以这种方式搜索地图,您可能会想查看 Boost Bimap

【讨论】:

  • 是的,我是初学者。我已经为这个项目苦苦挣扎了 3 周了!我会更新问题
  • 好的,我想了解您的问题。在我的脑海中,我首先将所有数据放入地图中(接下来添加了最初未初始化的字段)。然后我会遍历整个地图,并为每个具有 value.prev==Y 的键做 map[Y]->value.next=X
  • 我有点赶时间,所以我没有时间测试它,但你可能想自己尝试一下,如果可以的话修复错误...#include #include 使用命名空间标准;结构 mystruct { int prev;下一个;诠释重量;字符串名称; }; std::map 表; int main() { mystruct 首先; mystruct 第二个;表[11] = 第一个;表[22] = 第二; for (auto&el: table) { if (el.second.prev!=-1) table[el.second.prev].next=el.first; } }
【解决方案5】:

难道不能用类似的东西生成一个反向地图

typedef std::map<int, struct_t*> map_t;
typedef std::map<struct_t*, int> reverse_map_t;

reverse_map_t get_reverse( map_t m )
{
    reverse_map_t r;
    for( const auto& p: m )
    {
        r[p.second] = p.first;
    }
    return r;
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2016-04-03
    • 2014-08-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-08-25
    • 1970-01-01
    相关资源
    最近更新 更多