Python相当于std :: set和std :: multimap

时间:2010-02-22 07:28:26

标签: c++ python performance data-structures dictionary

我正在将一个C ++程序移植到Python。在某些地方,它使用std::set来存储定义自己的比较运算符的对象。由于Python标准库没有等效的std::set(一个有序键值映射数据结构),我尝试使用普通字典,然后在迭代时对其进行排序,如下所示:

def __iter__(self):
    items = self._data.items()
    items.sort()
    return iter(items)

但是,分析表明,.sort()__cmp__的所有来电都是严重的瓶颈。我需要一个更好的数据结构 - 本质上是一个排序字典。有谁知道现有的实施?如果不这样做,关于我应该如何实现这一点的任何建议?读取性能比写入性能更重要,时间比内存更重要。

如果每个键支持多个值,则加分,例如C ++ std::multimap

请注意,OrderedDict类不符合我的需要,因为它按插入顺序返回项目,而我需要使用__cmp__方法对它们进行排序。

4 个答案:

答案 0 :(得分:5)

您应该使用sort(key=...) 您使用的关键功能将与您已使用的cmp相关。优点是key函数被调用n次,而cmp被称为nlog n次,而key通常是cmp所做工作的一半

如果您可以加入__cmp__(),我们可能会向您展示如何将其转换为关键功能

如果您在修改之间进行了大量迭代,则应该缓存已排序项的值。

答案 1 :(得分:5)

对于排序字典,你可以(ab)使用python的timsort的稳定性:基本上,保持项目部分排序,在需要时在最后追加项目,切换“脏”标志,并在迭代之前对剩余项进行排序。有关详细信息和实施,请参阅此条目(A Martelli的回答): Key-ordered dict in Python

答案 2 :(得分:3)

Python没有内置的数据结构,尽管bisect模块提供了使用适当高效的算法保持排序列表的功能。

如果您有一个排序键列表,可以将它与collections.defaultdict(list)结合使用,以提供类似多图的功能。

答案 3 :(得分:0)

在他的书“Programming in Python 3”中,Mark Summerfield介绍了一个排序的字典类。源代码在this zip archive中可用 - 查找SortedDict.py。在书中详细描述了SortedDict类(我非常推荐)。它支持用于比较的任意键和每个键的多个值(Python中的任何字典都可以,因此,我认为这不是什么大问题。)