C++ 双映射是否可以使视图的一侧与视图值的另一侧具有不同的键?怎么做呢?

Is C++ bimap possible with one side of view having different key than other side of the view value? How to do that?

提问人:Lukas Salich 提问时间:6/4/2018 最后编辑:Lukas Salich 更新时间:6/6/2018 访问量:311

问:

一开始我需要一张地图,所以我使用了 std::map。
然后,添加了一些要求,我还需要获取“value”的“键”(foos for bar),所以我使用了

boost::bimaps::bimap<
  boost::bimaps::unordered_set_of<boost::bimaps::tagged<std::string, foo>>, 
  boost::bimaps::multiset_of<boost::bimaps::tagged<std::string, bar>>>

在那之后,又增加了一些要求,所以现在我需要为每个 foo 存储一个号码,从右侧视图中,我需要能够调用和获取成对(foo + 为 foo 存储的数字),但我仍然希望能够调用并获取酒吧。<bimap>.righ.find(bar)<bimap>.left.find(foo)

如何实现?如果可能的话,我更喜欢一些现代的 C++ 而不是提升,但我想如果没有提升,就很难拥有双映射功能。

编辑:我应该注意尺寸很重要,所以我不想存储任何涉及两次的零件,速度也很重要。

我应该有类似
的东西.
我希望能够调用并获取“bar1”,
但也希望能够获取 pair(“foo1”, 100)。
"foo1"+100 <-> "bar1""foo2"+300 <-> "bar4"<bimap>.left.find("foo1")<bimap>.right.find("bar1")

C++ 键值对 Boost-BIMAP

评论

0赞 UKMonkey 6/4/2018
把数字放进foo?创建 foo->number 的新地图?
0赞 Lukas Salich 6/5/2018
对不起,我添加了一个注释,我不想存储两次 foo。我想将数字添加到 foo 中,但后来我意识到我希望能够在没有数字的情况下搜索 foo 并获取条形图。
0赞 UKMonkey 6/5/2018
“搜索没有号码的 Foo 并获取栏。 好的 - 所以制作一个具有可选号码的 Foo 版本;在(或 boost::bimap 使用的任何内容)中被忽略operator <
0赞 n. m. could be an AI 6/5/2018
我认为提升多索引在这里会是一个更好的选择。
0赞 Lukas Salich 6/5/2018
@UKMonkey我在想这样的事情。您的意思是使用字符串和 int 创建一个结构,并重写运算符<仅使用字符串部分?这可以工作,但我期望更整洁的东西。无论如何,谢谢。

答:

0赞 Lukas Salich 6/6/2018 #1
#include <boost/multi_index/hashed_index.hpp>
#include <boost/bimap/bimap.hpp>

using namespace std;

struct ElementType { 
  string foo; 
  string bar;
  uint64_t number; 
};

using namespace boost::multi_index;

using my_bimap = multi_index_container<
  ElementType,
  indexed_by<
    hashed_unique<member<ElementType, string, &ElementType::foo>>,
    ordered_non_unique<member<ElementType, string, &ElementType::bar>>
  >
>;

int main() {
  my_bimap instance;

  instance.insert({"foo", "bar", 0});
  instance.insert({"bar", "bar", 1});

  cout << instance.get<0>().find("bar")->foo << endl;
  cout << instance.get<0>().find("bar")->bar << endl;
  cout << instance.get<0>().find("bar")->number << endl;
  auto range = instance.get<1>().equal_range("bar");
  for (auto it = range.first; it != range.second; ++it) {
    cout << it->foo << endl;
    cout << it->number << endl;
  }

  cin.sync();
  cin.ignore();
}

输出:

bar
bar
1
foo
0
bar
1