我有一张存储<int, char *>
的地图。现在我想按照插入的顺序检索元素。 std::map
返回按键排序的元素。它甚至可能吗?
答案 0 :(得分:5)
如果您不关心基于int
的订单(IOW您只需要插入订单,而您不关心正常的密钥访问),只需将其更改为vector<pair<int, char*>>
即可,根据定义按插入顺序排序(假设您只在末尾插入)。
如果你想同时拥有两个索引,你需要Boost.MultiIndex
或类似的东西。你可能需要保留一个单独的变量,它只能向上计数(可能是一个稳定的计数器),因为你可以使用.size()+1
作为新的“插入时间键”,只有当你从未从地图中删除任何内容时
答案 1 :(得分:4)
现在我想按照插入的顺序检索元素。 [...]甚至可能吗?
不,不是std::map
。 std::map
将元素对插入已经排序的树结构中(在插入操作之后,std :: map无法知道添加每个条目的时间)。
您可以通过多种方式解决此问题:
使用std::vector<std::pair<int,char*>>
。这将有效,但不提供地图的自动排序。
使用Boost东西(@BartekBanachewicz建议使用Boost.MultiIndex)
使用两个容器并保持同步:一个带有顺序插入(例如std::vector
),另一个带按键索引(例如std::map
)。
自己使用/编写自定义容器,以便支持两种类型的索引(按键和插入顺序)。除非你有非常具体的要求并且经常使用它,否则你可能不需要这样做。
答案 2 :(得分:1)
有两种选择(除了Bartek建议的那些):
如果您仍需要基于密钥的访问权限,则可以按插入顺序使用地图以及包含所有密钥的向量。但是,如果您想稍后删除元素,则效率会降低。
您可以在您的值中构建链表结构:而不是值为char * s,它们是char *的结构以及之前和之后插入的键**;一个单独的变量存储列表的头部和尾部。您需要自己进行簿记,但它可以为您提供有效的插入和删除。它或多或少是boost.multiindex会做的。
**存储地图迭代器会很好,但这会导致循环定义问题。