首页 > 解决方案 > IndexError:索引存在时列表索引超出范围

问题描述

对于 NOI 2018(荷兰国家信息学奥林匹克),我需要解决一个编码问题。

我的程序从标准输入接收一个介于 3 到 17 之间的偶数 N。然后它生成一个包含 N/2 个零和 N/2 个零的数组(如 [0,0,0,1,1,1])然后它按字典顺序生成该数组的所有排列并将其存储在另一个数组中。然后它会删除重复项,因为我生成所有排列的函数会生成重复项。

然后它会删除所有不符合标准的项目,即彼此相邻的相同值可能不超过两个。

然后它返回剩余项目的数量,然后输出每个项目。

这是我的代码:

N = int(input('N:'))

def genPermutations(num, index):

    if len(num) - 1 == index:

        if num not in rows:

            rows.append(num)

    for i in range(index, len(num)):

        newList = num[:]
        temp = newList.pop(i)
        newList.insert(index, temp)
        genPermutations(newList, index + 1)

num = []
rows = []

for j in range(2):

    for i in range(int(N) // 2):

        if j == 0 :

            num.append(0)

        else:

            num.append(1)

genPermutations(num, 0)
rows = list(set(map(tuple, rows)))

for i in reversed(range(len(rows))):
    rows[i] = list(rows[i])

    for j in range(len(rows[i]) - 2):

        if rows[i][j] == 1 and rows[i][j + 1] == 1 and rows[i][j + 2] == 1:

            rows.pop(i)

        elif rows[i][j] == 0 and rows[i][j + 1] == 0 and rows[i][j + 2] == 0:

            rows.pop(i)

print(len(rows))

for i in reversed(range(len(rows))):

    string = ''

    for j in range(len(rows[i])):

        string += str(rows[i][j])

    print(string)

现在的问题是,当我输入 N = 6 时,程序返回错误。对于 3 < N < 17 的所有其他值,它正在工作

标签: pythonpython-3.x

解决方案


print我用一个简单的语句追踪了这个问题:

for i in reversed(range(len(rows))):
    rows[i] = list(rows[i])
    for j in range(len(rows[i]) - 2):
        print("i=", i, "j=", j, len(rows), "rows;", len(rows[0]), "cols")
        if rows[i][j] == 1 and rows[i][j + 1] == 1 and rows[i][j + 2] == 1:
            rows.pop(i)

输出:

i= 19 j= 0 20 rows; 6 cols
i= 19 j= 1 20 rows; 6 cols
i= 19 j= 2 20 rows; 6 cols
i= 19 j= 3 19 rows; 6 cols

......还有你的问题。当您仍在尝试处理该行时,您从表中删除了一行。当你这样做时,你也需要break脱离j循环。在这两个子句中:

    if rows[i][j] == 1 and rows[i][j + 1] == 1 and rows[i][j + 2] == 1:
        rows.pop(i)
        break

    elif rows[i][j] == 0 and rows[i][j + 1] == 0 and rows[i][j + 2] == 0:
        rows.pop(i)
        break

这产生了 14 个排列的预期答案。

这仅失败了,N=6因为这是最终排列被删除的唯一集合。打印出每个 N 值的最终列表,你会看到...


推荐阅读