问题是您需要通过 keys 对其进行排序或散列以获得合理的插入和查找性能。实现它的一种天真的方法是按值排序的条目树结构,以及用于查找键的树位置的字典。不过,您需要深入更新树,因为此查找字典需要保持正确。本质上,就像您对可更新堆所做的那样。
我认为有太多的选择可以从这样的结构中创建一个合理的标准库选项,而它却很少需要。
更新:可能对您有用的一个技巧是使用双重结构:
像往常一样存储键值对的常规dict
任何类型的排序列表,例如使用bisect
然后你必须在两者上实现共同的操作:一个新的值被插入到两个结构中。棘手的部分是更新和删除操作。您使用第一个结构查找旧值,从第二个结构中删除旧值,然后(更新时)像以前一样重新插入。
如果您也需要知道键,请将 (value, key) 对存储在您的 b 列表中。
更新 2:试试这个课程:
import bisect
class dictvs(dict):
def __init__(self):
self._list = []
def __setitem__(self, key, value):
old = self.get(key)
if old is None:
bisect.insort(self._list, value)
dict.__setitem__(self, key, value)
else:
oldpos = bisect.bisect_left(self._list, old)
newpos = bisect.bisect_left(self._list, value)
if newpos > oldpos:
newpos -= 1
for i in xrange(oldpos, newpos):
self._list[i] = self._list[i + 1]
else:
for i in xrange(oldpos, newpos, -1):
self._list[i] = self._list[i - 1]
self._list[newpos] = value
dict.__setitem__(self, key, value)
def __delitem__(self, key):
old = self.get(key)
if old is not None:
oldpos = bisect.bisect(self._list, old)
del self._list[oldpos]
dict.__delitem__(self, key)
def values(self):
return list(self._list)
我猜这不是一个完整的dict。我还没有测试过删除,只是一个很小的更新集。您应该对其进行更大的单元测试,并将values() 的返回与sorted(dict.values(instance)) 的返回进行比较。这只是为了展示如何使用bisect更新排序列表