python教程—提高Python中非常大的字典的性能-Python实用宝典

python教程—提高Python中非常大的字典的性能

我发现,如果我在开始时初始化一个空字典,然后在for循环中向字典中添加元素(大约110,000个键,每个键的值是一个列表,在循环中也在增加),那么速度会随着for循环的进行而下降。

我发现,如果我在开始时初始化一个空字典,然后在for循环中向字典中添加元素(大约110,000个键,每个键的值是一个列表,在循环中也在增加),那么速度会随着for循环的进行而下降。

我怀疑问题是,字典在init时不知道键的数量,并且它没有做一些非常聪明的事情,所以可能存储冲突变得非常频繁,并且它变慢了。

如果我知道键的数量,并且确切地知道这些键是什么,那么python中有没有什么方法可以使dict(或散列表)更有效地工作?我隐约记得,如果你知道键,你可以巧妙地设计哈希函数(完美哈希?)并预先分配空间。

回答

如果我知道键的数目以及这些键的确切数目,就在这里
python中使dict(或散列表)更有效的任何方法
有效吗?我依稀记得,如果你知道钥匙,你就能
巧妙地设计哈希函数(完美哈希?)并分配
事先空间。

Python没有提供一个预调整大小的选项来加速字典的“增长阶段”,也没有对字典中的“放置”提供任何直接控制。

说,如果钥匙总是提前知道,您可以将它们存储在< a href = " http://docs.python.org/2.7/library/functions.html func - set " rel = " noreferrer " > < em > < / em > < / >和建立你的字典从集合使用< a href = " http://docs.python.org/2.7/library/stdtypes.html # dict.fromkeys”rel = " noreferrer " > < em > dict.fromkeys () < / em > < / >。这个类方法是,根据集合大小对字典进行了优化,它可以填充字典,而不需要任何对_hash__()的新调用:

    >>> keys = {'red', 'green', 'blue', 'yellow', 'orange', 'pink', 'black'} >>> d = dict.fromkeys(keys) # dict is pre-sized to 32 empty slots

如果您的目标是减少碰撞,那么您可以按照字典中的插入顺序运行实验,以最小化堆积。(查看Knuth的TAOCP中Brent对算法D的变体,了解这是如何实现的)。

通过为字典检测一个纯Python模型(例如this ),可以计算另一种插入顺序的平均探测权重。例如,插入dict.fromkeys([11100, 22200, 44400, 33300])平均每次查找1.75个探针。这超过了每次查找dict.fromkeys([33300, 22200, 11100, 44400])时平均2.25次探测。

另一个“技巧”是在一个完全填充的字典中增加空闲度,方法是把它骗到中,在不添加新键的情况下增加它的大小s:

    d = dict.fromkeys(['red', 'green', 'blue', 'yellow', 'orange']) d.update(dict(d)) # This makes room for additional keys # and makes the set collision-free.

最后,您可以为您的键引入您自己的定制的_hash__(),目的是消除所有冲突(可能使用一个完美的散列生成器,例如gperf)。

​Python实用宝典 (pythondict.com)
不只是一个宝典
欢迎关注公众号:Python实用宝典

本文由 Python实用宝典 作者:Python实用宝典 发表,其版权均为 Python实用宝典 所有,文章内容系作者个人观点,不代表 Python实用宝典 对观点赞同或支持。如需转载,请注明文章来源。
1

发表评论