C++ 插入无序的_映射需要太多时间

C++ 插入无序的_映射需要太多时间,c++,performance,stl,unordered-map,C++,Performance,Stl,Unordered Map,我编写了一个程序,从一个文件(大约500000个)中读取数字,并将其插入到数据结构中。数字是不同的。 我正在使用另一个结构(使用std::make_pair(myNumber,emptyStruct))将数字插入到一个无序映射中 在插入所有的数字之后,我只用它搜索几百次。在程序运行完成之前,我从不删除DS 分析之后,我注意到插入操作占用了大约50%的运行时间。(还有一些其他代码,它的运行次数与插入相同,但并不需要太多时间) 我想调整大小可能需要时间,所以我使用了保留函数500000,但结果仍然是

我编写了一个程序,从一个文件(大约500000个)中读取数字,并将其插入到数据结构中。数字是不同的。 我正在使用另一个结构(使用
std::make_pair(myNumber,emptyStruct))
将数字插入到一个
无序映射中

在插入所有的数字之后,我只用它搜索几百次。在程序运行完成之前,我从不删除DS

分析之后,我注意到插入操作占用了大约50%的运行时间。(还有一些其他代码,它的运行次数与插入相同,但并不需要太多时间)

我想调整大小可能需要时间,所以我使用了保留函数500000,但结果仍然是一样的


据我所知,这个DS应该是O(1)插入和搜索(取舍是大内存),所以我不明白为什么插入要花这么多时间。如何改进结果?

无序映射使用哈希表实现。它摊销了固定插入时间。为地图保留大小会有所帮助,但不会太多。在插入方面,没有比这更好的了

这意味着你也许可以在一段时间内刮胡子,但这只会是边缘的。例如,插入向量的速度稍快一些,但它也是按固定时间摊销的。因此,您将以搜索为代价在插入过程中节省一些时间


这就是数据库的作用所在。假设您将数据放在sqlite数据库中。创建数据库,创建以搜索值作为主键、以数据值作为其他属性的表,然后将这些值插入表中一次。现在,程序只需运行和查询数据库。它只读取所需的最小值。在本例中,sqlite数据库扮演您正在使用的无序映射的角色。

因为您没有使用值,只是在搜索存在,所以使用std::unordered_set。当您为地图中的每个关键点创建一个虚拟值时,它会执行您想要的操作

首先,我想重述一下大家所说的:插入500000项以使用它数百次将占用您相当大的时间,您无法真正避免这一点,除非您能够扭转局面--构建一组您正在搜索的内容,然后搜索500000次

综上所述,考虑到哈希表的性质,我能够在测试应用程序中插入500000个条目,从而获得一些改进:

回顾过去,我发现:

[插入]复杂性:平均情况:O(1),最坏情况O(大小())

默认情况下,无序映射容器的最大加载系数为1.0

当你为500000件物品预留空间时,你会得到500000个桶。如果在500000个存储桶中放入500000个数据块,将会发生大量冲突。我预留了额外的空间,而且速度更快


如果您确实需要速度,并且愿意得到一些错误,请查看bloom过滤器。

这是每次插入的O(1)。n个插入仍然是O(n)。我同意。这似乎是合理的。插入将是昂贵的。向后操作如何:首先加载要比较的值,然后检查输入文件。除了插入
无序映射
之外,您还可以进行更多其他处理,这将降低50%的部分。“时间太多”到底是多少?在地图中插入500000个元素的适当时间是多少?您考虑过使用向量吗?将它们全部插入,然后对向量排序,然后使用
binary\u search
进行搜索。无序映射使用哈希函数进行插入。这就是为什么它通常在插入时很慢,在查找时很快。您正在进行大量插入,并且有一个frew读取,因此std::map可能是一个更好的解决方案。看见