Python for语句的混乱行为

Python for语句的混乱行为,python,windows,if-statement,for-loop,Python,Windows,If Statement,For Loop,我有以下python代码: x = range(0,10) print x for number in x: print(number) if number%2<> 0: x.remove(number) print x 第一行和最后一行是对的,但是为什么没有打印出2、4、6和8呢?print语句不在if语句中 我在Windows7上使用pythonx,y。另外,我是Python新手……我已经习惯了C++您正在从列表x中删除项。在对列表x中的

我有以下python代码:

x = range(0,10)
print x

for number in x: 
    print(number)
    if number%2<> 0: 
        x.remove(number)

print x
第一行和最后一行是对的,但是为什么没有打印出2、4、6和8呢?print语句不在if语句中


我在Windows7上使用pythonx,y。另外,我是Python新手……我已经习惯了C++

您正在从列表x中删除项。在对列表x中的数字进行迭代时删除


for in单独维护一个索引,这就是为什么修改列表会产生意外行为。

您正在从列表x中删除项。在对列表x中的数字进行迭代时删除


for in单独维护一个索引,这就是为什么修改列表会产生意外行为。

基本上,当您在删除的同时迭代某些内容时,可能会出现奇怪的行为。发生的情况是,由于将某些值转移到已经迭代过的索引中,所以跳过了这些值

一种更好的方法是使用列表理解来过滤掉一些项目,例如:

[x for x in range(10) if x%2==0]
您可以简单地使用范围步骤仅创建偶数,但上面的解决方案允许您在任何条件下过滤掉


某些数字没有打印的原因是,当您循环并删除它们时,这些值正在改变位置。移除1时,可以想象所有值都被移动一个位置,迭代器指向2以前所在的位置,但现在那里的值是3,因此2永远不会被打印。其余的值也是如此。

基本上,当你在删除的同时迭代某些内容时,你可能会有奇怪的行为。发生的情况是,由于将某些值转移到已经迭代过的索引中,所以跳过了这些值

一种更好的方法是使用列表理解来过滤掉一些项目,例如:

[x for x in range(10) if x%2==0]
您可以简单地使用范围步骤仅创建偶数,但上面的解决方案允许您在任何条件下过滤掉


某些数字没有打印的原因是,当您循环并删除它们时,这些值正在改变位置。移除1时,可以想象所有值都被移动一个位置,迭代器指向2以前所在的位置,但现在那里的值是3,因此2永远不会被打印。其余的值也是如此。

正如Mark Rushakoff提到的,在迭代时不应该修改某些内容。将x中的for number更改为x[:]中的for number,它将按照您的预期工作。在本例中,您正在对副本进行迭代。

正如Mark Rushakoff提到的,您不应该在迭代过程中修改某些内容。将x中的for number更改为x[:]中的for number,它将按照您的预期工作。在本例中,您正在对副本进行迭代。

列表使用其索引进行迭代,但删除元素时会跳过一些索引

例如:

除去

[0,2,3,...] # (iterator is still at second)
迭代器进展

[0,2,3,...] # (iterator is at third - print 3)

列表使用其索引进行迭代,但删除元素时会跳过一些索引

例如:

除去

[0,2,3,...] # (iterator is still at second)
迭代器进展

[0,2,3,...] # (iterator is at third - print 3)
为清晰起见,添加一些打印语句:

x = range(10)

for index, number in enumerate(x):
    print "x is      ", x
    print "element is", number
    print "index is  ", index
    print

    if number % 2 == 0: 
        x.remove(number)
以及输出:

x is       [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
element is 0
index is   0

x is       [1, 2, 3, 4, 5, 6, 7, 8, 9]
element is 2
index is   1

x is       [1, 3, 4, 5, 6, 7, 8, 9]
element is 4
index is   2

x is       [1, 3, 5, 6, 7, 8, 9]
element is 6
index is   3

x is       [1, 3, 5, 7, 8, 9]
element is 8
index is   4
正如您所看到的,即使从列表中删除了元素,索引仍会继续增加1。这就是导致循环跳过元素的原因

正如其他人所指出的,在列表上循环并从中删除元素不是一个好主意。而是在副本上循环:

for number in x[:]:
或:

更好的是,用列表理解制作一个新列表:

[number for number in x if number % 2 == 0]
为清晰起见,添加一些打印语句:

x = range(10)

for index, number in enumerate(x):
    print "x is      ", x
    print "element is", number
    print "index is  ", index
    print

    if number % 2 == 0: 
        x.remove(number)
以及输出:

x is       [0, 1, 2, 3, 4, 5, 6, 7, 8, 9]
element is 0
index is   0

x is       [1, 2, 3, 4, 5, 6, 7, 8, 9]
element is 2
index is   1

x is       [1, 3, 4, 5, 6, 7, 8, 9]
element is 4
index is   2

x is       [1, 3, 5, 6, 7, 8, 9]
element is 6
index is   3

x is       [1, 3, 5, 7, 8, 9]
element is 8
index is   4
正如您所看到的,即使从列表中删除了元素,索引仍会继续增加1。这就是导致循环跳过元素的原因

正如其他人所指出的,在列表上循环并从中删除元素不是一个好主意。而是在副本上循环:

for number in x[:]:
或:

更好的是,用列表理解制作一个新列表:

[number for number in x if number % 2 == 0]

不要修改正在迭代的列表。其他人建议复制列表或收集新的要删除的内容列表。取而代之的是,收集那些你想留下的。这比复制列表并从未被迭代的副本中删除要快,也比收集要删除的列表然后删除它们要快

    evens = []
    for number in x:
        if number%2 == 0:
            evens += [number]
    print(evens)

不要修改正在迭代的列表。其他人建议复制列表或收集新的要删除的内容列表。取而代之的是,收集那些你想留下的。这比复制列表并从未被迭代的副本中删除要快,也比收集要删除的列表然后删除它们要快

    evens = []
    for number in x:
        if number%2 == 0:
            evens += [number]
    print(evens)

我第一次看到有人用pascal。认真地说,使用!=从现在起,在Python 3中已经消失了,除非您从未来导入barry,因为不再使用;它早就被弃用了,从Python3中消失了。使用!=相反。谢谢,我知道!=,我尝试了不同的事情,因为它没有按照我想要的方式工作。我是蟒蛇新手
我第一次看到有人用帕斯卡。认真地说,使用!=从现在起,在Python 3中已经消失了,除非您从未来导入barry,因为不再使用;它早就被弃用了,从Python3中消失了。使用!=相反。谢谢,我知道!=,我尝试了不同的事情,因为它没有按照我想要的方式工作。我是pythonnice的新手,因为我对它进行了解释。很好,因为我对它进行了解释。为了解决这个问题,我只需在列表中收集我要删除的内容,并在循环后删除它们。谢谢,为了解决这个问题,我只需在列表中收集我要删除的内容,并在循环后删除它们。列表理解过滤器的良好使用列表理解过滤器的使用这是这里最全面的答案:解释,解决方案和更好的选择。这是这里最全面的答案:解释,解决方案和更好的选择。