这个问题已经在这里有了答案:

    print difflist
    for line in difflist:
        if ((line.startswith('<'))or (line.startswith('>')) or (line.startswith('---'))):
            difflist.remove(line)
    print difflist

在这里,最初,

difflist = ['1a2', '> ', '3c4,5', '< staring', '---', '> starring', '> ', '5c7', '< at ', '---', '> add ', '']

我对代码的期望是打印

['1a2', '3c4,5', '5c7', '']

但是我得到的是

difflist= ['1a2', '3c4,5', '---', '> ', '5c7', '---', '']

===============>>#1 票数:3

当遍历列表时,python会保留它所指向的数组元素的整数索引。 但是,当您删除当前元素时,所有后面的元素都将移至较低的索引。 然后,位置索引会递增,然后您才能“查看”已移动的元素来代替已删除的元素。

最终,最好通过列表理解来完成:

difflist = [ line for line in difflist if not line.startswith(('<','>','---'))]

如果您确实需要执行该操作,只需在左侧使用切片分配:

difflist[:] = [ line for line in difflist if not line.startswith(('<','>','---'))]

===============>>#2 票数:2

我认为您可能会使迭代器无效; 换句话说,您不应尝试删除要遍历的列表中的项目。

您可能想创建一个新列表,其中仅包含您关心的项目。

例如:

newdifflist = []
for line in difflist:
    if not ((line.startswith('<'))or (line.startswith('>')) or (line.startswith('---'))):
        newdifflist.append(line)

使用列表startswith()startswith()多个参数的更多pythonic:

newdifflist = [line for line in difflist if not line.startswith(('<', '>', '---')) ]

===============>>#3 票数:1

result = []
for line in difflist:
    if not line.startswith(('<', '>', '---')):
        result += [line]

或使用列表推导:

[line for line in difflist if not line.startswith(('<', '>', '---'))]

===============>>#4 票数:1

改为这样做:

>>> difflist = [i for i in difflist if not i.startswith(('<','>','---'))]
>>> difflist
['1a2', '3c4,5', '5c7', '']

进行.remove()更改顺序,因此(kinda)会弄乱for循环。 查看mgilson的答案以获取更多信息

===============>>#5 票数:0

与其尝试从列表中删除该项目,不执行任何操作并使用所需的内容创建另一个列表。

array = []
for line in difflist:
    if ((line.startswith('<'))or (line.startswith('>')) or (line.startswith('---'))):
        pass
    else:
        array.append(line)

现在,数组将成为您要寻找的数组!

===============>>#6 票数:0

发生的事情没有任何“异常”。 实际上,这很正常。 这是正在发生的事情:

  1. 循环正在查看项目i
  2. 项目符合您的测试,因此将其删除。 项目i + 1现在是项目i
  3. 您的循环再次开始,迭代器前进,指向项目i + 1 ,但从未测试项目i

有几种可能的解决方案:

  1. 创建一个仅包含所需项目的新列表,而不是从现有列表中删除项目。 这具有更好的算法复杂性,并且在Python中也更有效,但是可以使用更多的内存。
  2. 以相反的顺序迭代列表。 这样,您将仅转移已经查看过的项目。
  3. 遍历列表的副本。
  4. 使用内部while循环而不是if

对于此问题,解决方案4可能如下所示:

for i, line in enumerate(difflist):
    while line.startswith(('<', '>', '---')):
        difflist.pop(i)
        line = difflist[i]

这样,您一直在查看相同的索引,直到它无法通过测试为止,然后才允许迭代器继续进行下一个索引。

(我把你的条件消除不必要的括号过多,以及改变你的自由remove ,以pop - remove需要从列表中的每一次开始搜索,让您的环路倒楣的画家算法 )。

您可能要考虑的另一件事是使用deque (来自collections模块); 这是一个链接列表(常规的Python list实际上是可调整大小的数组),从中删除元素会更快一些。

  ask by user2086905 translate from so

未解决问题?本站智能推荐: