微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

类似于Python的二进制搜索功能,可在排序列表中查找大于特定值的第一个数字

如何解决类似于Python的二进制搜索功能,可在排序列表中查找大于特定值的第一个数字

您是否尝试过该bisect模块

def find_ge(a, key):
    '''Find smallest item greater-than or equal to key.
    Raise ValueError if no such item exists.
    If multiple keys are equal, return the leftmost.

    '''
    i = bisect_left(a, key)
    if i == len(a):
        raise ValueError('No item found with key at or above: %r' % (key,))
    return a[i]

find_ge(somenumbers, 262139)

您的代码错误(1)low > high是有效的终止情况。(2)你不应该停留在low == high,例如,当它会返回一个不正确的索引num == 3你的somenumbers

解决方法

我试图用Python编写一个函数,该函数在排序列表中查找第一个数字,该数字大于作为参数传递的特定值。我在网上找到了使用简单列表推导来实现此目的的示例,但是出于我的目的,我需要经常在大型列表上执行此操作,因此以线性时间运行的搜索过于昂贵。

我在编写类似于迭代的二进制搜索的函数来实现此目的方面遇到了麻烦,尽管我遇到了一些无法正常工作的情况。顺便说一句,该功能不需要处理列表中没有较大项目的情况。这是我现有的功能:

def findFirstLarger(num,sortedList):
    low = 0; 
    high = len(sortedList) - 1

    mid = -1
    while True:
        print("low: " + str(low) + "\t high: " + str(high))
        if (low > high):
            print("Ah geez,low is " + str(low) + " and high is " + str(high))
            return # debugging,don't want this to happen
        if low == high:
            return sortedList[low]
        else:
            mid = (low + high) / 2;
            if num == sortedList[mid]:
                return sortedList[mid]
            elif num > sortedList[mid]:
                low = mid + 1
            else:
                high = mid - 1

我已经注意到该功能不起作用的一种情况如下:

>>> somenumbers=[n*2 for n in range(131072)]
>>> somenumbers[-5:]
[262134,262136,262138,262140,262142]


>>> binsearch.findFirstLarger(262139,somenumbers)
low: 0   high: 131071
low: 65536   high: 131071
low: 98304   high: 131071
low: 114688  high: 131071
low: 122880  high: 131071
low: 126976  high: 131071
low: 129024  high: 131071
low: 130048  high: 131071
low: 130560  high: 131071
low: 130816  high: 131071
low: 130944  high: 131071
low: 131008  high: 131071
low: 131040  high: 131071
low: 131056  high: 131071
low: 131064  high: 131071
low: 131068  high: 131071
low: 131070  high: 131071
low: 131070  high: 131069
Ah geez,low is 131070 and high is 131069

此处的正确结果将是262140,因为这是列表中的第一个数字大于262139

谁能推荐一个更清洁的实施方案,实际可行?我认为这不会是一个深奥的问题,尽管到目前为止我还无法在任何地方找到解决方案。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。