python隐式二进制搜索

时间:2014-05-10 06:26:44

标签: python performance

我有已经排序的列表。

我经常需要查看

if foo in sortedlist:
    pass  # not really.  but not the point.

有没有办法教'in',sortlist是排序的,它应该二进制搜索列表?

2 个答案:

答案 0 :(得分:4)

Python支持显式过度隐式。如果您知道数据已排序,则可以选择显式使用bisect module,或者使用该模块创建实现list的{​​{1}}子类。

例如:

__contains__

可以用作import bisect class SortedList(list): def __contains__(self, elem): idx = bisect.bisect_left(self, elem) return idx < len(self) and self[idx] == elem 的替代,list会自动使用in。您可能希望覆盖__contains____setitem__.extend()以按排序顺序维护列表。

答案 1 :(得分:2)

我的建议是将列表子类化为使用排序列表:

from bisect import bisect_left
class SortedList(list):
    def __init__(self, l):
        list.__init__(self, sorted(l))
    def __contains__(self, obj):
        pos = bisect_left(self, obj, 0, len(self))
        return (pos != len(self) and self[pos] == obj)

然后:

>>> l = SortedList([4,3,5435,123,54,2,343,23])
>>> l
[2, 3, 4, 23, 54, 123, 343, 5435]
>>> 23 in l
True
>>> 25 in l
False
>>> 123122 in l
False
>>> -1 in l
False