为什么multimap允许重复的键值对?

时间:2011-04-12 08:09:59

标签: c++ multimap

编辑: 注意,我询问为什么multimap不能包含重复的

multimap允许重复键值对的原因是什么? (不是

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

int
main(int argc, char** argv)
{
    std::multimap<std::string, std::string> m;
    m.insert(std::make_pair("A", "B"));
    m.insert(std::make_pair("A", "B"));
    m.insert(std::make_pair("A", "C"));
    std::cout << m.size() << std::endl;
    return 0;
}

这打印3,有点让我感到惊讶,我希望multimap表现得像一组,所以我期待2。

直观地说,它与C ++ std::map行为不一致,insert并不总是更改地图(而不是operator[])。

它背后有理由,还是随意的?

7 个答案:

答案 0 :(得分:17)

Multimap只有一个谓词排序键。它没有方法来确定值是否相等。值“A”是值“a”的重复吗?没有值的第二个谓词,没有任何说明。因此,在多图中讨论重复值甚至没有意义。

如果您想要一个存储对的容器,并强制执行该对的两个部分的唯一性,请查看boost::multi_index_container。它非常灵活,但结果却需要大量的参数。

答案 1 :(得分:11)

编辑:这个答案不再回答当前的问题了。我会保持原样,因为它已经投了很多,所以对某些人来说一定有用。

multimap中的 multi 表示相同的可以发生多次次。

标准对用作值的类型没有限制,因此不能假定operator==()已定义。因为我们不希望代码的结果取决于是否定义了运算符==(),所以它永远不会被使用。

std::multimap不是std::map的替代品。正如您所注意到的,当多次插入相同的密钥时,它的行为会有所不同。如果您想要std::map的行为,请使用std::map

还有std::multiset

理性:有时人们希望保留所有旧条目以获得相同的密钥。 [待定:在此处插入一些示例]

就个人而言,我几乎没有使用std::multimap。如果我想要同一个密钥的多个条目,我通常依赖std::map<std::vector<T> >

答案 2 :(得分:2)

允许值重复,因为它们不需要相互比较。除了复制它们之外,容器不能对值执行任何操作。这样可以启用multimap< int, my_class >等类型。

如果不希望使用重复的键值对,请使用set< pair< T, U > >并使用lower_bound查找给定键的第一个匹配项。

答案 3 :(得分:1)

如您所知,multimap允许拥有多个密钥。由于它没有对价值可比性施加任何限制,因此无法检查价值是否未加倍。

如果您想要一些字典数据结构允许重复键,而不是键值对,则必须确保值具有可比性。

假设我们有一种类型的游戏,其中有二维世界的sqaure字段,你可以把项目放在字段上。您可以拥有multimap<Field, Item>,这样您就可以在该字段上保留两个相同的项目。物品不一定要在这里比较。

答案 4 :(得分:1)

我的推理是multimap是基于Key查找/插入而不是值。因此,当插入元素时,重复键上的值是否相同不起作用。

23.3.2 类模板多图

  

1多图是一种关联   支持等效的容器   键(可能包含多个键)   相同键值的副本)和   提供快速检索值   基于键的另一种类型T。

答案 5 :(得分:0)

"multimap"旨在支持“多个”键,而不像简单的"map"。由于它允许多个键,因此不会为其值而烦恼,因此它在您的示例中显示了3个元素。另一个区别是,operator []不能multimap

答案 6 :(得分:0)

使用重复的[map,value]对是为了计算一个单词在一个书页上出现的次数,无论是没有次数,因此在该单词的多重映射中都没有输入,只要用一个条目,或多个条目与make_pair(word,page_number)在multimap中的出现次数有关。设计是我偶然发现这种用法的。