0
    def unique(ip):
         file = open("/home/USER/Desktop/ipAddreses.txt",'r')
         list = file.readlines()
         list.sort()
         low = 1
         hi = len(list)
         target = convertToStr(ip)
         if hi > 1:
                 while low <= hi:
                 mid = low + (hi-low)/2
                 if list[mid] == target:
                     file.close()
                     return False            
                 elif list[mid] < target: 
                     low = mid+1
                 else:
                     hi = mid-1
         else:
                 if target == list[0]:
                     return False

file.close()
return True

得到这个错误:

    if list[mid] == target:
    IndexError: list index out of range

目的是搜索生成的 ip 地址,以确保所有随机创建的 ip 地址都是唯一的。以前在工作...回到家,现在我收到此错误

4

2 回答 2

0

我没有立即看到如何解决您的代码问题,但如果您只想解决手头的问题,这可能不是最好的方法。

  • 一般来说,排序然后进行二进制搜索几乎总是比对数组进行简单的线性搜索更糟糕。排序是 O(n log n),实际上需要“查看”数组的每个元素至少一次,并且需要将整个文件的至少一个副本存储在内存中。如果您只是遍历文件,您最多只能查看每个元素一次,并且只使用恒定数量的内存。

  • 无论如何,您可能不应该自己实现二进制搜索(除非您这样做是为了练习),因为您已经发现很容易出错。改用模块_bisect

  • 看起来您的代码中有一个退出路径,您没有明确关闭filetarget == list[0]部分)。这就是为什么with陈述很好的原因;他们为您处理。

你可以这样做:

def unique(ip):
    ip_str = convertToStr(ip)
    with open("/home/USER/Desktop/ipAddreses.txt", 'r') as f:
         return all(line.rstrip() != ip_str for line in f)

如果你要调用unique一堆 ip 地址,你可以避免每次都读取整个文件,并获得更快的查找,使用set

with open("/home/USER/Desktop/ipAddreses.txt", 'r') as f:
    ip_addresses = set(line.rstrip() for line in f)

def unique(ip):
    return convertToStr(ip) not in ip_addresses

也就是说,与模块的来源bisect相比,似乎不同之处在于您使用while low <= hi但他们使用while lo < hi,以及您使用hi = mid - 1他们使用的地方hi = mid。我认为(尽管我没有运行它来确定)如果您要搜索的字符串是列表中最大的字符串,那么您最终会得到low == hi == len(list), 所以你设置mid = len(list),当你这样做时它会中断list[mid]

于 2013-02-17T06:18:38.850 回答
-1

检查 mid 是否存在于列表中。

if mid in list:
    if list[mid] == target:
        # ...
于 2013-02-17T06:12:59.100 回答