Python列表索引超出范围,即使在对索引定界之后也是如此

时间:2018-06-25 10:27:05

标签: python arrays list range index-error

在下面的代码中,我尝试查看给定列表的下一项是否与上一项相反(即“北”与“南”或“东”与“西”)。当然,一旦到达列表的最后一项,这将引发IndexError。 但是,我已经仔细地定界了for循环,以便它在到达最后一个索引之前停止。

"TypeError: Cannot read property 'name' of undefined"

有人可以向我解释为什么这仍然会引起def dirReduc(arr): for i in range(len(arr)-1): if arr[i] == "NORTH" and arr[i+1] == "SOUTH": arr.remove("NORTH"), arr.remove("SOUTH") elif arr[i] == "SOUTH" and arr[i+1] == "NORTH": arr.remove("SOUTH"), arr.remove("NORTH") elif arr[i] == "WEST" and arr[i+1] == "EAST": arr.remove("WEST"), arr.remove("EAST") elif arr[i] == "EAST" and arr[i+1] == "WEST": arr.remove("EAST"), arr.remove("WEST") return arr 吗?

这是示例输入: IndexError: list out of range

6 个答案:

答案 0 :(得分:3)

问题是START_HOURS_RANGE=6-22 返回一个迭代的固定对象。每次迭代都不会重新计算数组的长度。

一种可能的解决方案是将所有您不想“删除”的元素复制到另一个列表中。

答案 1 :(得分:0)

在进行迭代时不要从list中删除项目(这会导致您的错误)。您可以尝试以下方法:

def dirReduc(arr):
    expected_list = arr
    for i in range(len(arr) - 1):

        if arr[i] == "NORTH" and arr[i + 1] == "SOUTH":
            expected_list.remove("NORTH"), expected_list.remove("SOUTH")

        elif arr[i] == "SOUTH" and arr[i + 1] == "NORTH":
            expected_list.remove("SOUTH"), expected_list.remove("NORTH")

        elif arr[i] == "WEST" and arr[i + 1] == "EAST":
            expected_list.remove("WEST"), expected_list.remove("EAST")

        elif arr[i] == "EAST" and arr[i + 1] == "WEST":
            expected_list.remove("EAST"), expected_list.remove("WEST")

    return expected_list

答案 2 :(得分:0)

这是因为要从列表中删除该元素,然后它将以未更新的len / range继续遍历列表。 为了避免这种情况,可以使用这种丑陋的方法:

def dirReduc(arr):

    for i in range(len(arr)-1):
        if i >= len(arr):
            break
        if arr[i] == "NORTH" and arr[i+1] == "SOUTH":
            arr.remove("NORTH"), arr.remove("SOUTH")

        elif arr[i] == "SOUTH" and arr[i+1] == "NORTH":
            arr.remove("SOUTH"), arr.remove("NORTH")

        elif arr[i] == "WEST" and arr[i+1] == "EAST":
            arr.remove("WEST"), arr.remove("EAST")

        elif arr[i] == "EAST" and arr[i+1] == "WEST":
            arr.remove("EAST"), arr.remove("WEST")

    return arr

答案 3 :(得分:0)

该错误可能是由于第二个'elif'引起的,因为如果您正在阅读的arr[i]与数组的最后一个元素匹配,则无法考虑下一个元素{ {1}},因为您超出了数组的长度。

答案 4 :(得分:0)

发生错误是因为您要遍历列表并在每次迭代期间删除元素。通常,修改要迭代的基础对象很危险,并且无论使用哪种语言,都会导致有趣的错误。作为初学者,除非有充分的理由,否则应避免这种做法。

如建议的那样,创建基础列表的副本并从该副本中删除元素而不是要迭代的对象是避免这种情况的一种好方法。如果这样做,make sure you do it correctly

作为另一种可能的解决方案,请考虑使用字典将每个方向映射到相反的方向:

opposite = { "NORTH": "SOUTH", "SOUTH": "NORTH", "EAST": "WEST", "WEST": "EAST" } 

现在,当您遍历列表时,可以进行

def consolidate_directions(direction_list):
    directions = []
    # iterating over enumerate(iterable) is like iterating 
    # over iterable except it gives you access to both the current 
    # iteration count and the current item being processed on each iteration
    for i, direction in enumerate(direction_list):
        # this is a trick to avoid out of bounds error when checking for
        # the last element of the list. % is the modulus operator that returns 
        # 0 if the right hand side divides the left hand side evenly. In this 
        # case that would signify the first element of the list, meaning the 
        # current element is the last 
        last_index = (i - 1) % len(direction_list)
        next_index = (i + 1) % len(direction_list)
        if next_index == 0:
            return directions
        else:
            if not (direction_list[next_index] == opposite[direction]) \
             and not (direction_list[last_index] == opposite[direction]):
                directions.append(direction)
    return directions

更多一般性的反馈:大多数Python程序员使用蛇形大小写代替函数名(就像我在上面所做的那样)而不是驼峰式大小写。而且,Python作为一种语言的优势之一是它具有很高的可读性-它几乎可以像英语一样阅读。随意对变量和函数使用高度描述性的名称。这使您的代码更容易为其他程序员阅读和理解,也使您以后更容易阅读和理解。

PEP-8 Style Guide中对此进行了很好的介绍,在使用Python进行编程时,您应该尝试尽可能严格地遵循它。

答案 5 :(得分:0)

def dirReduc(arr):
    if len(arr)-1>0:
       num=  len(arr)-1
       for i in range(num):
           if arr[i] == "NORTH" and arr[i+1] == "SOUTH":
               arr[i]="error", arr[i+1]="error"

           elif arr[i] == "SOUTH" and arr[i+1] == "NORTH":
               arr[i]="error", arr[i+1]="error"
           elif arr[i] == "WEST" and arr[i+1] == "EAST":
               arr[i]="error", arr[i+1]="error"
           elif arr[i] == "EAST" and arr[i+1] == "EAST":
               arr[i]="error", arr[i+1]="error"
    return arr

def main(){
    arr=["EAST","EAST"]#just a example
    arrbuff=[]
    arrbuff.append(dirReduc(arr))#arrbuff is ["error","error"]
    newArr=[];#all correct direction
    for i in range(len(arrbuff)):
        if arrbuff[i] == "error" :
            print("what the error u set hahaha")
        else:
            newArr.append(arrbuff) 
}